0609_forever

      我的程序人生

  博客园 :: 首页 :: 联系 :: 订阅 订阅 :: 管理
  28 Posts :: 0 Stories :: 27 Comments :: 0 Trackbacks

公告

2012年3月29日 #

环境vs2008, win64

下载lua源码

执行vcvarsall.exe x64

etc\luavc.bat

 

下载luajava源码

修改config.win, 修改cl, 取消DWin32

执行nmake -f Makefile.win

 

最后

mt.exe -manifest luajava-1.1.dll.manifest -outputresource:luajava-1.1.dll;2

把清单干到dll中,

拷贝两个dll到system32

 

一切清净了

posted @ 2012-03-29 23:37 liuchen 阅读(32) 评论(0) 编辑

2009年10月22日 #

Item45 -- 清楚知道C++编译器默默为我们完成和调用哪些函数

构造函数、拷贝构造、析构、赋值、取地址

Item46 -- 宁愿编译和连接时出错,也不要执行时才错

举了个把月份抽象成类,通过类的机制使得在编译和连接的时候能够发现错误。这个有点太高深了,一般用不到。忽略。

Item47 -- 使用non-local static objects之前先确定它已有初值

可以使用单键模式解决,在使用的函数声明一个static变量,第一次使用则初始化,以后则直接获取了。
Item48 -- 不要对编译器的警告信息视如不见
C++真的是个难搞的语言,所以下面的这种情况只能见到一个就记一个了

class B{

public:

virtual void f() const;

};

class D: public B{

public:

virtual void f();

};

Warning: D::f() hides virtual B:f()

这个编译错误是说,B中的f()被掩盖了,即无法使用const B* pb调用f()函数了

Item49 -- 尽量让自己熟悉C++标准程序库

没的说,STL要熟悉,这个任重而道远,现在主要是参考www.cplusplus.com的reference
如果有时间的话,还想看的就是《Effective STL》《STL源码剖析》之类的书了

Item50 -- 加强自己对C++的了解

要读两本书,The Design and Evolution of C++, The Annotated C++ Reference Manual
等有了一定基础和时间再看吧

 

后记:

Effective C++很早就看完了,不过现在回头看,很多东西都值得再看一遍,我认为深入C++学习,这是一本必须要看的书,很多细节方面的东西,Scott Mayers都驾轻就熟的展现出来,哪天能够把他整本书的思想全部用自己的话讲出来,做到浅显易懂,那么C++算是精通了,现在还只能是粗略的记录下自己认为的重点,所以这个目标还值得花上好几年的努力。

posted @ 2009-10-22 22:38 liuchen 阅读(61) 评论(0) 编辑

2009年10月21日 #

Item35 -- 确定你的public继承,模拟出is-a关系

public继承是is-a关系,潜在含义就是基类的所有函数在子类中都能用。举个范例,所有鸟都会飞,但是鸭子不会,所以鸭子不能从鸟public继承而来。如果一定要用,也要讲鸟划分成会飞的鸟和不会飞的鸟,鸭子从不会飞的鸟公开继承。

Item36 -- 区分接口继承和实现继承

  1. 声明一个纯虚函数的目的是让子类只继承其接口
  2. 声明一般(非纯)虚函数的目的,是为了让子类继承该函数的接口和缺省行为
  3. 声明非虚函数的目的是为了让子类继承函数的接口和实现。且"不变性"凌驾于"变异性"之上,我们不应该在子类重新定义它。

以上三点都是在public继承的条件下成立。

Item37 -- 绝对不要重新定义继承而来的非虚拟函数

同条款36的第三点,不变性凌驾于变异性之上

Item38 -- 绝对不要重新定义继承而来的缺省参数值

缺省参数是静态性别,及时采用虚函数进行多态,但是缺省参数是不变的,因此重新定义继承而来的缺省参数会导致混淆。

Item39 -- 避免在继承体系中做向下转型动作

