博客

  • Lua程序设计(第二版)阅读笔记

     

    很有意思的是,下面的代码是有效地,我也是看了书才知道。代码后面可以跟着,也可以不跟分号。

     1: a = 5 b = 6

     2: c = 7; d = 8;

     3: print(a, b, c, d)

    Lua中,什么是字母依赖于locale的设置,也就是中文环境下,中文可以用作变量名(?这个需验证)

    Lua有大小写之分。

    常用的块注释方式是–[[然后以–]]结尾,这样如果想取消块注释,就把开头多加个-就行了。

    LUA_INIT内容为@文件名,解释器会先执行这个文件(?需验证)。

    Lua中的(以后省略)函数为第一类值,比如print = type; print(a); 这个是合法合理的,但是print就没有了,一般用于沙箱sandbox操作。

    条件判断只有两种情况为假,false以及nil。其余都为真。

    number是实数(通常下)。用双精度代表整数,只要这个数字不大于10的14次方就没问题(本书这里笔误为1014,shit,我对照了PIL第一版确认的)。重新编译数字类型可以方便用于其它平台luaconf.h。数字可以写作4.57e-3 0.3e12 5e+20这种科学计数法。

    Lua可以存储任意二进制字符到字符串类型中。5.1支持的长括号写法[===[匹配]===],只要等号数量移植。字符串与数字运算,数字会转成字符串,可以用tonumber把字符变成数字。

     1: local str = "5e+20"

     2: local num = tonumber(str)

     3: print(num)

    数字转成字符,可以用tostring或者让数字与空字符串连接。

    5.1的字符串支持#。

    local a = {}创建了一个table,并且让a引用这个table,通过a这个变量我们可以操作这个table,如果没有变量继续引用这个table(a = nil),Lua会负责回收内存销毁它。

    a["nameX“] = 5 等价于 a.nameX = 5,注意key里面的引号。local a = {}; a[x] = 5这个代码是不合法的。local a = {}; a["x"] = 5; print(a.x);这个会打印出5。

    长度操作#的常用做法,print(a[#a])打印最后一个(因为Lua的table索引从1开始),a[#a +1] = n常用与自增,a[#a] = nil删除最后一个。

    注意当table中有空洞(数字索引不连续,或者某个值为nil)的时候,#操作未必得到正确值。

    5.1新增%取模操作。a % b == a – floor(a / b) * b,结果符号永远与第二个参数相同。print(5 % -2)得到-1,print(-5 % 2)得到1。另外取模操作可以用于对实数取整数部分或者小数部分。x = math.pi; x – x % 0.01 是让x精确到小数点后2位。x % 1 取小数部分,x – x % 1 取到整数部分。

    table,userdata以及function,比较引用。

    and与or都是用短路求值。 x = x or v常用于默认值设置。

    Lua中的字符串是不可变值immutable value,两个字符串链接,会返会一个新的字符串。

    链表写法:

     1: list = nil

     2: for line in io.lines() do

     3: list = {next = list, value = line}

     4: end

    local a = { [-1] = 3, ["3"] = 5, ["n"] = "bbb"};

    print(a[-1]); print(a["3"]); print(a.n);比较有意思的是a["3"]没法写成a.3。

    a = {x = 0, y = 0} 相当于a = {["x"] = 0, ["y"] = 0}的语法特例。

    local a = { [-1] = 3; ["3"] = 5; ["n"] = "bbb"};这样写也是合法的,构造式可以用分号代替逗号。

    第四章

    x, y = y, x交互x与y的值。

    可以用do-end控制局部变量的范围。

    local print = print,相当于定义了一个局部变量print(函数),后面如果使用print,就是访问了这个局部变量。访问局部变量要比访问全局变量快。

    while x do .. end,当x为真值时进入while;repeat .. until x,当x为真值的时候结束循环。这点我弄混过。

  • 选书之美与购书之道

    什么什么之美与什么什么之道现在简直是有些烂大街了,
    就好像“寂寞”之于春晚,美和道这两个词能让计算机书商用上三四年没问题,
    比如《代码之美》与《代码之道》我都买了,可是都没看完,如果用豆瓣打分也就是三星,可以读读。我承认,这两本书买了有些后悔。

    好了,想说什么问题呢?怎么也要表达一些中心思想吧,
    没错,“选书跟买电脑一样,不要在刚出来的时候就买,至少等一两个月“
    这就是我的选书之美,美不美?

    比如《代码之美》这本书的内容简介(from china-pub):
    本书介绍了人类在一个奋斗领域中的创造性和灵活性:计算机系统的开发领域。在每章中的漂亮代码都是来自独特解决方案的发现,而这种发现是来源于作者超越既定边界的远见卓识,并且识别出被多数人忽视的需求以及找出令人叹为观止的问题解决方案。
    本书33章,有38位作者,每位作者贡献一章。每位作者都将自己心目中对于“美丽的代码”的认识浓缩在一章当中,张力十足。38位大牛,每个人对代码之美都有自己独特的认识,现在一览无余的放在一起,对于热爱程序的每个人都不啻一场盛宴。虽然本书的涉猎范围很广,但也只能代表一小部分在这个软件开发这个最令人兴奋领域所发生的事情。

    太牛逼了,简直是无以伦比的文案,可实质上,这本书就是一部散文集罢了。

    另外《代码之道》这本书,不知是不是我境界太低,读起来真是费劲啊,看了几张就丢一边了。如果你在书刚刚发布的几天购买,会发现星星的评分真是高,编辑、作者一个劲推荐,也有一些名牛人使劲推(我不认识这些名牛人,无法评价他们是不是真的看了),让你感觉不买就买不到了(新楼盘?)。过了几周,你会发现一些”不和谐“的声音慢慢出现了,这其实才是真正的读者开始慢慢浮现。我们排除敌对出版社的打击,里面还是有不少值得借鉴的意见和观点。

    OK,还有另外一半,就是购书之道。前面有同学在TL提问买什么书好,我的建议很简单,
    不要买带“美”和“道”的书,太玄了,编程就是编程,扯什么大道至简、负负得正的有什么意思?是不是联系上道家思想,编程就会变得清新空灵?(请去豆瓣搜“小清新”小组)

    好了,我瞎掰完了。

  • 一个有趣的代码问题

    OldNewThing发布了一篇很有意思的文章http://blogs.msdn.com/oldnewthing/archive/2010/01/20/9950638.aspx

    The wrong way to determine the size of a buffer

    A colleague of mine showed me some code from a back-end program on a web server. Fortunately, the company that wrote this is out of business. Or at least I hope they’re out of business!

    size = 16384;

    while (size && IsBadReadPtr(buffer, size))

    { size--; }

    高人就是高人,这个代码其实还是需要好好想一想才能明白为何有问题。

    IsBadReadPtr的意思是尝试去读一个不属于自己进程的内存地址,因为指针越界在大多数情况下都是代表错误发生。但是这个函数实际上并不是那么好用,具体原因可以看OldNewThing的这篇文章http://blogs.msdn.com/oldnewthing/archive/2006/09/27/773741.aspx 介绍的非常详细。

    回到这个问题上,在OldNewThing的文章中介绍的非常清楚“But guard page exceptions are raised only once.”,也就是说,IsBadReadPtr将只会有效一次(?need to double check),这个代码逻辑就是有问题的。

    再把其中包含的问题列一下,主要参考了文章后的留言。

    1)16384这个16K大小来的莫名其妙,当然不排除在某些特定软件设计中,最大就是这个大小。

    2)第二个问题,IsBadReadPtr并不是那么好用。

    3)这个计算得到的值未必正确。

    那么我们该如何获取buffer的大小呢?

    在c-faq中告诉我们,通常情况下是没有解决办法的,只能自己保存这个buffer大小。办法也很简单,我们需要申请的时候就把buffer大小记住,需要知道的时候,查找一下就知道了,或者是使用某种数据结构,把buffer的大小以及其他信息放在开头固定的一块大小就行了。

    如果是windows,那么有一些特定的办法。可以用_msize来获得malloc申请的buffer。

    allocated with LocalAlloc, use LocalSize. For HeapAlloc, use HeapSize. For GlobalAlloc, use GlobalSize,如果使用CoTaskMemalloc,可以先用CoGetMalloc拿到一个IMalloc接口,然后调用GetSize()

    这些函数到底好用不好用,还是得靠你自己多测试。最简单牢靠的办法还是自己保存这个size信息。

  • 吾家有女初长成

    上周末回到萌萌爷爷奶奶家,看到一件非常有意思的事情,一定要写写。

    话说萌萌到了4岁以后,自己的主意越来越多,穿什么衣服,戴什么发卡都要自己定,不好看的不穿。据她妈妈说,上次她去训练的时候,戴了一头的发卡,数数足足有13个,都是她自己别的。

    晚饭还是吃的涮羊肉,比较省事。吃完了以后,萌萌就开始嫌自己的辫子不好看,要重新扎。

    只见她小手把头发捋顺,挑起一缕头发,熟练地用皮筋把头发扎成一个小马尾,最后还把头发拽拽,让皮筋能扎到辫子根。oh my girl,你简直是太神奇了。(可惜没有带相机,没法拍视频)扎了几次,她还是感觉不太好看,于是让爷爷又给她扎成羊角辫。

    头发弄好以后,就大概折腾了半个多小时了,然后又去把自己的漂亮发卡都找出来。然后对着镜子一个个别在头上,来来回回的又是整了半个多小时,就是弄个头发就整了快一个小时,而且一点也不觉得烦。好不好看不论,这份爱臭美的个性到底像谁呢?难道是随她妈妈?

  • 如何给小孩挑选绘本图画书

    如果要挑书,douban算是一个不错的地方,尽管也有书托,相比dangdang或者卓越这些网站还是要客观不少,而且能发现不少有趣的东西。

    我在里面发现了一个绘本图画书的不错列表《美国凯迪克大奖》。

    美国凯迪克大奖(The Caldecott Medal)创自1938年,以英国杰出的童书插画家Randolph Caldecott为名设立。每年由美国图书馆协会从上一年美国出版的数万本童书中,选出一名首奖和三名杰作,并颁发奖章。凡是得奖作品,封面上都贴有 Caldecott先生的著名插画“骑马的约翰”奖牌贴纸,金色为首奖,银色为杰作。凯迪克大奖代表童书界的至高荣誉,可谓图画书的“奥斯卡”奖。

    凯迪克大奖可以在这里找到获奖名单,然后到dangdang或卓越上就可以找到相应的获奖书籍了。也可以从这个豆列直接选择。

    1985年的honor奖有Hansel and Gretel, illustrated by Paul O. Zelinsky; text: retold by Rika Lesser (Dodd),我们领着萌萌去看青少年宫过这个舞台剧,翻译成《亨特与格蕾特儿》,原来竟然是格林童话,我真是无知了。