随笔分类 - Programming C/C++
C/C++程序设计中的一些想法,问题解决等
摘要:boost memory的gc_allocator的使用首先编译生成boost-memory的库,由于生成的是.so的动态库,所以需要在运行程序之前,将库文件的路径添加到LD_LIBRARY_PATH中。简单使用,auto_alloc比较简单,可以使用默认的存储管理,NS_BOOST_MEMORY::auto_alloc alloc;而scope_alloc稍微复杂一点,使用block_pool管理存储单元。NS_BOOST_MEMORY::block_pool recycle;NS_BOOST_MEMORY::scoped_alloc alloc(recycle);而在为变量申请空间时,使用
阅读全文
摘要:最开始的时候看到了许式伟的内存管理变革系列,看到性能测试结果的时候,觉得这个实现很不错,没有深入研究其实现。现在想把这个用到自己的一个项目中来,在linux下编译存在一些问题,所以打算深入研究一下。讨论C++内存管理的有两个主要的博客,一个是许式伟的系列,(CSDN: http://blog.csdn.net/xushiweizh/article/details/1388982,许式伟个人空间:http://xushiwei.com/gc-allocator-summary);另一个是CppExplore的一个内存管理系列(http://www.cppblog.com/CppExplore/a
阅读全文
摘要:C++中的枚举类型C++11提供了更安全的枚举类型,不能再直接把这种枚举值当作整数值来使用。但如果我们想把它作为整数来使用呢?例如enum class ElemType{ CAP, IND, VS};在以前,我们使用枚举类型的时候,没有添加class关键词,可以如下定义,enum ElemTypeOld{ CAP = 1, IND, VS = 3};在定义了某个枚举变量之后,可以将其与整数直接进行比较。但这样做存在一些问题,因为自定义的整数值可能不连续,某个定义了,其它的没有定义等。那么输出ElemTypeOld::IND时,会输出2,但如果把CAP的值改为2,那么IND的值就会是3,这就与V
阅读全文
摘要:在linux下编写C/C++程序,一般会习惯用Makefile来编译程序。总结一下自己学习使用Makefile的经验。一个C/C++项目,会有多个头文件和源程序文件,有时候还会用多个文件夹来组源代码的结构。文件之间会有依赖关系,当一个被依赖的文件被修改之后,不仅它自己需要重新编译,依赖它的文件也需要重新编译。然而如果一个文件不被其它文件依赖,那么它更改之后,就只需要重新编译自己,然后重新进行链接。当程序的文件比较多的时候,很多时候只有部分文件需要重新编译,不需要整个重新编译,所以这种编译链接的方式,是很有效的。在linux下面,使用make作为程序自动维护的工具。它会检查程序中文件或者模块的修
阅读全文
摘要:要实现一个类似于matlab可以计算表达式的程序,例如: x = agauss(4, 0.3, 1) /* agauss(u, s, d) 表示产生类似于高斯分布的随机数,u表示平均值,s表示方差sigma,d表示允许的最大偏离值。 */ y = x^2 - x; print eval(y) /* eval(x) 表示对x进行求值 */与一般的计算器不一样,求值不是实时计算,而是先用符号表示,类似于包含未知变量,然后给定未知变量的值,对符号表达式进行计算。程序设计表达式可以用一个类似于二叉树的结构组织起来,比如 a + b, 根节点 +, 包含左右两个节点a, b作为操作数,而agauss这.
阅读全文
摘要:先回顾一下hash表的相关内容,STL里面的unordered_map和map。使用unordered_map,通过hash函数,将key映射到一个位置,如果这个位置原本没有值,那么就可以将这个key作为唯一的下标来访问这个位置。但是如果这个位置已经被占了,那么就需要比较这个key和已经存在的下标是否一样。所以unordered_map需要提供key的hash和等于函数。由于是使用hash得到的值作为下标,所以会出现不同的key得到相同的下标值,称为冲突。处理冲突的方法,一种是使用一个链表,保存这个位置的key。每次hash到这个位置,就逐次比较链表里的key,以确定这个key是否已经存在。另
阅读全文
摘要:在C++中,标准库里面的容器,如vector,list都可以动态增长,如果把这些容器作为某个class的成员,那么这个class的内存是怎么分配的呢?写了一个简单的程序测试一下,如下,#include <string>#include <vector>#include <list>#include <iostream>using std::string;using std::vector;using std::list;using std::cout;using std::endl;class Elem{public: Elem(int i,st
阅读全文
摘要:在看一些C++的文章的时候,经常会看到关于delete与free的区别,delete不需要检查指针是否为NULL。如下面一篇文章http://www.cnblogs.com/zhuyp1015/archive/2012/07/20/2601698.html。但是有时候,又会看到由于delete引起的double free or corruption,我们可以写一个很简单的程序,来测试delete会不会引起double free。#include <iostream>using namespace std;#ifndef NULL#define NULL 0#endifclass A
阅读全文
摘要:一直想试试这个LLVM的,据说错误提示信息比GCC好,C++11支持的也更多。今天编译的时候,发现用了几个C++11特性了,gcc4.4没法编译,于是想,那就尝试一下LLVM吧。既然是想安装比较新的版本的LLVM,新立得软件包上的肯定不是好的选择。想用预编译好的.deb包,却发现不支持ubuntu10.04,好像11.10之后的是可以用deb包的。那就源代码编译吧,这应该总是可以的。目的,LLVM和Clang,编译C/C++,环境Ubuntu10.04,X86,gcc4.4.先搞清楚要准备哪些东西,在http://llvm.org/docs/GettingStarted.html#gettin
阅读全文
摘要:之前纠结enum class,其中一个问题就是,要输出type的名字,方便调试。今天尝试了一下输出重载,没想到竟然可以。测试如下,#include <iostream>using namespace std;enum class Type{ TEXT, _EOF};ostream& operator << (ostream& out,Type tp){ switch(tp) { case Type::TEXT: out << " TEXT ";break; case Type::_EOF: ...
阅读全文
摘要:之前实现的枚举类enum class虽然达到了当时期望的功能,但现在在用的时候出现了一些问题。比如新定义了一个Token的类,定义如下,class Token{public: Token(){} Token(int tp, string tx) { type = tp; text = tx; } int Type() const { return type; } string Text() const { return text; } friend ostream& operator << ...
阅读全文
摘要:虽然写过一些C++程序,有类有继承,但对虚函数和多态用的不多,最近想尝试一下多态,却出了些问题。于是不得不重新来学习虚函数与多态。简单的示例程序如下,class Lexer{public: Lexer(){} Lexer(string t){ name = "Lexer"; text = t; } virtual void Print(){ cout << name << ":" << text << endl; }protected: string name; string text;};class Ex
阅读全文
摘要:在实现lexer和parser的过程中,要定义token的类型。《编程语言实现模式》中使用的是java代码,直接定义static int TEXT = 1;并且可以在lexer扩展的时候继承到实际使用的lexer里面。但C++定义类的static成员时,必须在外面单独的进行初始化,对这一点不是很爽,在C++11中,实现了enum class,先看看这个enum class能不能满足要求,例如enum class TokenType{ _EOF, TEXT};TokenType a = TokenType::TEXT;那么就可以方便地使用TokenType::TEXT指代类型,只有同...
阅读全文
摘要:前几天使用list的排序功能,出现了一点问题,来总结一下。定义一个简单的节点类,包含一个字符串和一个整数,并重载了小于操作,根据整数的大小进行比较。class Node{ public: Node(string nm,int i) { name = nm; id = i; } void Print() { cout << name << ":" << id << endl; } friend bool operator < (...
阅读全文
摘要:Python里面字符串的操作很方便,比如split,strip。在C++里,string提供了length,得到字符串的长度,append,在字符串末尾添加字符串,push_back,在字符串末尾添加字符,insert,指定位置处插入字符串,或n个字符,assign,对字符串赋值,可以是某个字符串的从某个位置开始的多少个字符,也可以是常量字符串,也可以是指定个数的n个字符,replace,用某个字符串,或者某个字符串的从某个位置开始的多少个字符,替换原字符串从某个位置开始的多少个字符,erase,擦除指定区间的字符,swap,两个字符串的内容交换,但是没有提供split和strip,strip
阅读全文
摘要:C++文件操作。C++中引入了stream,相关的头文件<fstream>,支持文件输入与输出,还有两个<ifstream>和<ofstream>,分别支持文件读入和写入。文件的打开与关闭fstream作为一种对象,它的操作由构造函数,成员函数来完成。fstream ( ); explicit fstream ( const char * filename, ios_base :openmode mode = ios_base::in | ios_base::out ); fstream f("input.txt",fstream::in
阅读全文
摘要:前几天一直用Python做google code jam的练习题,文件操作很方便。如果用C/C++去做的话,那么首先要解决的就是文件操作。于是整理了一下文件操作的函数用法。先来看看C的文件操作。FILE* stream相关的头文件stdio.h,就可以使用与文件操作相关的数据类型和函数。文件的打开与关闭首先,定义文件指针,FILE* f,用fopen(const char* filename,const char* mode)来打开文件,用fclose(File* p)来关闭文件。文件的打开方式,"r"表示读,"w"表示写,"a"表示
阅读全文
摘要:在使用hash_map的程序中,编译的时候会报出warning,In file included from /usr/include/c++/4.4/ext/hash_map:60, from hash_a.h:6, from test.cpp:5:/usr/include/c++/4.4/backward/backward_warning.h:28:2: warning: #warning This file includes at least one deprecated or antiquated header which may be removed without further n
阅读全文
摘要:好久没做事情,也就没什么内容可更新的。这两天开始做事情了,问题就不断地出现了,就连使用标准的complex类都出问题。先说说问题吧。xxxx.cpp: In member function ‘void xxxx::xxxxxxxx()’:xxxx.cpp:100: error: ISO C++ forbids declaration of ‘type name’ with no typexxxx.cpp:100: error: expected primary-expression before ‘double’xxxx.cpp:100: error: expected ‘;’ before
阅读全文
摘要:使用list, vector 等这些标准库的类,查找是比较常用的功能,但是这些类没有提供find函数,因为对于自定义类型,它不知道如何去比较两个类型。http://www.cppreference.com/wiki/container/list/start但是STL提供了一种通用的查找函数find(iterator it0,iterator it1,target),下面介绍如何使用这个查找函数。// 定义一个简单的数据结构Inst.class Inst{ public: Inst(string nm,int val){ name = nm; ...
阅读全文