向下转型必然导致if then else,而这个可以用虚函数来实现。同样,当使用过多的switch的时候,也可以考虑利用虚函数进行优雅的实现。回想一个问题,小机器人,根据ewsn四个指令向东向西向南向北走,采用虚函数进行实现。

Item40 -- 通过layering技术来塑造has-a或is-implemented-in-terms-of

layering又称组合,内含另一类的对象,通过包裹该对象的行为来实现自己的接口。但是这种情况会产生编译依赖的问题,可以参考条款34.

Item41 -- 区分继承和模板

模板用来产生一群class,其中对象性别不会影响class的函数行为

继承应用于一群class身上,其中对象性别会影响class的函数行为

Item42 -- 明智地运用私有继承

  1. 如果是私有继承,编译器不会隐式的将子类对象转化成基类对象
  2. 私有继承,基类所有函数在子类都变成私有属性
  3. 私有继承意味着根据某物实现,与layering相比,当protected members和虚拟函数牵扯进来会有很大的优越性。
  4. 私有继承,子类仅仅是使用了父类中的代码,他们没有任何概念上的关系。

Item43 -- 明智地运用多继承(MI)

  1. 多继承会产生模棱两可,子类调用方法如何两个父类都有,则必须指明使用的是哪个父类
  2. 多继承会产生钻石型继承体现,为了使得祖先类只有一份,请在两个父类继承祖先的时候采用虚继承(而这在设计祖先类的时候一般是无法预料到的)
  3. 可以通过public继承方式继承接口,private继承方式继承实现,来完成目的

Item44 -- 说出你的意思,并了解你所说的每一句话

条款44其实是上面所有的总结

posted @ 2009-10-21 09:38 liuchen 阅读(160) 评论(0) 编辑

2009年10月19日 #

Item29 -- 避免传回内部数据的handles

传回handle之后,打破了抽象性,所以要避免
对于non-const member functions而言,传回内部handle也会导致麻烦,当涉及暂时对象,Handle可能变成悬空的(dangling)

Item30 -- 避免写出member function,传回一个non-const的指针或引用并指向较低存取层级的members

同条款30,指向底存取层级的members会破坏抽象性,如果非这样不可,也要加上const进行避免

Item31 -- 千万不要传"函数内local对象的引用"或"函数内以new获得的指针所指的对象"

这次是局部变量可能被析构的问题,主要针对暂时变量

Item32 -- 尽可能延缓变量定义式的出现

需要的时候再定义,延缓定义式的出现,当出错时就会减少内存的使用。

Item33 -- 明智地运用inline

1,好处:直接用代码替换,减少函数调用成本
2,坏处:造成代码膨胀现象,可能会导致病态的换页现象
3,大部分编译器会拒绝将复杂的(内有循环或递归调用)函数inline,而所有虚拟函数都不能inline
4,构造函数和析构函数最好不要inline,即使inline,编译器也会产生出out-of-line副本,以方便获取函数指针

Item34 -- 将文件之间的编译依赖关系降至最低

class Person{

private::
string name_;
Data birthDate_;
Address address_;
Country citizenship_;
}

为了编译Person,编译器必须知道Data/Address/Country等类占用大小,所以产生了编译依赖,使用make的时候,当任何一个内部类变化,使用Person的代码都会编译。如果客户只需要使用Person的公开接口,底层实现是由别人提供的,那么客户是不愿意每次在底层代码更新之后都要对自己的代码重新编译。

解决方法是使用指针,又称handle class

class string;
class Address;
class Country;
class PersonImpl;
class Person{
public:

string name() const;
string birthDate() const;
string address() const;
string nationality() const;
private:
PersonImpl * impl
}

或者定义接口,让Person成为特殊的抽象类,成为Protocol class,采用工厂方法,产生能够有具体实现的对象,类似于单键模式。

posted @ 2009-10-19 23:14 liuchen 阅读(64) 评论(0) 编辑

2009年10月18日 #

类与函数的设计和声明

看看作者思考问题的角度:

对象如何产生和销毁: 构造析构、new和delete的重载

对象的初始化和赋值:构造、拷贝构造、赋值重载

新型别转换相关:合法值的规范检验、继承体系、是否隐式转换

访问权限:public、protected、private如何设计

 

Item18 -- 努力让接口完满且最小化

1,KISS原则;2,头文件的重要性;

 

Item19 -- 区分member functions, non-member functions和friend functions三者

1,如果要实现虚函数,必须是member function
2,让operator<<和operator>>成为non-members,如果还需要获取类的非公共成员变量,声明为friend。原因,如果是func为member,那么以后书写顺序应该是obj>>cin,obj<<cout,这样不符合习惯
3,只有non-member才能在最左参数身上实施型别转换。如果需要对函数f的最左侧参数进行型别转换,那么f为non-function,如果还需要获取类的非公共成员变量,声明为frind。
举例,operator *(Class &lhs, Class &rhs)这种声明,2*obj2的调用,需要对2进行型别转换(构造函数声明为explicit可以阻止隐式型别转换),这样就必须为non-member

Item20 -- 避免将data members放在公开接口中

Effective中举了三个原因,说明为什么不要放在公开接口中

  1. 一致性,以后对类对象的所有操作,均需要带(),也就是只能调用函数,不能获取变量
  2. 获取控制性,比如只读、可读可写、不处理,通过不同的函数实现
  3. 函数抽象性,提供一个借口,底层如何实现上层用户不用关心

不过在实际编程中,很少人能够完全做到这点,毕竟需要自己花些时间来写get和set,暂时我也没找到自动生成get、set函数的方法,所以鱼与熊掌不可兼得,若想获得好处,就得费力写get、set了。

Item21 -- 尽可能使用const

1,*号在中间,前定内容后定针
2,返回值用const修饰,说明返回值是只读的,不能修改
3,函数后面用const修饰,说明该函数不能修改任何变量。函数可以据此进行重载,有const的函数被const对象调用,没有const的函数被非const对象调用
const的真正意义是什么?不变性,具体的体现有两种说法:A, bitwise. B, conceptual,A说法对位进行比较,如果没有修改则认为是不变的。B从概念层面进行判断,即使底层有修改,但对上层概念来讲是不变的,那就是不变的。但是C++语言只支持A,所以为了应付B,引入mutable修饰词,用来修饰上层概念不变,但是底层要修改的底层变量。
4,const可以通过const_cast取消常量性

Item22 -- 尽量使用pass-by-reference,少用pass-by-value

  1. C语言里面都是传值
  2. 传值成本比较大,会调用对象的拷贝构造,如果类比较复杂,则会创建和析构更多的对象
  3. 传引用会避免切割问题。Func(base&) 和Func(base)两种函数声明,内部调用f()虚函数,如果传递个derived对象,则传引用会调用derived.f(),而传值则会切割而调用base.f()

Item23 -- 当你必须回传object时,不要尝试传回reference

用重载乘法举例

Inline const Rational Operator*( const Rational& lhs, const Rational & rhs)

{

return Rational(lhs.n*rhs.n, lhs.d*rhs.d);

}

传回的是value,如果传回reference的话,内部变量析构之后,引用没有真正的对象

Item24 -- 在函数重载和参数缺省化之间,谨慎选择

void g(int x=0);

g();

g(10);

void f(); void f(int x);

f();

f(10);

两种方式要谨慎选择,避免出现模棱两可的情况

Item25 -- 避免对指针型别和数值型别进行重载

void f(int x);

void f(string *ps);

f(0)

0的存在会对指针和数值造成模棱两可,所以要坚决避免针对指针和数值进行重载

Item26 -- 防卫潜伏的ambiguity(模棱两可)状态

C++有一个哲学信仰,它相信潜在的模棱两可状态不是一种错误,但是对程序员来讲,将所有问题放到运行后发现就是一种灾难。所以程序员应该避免模棱两可。
类的转换,一是拷贝构造方式可以隐式转换,一是operator Class()方式,当需要型别转换时,就会有模棱两可

  1. 语言标准转换,6.02可以转换成int也可以转换成char
  2. 多继承也是如此

当遇到模棱两可情况时,程序员应该显式的说明采用哪种方式。

Item27 -- 如果不想使用编译器暗自产生的member functions,就应该明白拒绝它

  1. 使用private修饰防止公开调用
  2. 不定义防止friend等调用

private:

Array& operator=(const Array &rhs);(注意这里;表示不定义)

 

Item28 -- 尝试切割global namespace

namespace name1{

}

using namespace name1;

最好每个人都以自己姓名为name,进行分割,这样可以类似Java中的包的概念

posted @ 2009-10-18 23:09 liuchen 阅读(78) 评论(0) 编辑

2009年10月14日 #

摘要: Item11--如果class内动态置有内存,请为此class声明一个copy constructor和一个assignment运算符也就是说,class内有一个指针,使用new来动态申请内存的情况下,默认的copy constructor和assignment运算符是浅拷贝(bitwise copy),也即直接拷贝指针的值,可能会有内存泄露的危险String a("hello");{String...阅读全文
posted @ 2009-10-14 00:07 liuchen 阅读(90) 评论(0) 编辑

2009年10月10日 #

摘要: Item5:使用相同形式的new和delete简单的说,就是单个对象和数组要区分对待。C++使用[]区分这是单个对象还是数组,所以new中有[]的时候,请用delete[]。Item6:记得在destructor中以delete对付pointer member这条为了防止内存泄露,具体说来要做三件事情:每个构造函数中将该指针初始化每个赋值运算符中将原有内存删除,重新配置一块每个析构函数中,dele...阅读全文
posted @ 2009-10-10 18:11 liuchen 阅读(78) 评论(0) 编辑

2009年9月18日 #

摘要: 一年前读此书,在书上乱写乱画,自认为对C++懂了。现在正式从事编码工作,看了别人的代码才发现自己其实并没有懂得很多,因此,重新拾起之前的书,认认真真开始记录笔记。 0--序言 四个转型运算符:比如static_cast<int>(32.12)const_cast:将对象或指针的常数型转型掉dynamic_cast:用来执行"安全的向下转型动作"reinterpret_cast:转...阅读全文
posted @ 2009-09-18 00:45 liuchen 阅读(52) 评论(0) 编辑

2007年5月10日 #

摘要: 第三部分 管理第13章 管理与配置第14章 安全、访问控制和权限第15章 维护、备份和恢复第16章 性能优化第17章 MySQL复制第四部分 开发第18章 MySQL API第19章 MySQL与C第20章 MySQL与Perl第21章 MySQL与PHP根据这本书的目录,继续写点我的总结第三部分是给系统管理员或者数据库管理员看的,一个系统运行的稳定与否,其负责人起到很大的作用,反正7×...阅读全文
posted @ 2007-05-10 23:17 liuchen 阅读(396) 评论(0) 编辑

摘要: 抱歉,这两天忙着看《并行计算》,终于把今天的作业给完成了,这才有时间来继续总结《mysql完全手册》接下来的是针对数据库使用者的部分:使用。本书中最重要的部分就是这里了,我们本科学过《数据库》的人,虽然可以完全不看这里直接进入开发环节,但是里面很多细微之处不了解,导致开发过程中朦朦胧胧始终找不到感觉,所以还是建议看看这个部分。我看这部分很爽,因为大部分SQL语句都是学过的,同时又能了解里面细微的地...阅读全文
posted @ 2007-05-10 23:16 liuchen 阅读(317) 评论(0) 编辑