免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: __BlueGuy__
打印 上一主题 下一主题

[C] Lua 造成的代码冗余太严重了, 这个现状怎么改善? [复制链接]

论坛徽章:
2
青铜圣斗士
日期:2015-11-26 06:15:59数据库技术版块每日发帖之星
日期:2016-07-24 06:20:00
111 [报告]
发表于 2012-11-19 14:03 |只看该作者
starwing83 发表于 2012-11-19 06:19
就这么简单。


用lua的是不是都喜欢说这句话?还包括云风。

99楼最后一段的回复呢?

实际做事的时候你真的愿意不断的在状态码和异常之间转换(不管是显式的还是包装在函数里的)?就为了证明lua有异常处理?
还是只是为了在这里给我证明lua有异常处理,实际开发时就甩得远远的?

论坛徽章:
2
青铜圣斗士
日期:2015-11-26 06:15:59数据库技术版块每日发帖之星
日期:2016-07-24 06:20:00
112 [报告]
发表于 2012-11-19 14:07 |只看该作者
回复 106# starwing83

已经比从debug里掏要好了吧。。。

论坛徽章:
2
青铜圣斗士
日期:2015-11-26 06:15:59数据库技术版块每日发帖之星
日期:2016-07-24 06:20:00
113 [报告]
发表于 2012-11-19 14:11 |只看该作者
回复 107# starwing83

哦,此事果然有蹊跷啊大人。。。
很久没用python了嘛。。。 都10年的陈年旧事了。。。

那叫 __FILE__ ? 还脏不脏。。。 有没有亲切感。。。 ruby就支持这东西。。。

论坛徽章:
3
寅虎
日期:2013-11-27 07:53:29申猴
日期:2014-09-12 09:24:152015年迎新春徽章
日期:2015-03-04 09:48:31
114 [报告]
发表于 2012-11-20 09:23 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
5
丑牛
日期:2014-01-21 08:26:26卯兔
日期:2014-03-11 06:37:43天秤座
日期:2014-03-25 08:52:52寅虎
日期:2014-04-19 11:39:48午马
日期:2014-08-06 03:56:58
115 [报告]
发表于 2012-11-20 09:56 |只看该作者
归根结底还是设计问题。
freshxman 该用户已被删除
116 [报告]
发表于 2012-11-20 10:09 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
3
巳蛇
日期:2013-10-03 10:41:48申猴
日期:2014-07-29 16:12:04天蝎座
日期:2014-08-21 09:24:52
117 [报告]
发表于 2012-11-20 10:34 |只看该作者
你们说了那么多,好多都不懂啊..

反正有那么一点我已经稍微有了点体会..
repl(read eval print loop)这个东西确实很舒服的.

在slime里面, 在racket里面,写出来函数立马在repl里面测试,好了之后继续,我想说的是这个过程确实很连贯..
比在c里面写lib,编辑,调用它,编译,运行,看结果要快的多.

论坛徽章:
1
程序设计版块每日发帖之星
日期:2015-10-21 06:20:00
118 [报告]
发表于 2012-11-20 11:35 |只看该作者
很典型的两位程序员。 看到第八页看不动了。 回个贴,再继续看。

论坛徽章:
5
狮子座
日期:2013-08-20 10:12:24午马
日期:2013-11-23 18:04:102015年辞旧岁徽章
日期:2015-03-03 16:54:152015亚冠之德黑兰石油
日期:2015-06-29 18:11:1115-16赛季CBA联赛之新疆
日期:2024-02-21 10:00:53
119 [报告]
发表于 2012-11-21 01:19 |只看该作者
本帖最后由 starwing83 于 2012-11-21 01:23 编辑

回复 110# OwnWaterloo


    真是太荒谬了!!!

我想问你,GCC实现异常的两大方法中,Windows实现C++异常的标准方法中,都有一个叫做SJLJ!请问这是什么?

凭什么non-local jump就不是异常?凭什么异常对象提取/异常扔出转换就不是异常了?

看看纯正的异常吧(C++):

1.
int f() {
   MyClass c;
   do_something();
}

2.
int f() {
  try {
    do_something();
  } catch (Exception& e) {
     ...
  }
}

思考题:
1. 在1中,这个函数本身,是不是无论如何编译都是可以在异常中,让c析构的?(答案明显是不是:至少要给出在unwind的时候,需要做的事情。GCC的做法是unwind_handler。总而言之必须额外的信息以及额外的代码组织,换言之,普通的,不考虑异常的编译无法达到支持异常的目标,即:只有特殊支持异常编译过的代码,才能够支持异常。)

2. 在2中,请问catch块是不是状态码/异常转换?请问catch和Lua的pcall究竟有什么区别?

编辑一下:这里做个说明,免得你又不知道我在说什么。
思考题1的意思是:要实现异常,就必须做出某种特殊处理。首先Lua的实现方式不是异常到状态码转换。Lua扔的自始自终就是完全合法的object。Lua只是缺乏类似Python的with,C++的析构这样的机制。但是用newtry完全可以弥补这个问题。因此Lua的异常和Python/C++的全无区别(请告诉我有什么事情是C++做得到而Lua做不到的)。

思考题2的意思是:即使在C++里面,要实现catch,实质上也意味着某种转换,意味着隐式的unwind和显式的代码执行行为的转换。这里的unwind就是longjmp,而代码执行就是普通的某快代码的执行。和Lua相比。C++只是多了一种内置语法而已


你太狭隘了知不知道?

请回答下面的问题:

1. 是不是只有语言明确说明内置异常,才是真的支持异常?
2. 是不是无论我将sjlj如何包装,结果都不是异常?
3. 如果第二问是否,那么newtry+protect包装+Lua的基础异常设施(pcall,error)是不是异常?


我真的很不明白,如果我不告诉你Lua的pcall如何实现,我只告诉你:

1. newtry(function()
    -- code1
end)(function()
   -- code2
end)
等价
try {
  -- code2
} catch(...) {
  -- code1
}


2. error { object }
等价:
throw object

3. if protect(function()
   -- code 1
end)(...) then
   -- code 2
end
等价:
try {
  -- code 1
} finially {
  -- code 2
}

请问,这到底是不是异常?请告诉我还缺什么?


您继续扯蛋。

论坛徽章:
2
青铜圣斗士
日期:2015-11-26 06:15:59数据库技术版块每日发帖之星
日期:2016-07-24 06:20:00
120 [报告]
发表于 2012-12-04 00:01 |只看该作者
回复 119# starwing83

1. 无论如何编译是指什么? 是指有没有/EHsc? 在这个层面上"异常需要特殊支持"是对的。
那Lua有这种特殊支持吗? 比如Lua的error会顾及某个registered handler吗?
至于那两个f函数又是什么意思? 有try的那个才会被析构,没有try的就不会析构? C++不需要我来科普吧?


2. 状态码和异常之间不停的转换我是在说protect/newtry, 而不是pcall/error。
protect是不是从转换到状态码? newtry是不是从状态码转换到异常? 我说错了没?
而pcall/error又没有特殊支持, 我说错了没?

注意: 我说的protect/newtry是那个wiki上的版本。 我不知道你说的是哪个版本。
这个疑问前面就有了, 这里又出现了。
按wiki上的版本, 你最后那堆代码是不等价的。


3. 至于"什么是C++做得到而C做不到"

3.1 什么是C做不到而C++,Lua做得到?
3.2 什么是asm做不到而C做得到?

3.3

  1. struct data {
  2.       T x;
  3.       U y;
  4. };

  5. class inner {
  6. static void* f(void* p) {
  7.       data arg = *static_cast<data*>(p);
  8.       delete static_cast<data*>(p);
  9.       // use arg.x and arg.y
  10. }
  11. };

  12. data* arg = new data;
  13. arg->x = ...;
  14. arg->y = ...;
  15. pthread_create(... &inner::f, arg , ... );
复制代码
这叫不叫closure?


3.4
http://www.opensource.apple.com/ ... bsd/libkern/crc32.c

将上面的实现改为:

  1. static uint32_t crc32_tab[] = {
  2. #include "crc32_tab"
  3. };

  4. uint32_t
  5. crc32(uint32_t crc, const void *buf, size_t size)
  6. {
  7.         const uint8_t *p;

  8.         p = buf;
  9.         crc = crc ^ ~0U;

  10.         while (size--)
  11.                 crc = crc32_tab[(crc ^ *p++) & 0xFF] ^ (crc >> 8);

  12.         return crc ^ ~0U;
  13. }
复制代码
然后按注释里的方法实现一个crc32_tab.c输出那个表。
最后makefile里这么写:

  1. crc32.c : crc32_tab
  2. crc32_tab : crc32_tab.c
  3.       tcc -run $< > $@
复制代码
这叫不叫meta programming?

3.5
http://www.schemers.org/Document ... -H-9.html#%_sec_6.4

  1. (define make-promise
  2.   (lambda (proc)
  3.     (let ((result-ready? #f)
  4.           (result #f))
  5.       (lambda ()
  6.         (if result-ready?
  7.             result
  8.             (let ((x (proc)))
  9.               (if result-ready?
  10.                   result
  11.                   (begin (set! result-ready? #t)
  12.                          (set! result x)
  13.                          result))))))))
复制代码
这叫不叫lazy evaluation?

3.more...


4. 我是不是太狭隘?
嗯,我就是狭隘地认为3里面提到的都不算。
哪怕就是有一点点细微的区别 —— 是否内置、 语法是否简练、从源代码到执行中原本的步骤里是否不需要再额外添加新的步骤... —— 就会在开发时有所考虑与权衡。
3里面提到的都不是"被优先考虑"的方案。

再重复一下我提到的(不仅是这楼,还有clojure shebang那楼):潜力、代价、实践折中。
"scheme有实现所有语言特性的潜力"于是总可以先用它实现一个包含需要特性的语言,然后再开发?
真有这样搞的? 不是toy program? 不是coding for fun? 而是真的投入实践中这么用的? 比例有多大?

实际开发的时候, 你会不会权衡"实现语言"的代价与收益 vs "在现有语言里用work around"的代价与收益?
所谓的"scheme -> interpreter for L -> development on L" 除了装装逼, 骗骗涉世未深的小朋友, 还有什么意义?

5. Lua是否支持异常

如果只是"Lua是否能实现", 你赢了。 而且你早就赢了,从1-2年前在qq上的讨论我就不是和你在争这个。
我想讨论的是"在实践中"Lua是否可以有效的使用异常处理?

前面还有一个问题你没回答我:
OwnWaterloo 发表于 2012-11-19 00:07
总之,用error的优势在哪里?
到底有多少人会去主动用error的? 不是因为底层的库用了non local jump所以他们也被迫用? 而是他们自己觉得应该用error? 这样的库被lua社区接受的又有多少?
多少人是因为lua的一些内建函数用error,所以他们不得不pcall? 如果lua内建函数都改为status code,他们会就开心得不得了?

如果只讨论潜力,现在听得到的语言没几个不是图灵完备的,潜力都一样。
哪又是什么导致这些语言有一样的潜力, 但就是各有不同? 因为在不同语言里做不同相同的事代价不同。
如果某种编程方式代价过高 —— 比如java8之前连function literal都没有 —— 怎么玩高阶函数相关的东西? C++没有lambda之前, algorithm也基本是个废物。
而那种模棱两可的, 说高不高说低不低的, 就不会被广泛应用。 比如lua的异常处理, scheme的先构建编译器再编程。 你能给我数据说明这两者的比例真的不是一些geek在玩, 而是真的有不少的人在这么用?


比如就以你github里的lua代码为样本如何? —— 我只看过你让我看过的那些, 我可没有提前去看里面到底有多少用了的, 多少没有用。
或者你给个合理的样本? 总不能专门找用了的, 然后给我说Lua都是这么干的?

如果样本合理, 而且确实有一半以上, 那我以后再也不说"Lua不支持异常处理"了, 行么?
一半的比例算不算高? 我只知道在python和java里肯定不止一半。
至于C++, 其他人我不知道, 我不用的最主要理由是它没法跨模块边界。 而Lua又不需要与不同的实现做斗争。

否则你在这里给我反复说"Lua支持异常处理"又有什么意义?
OwnWaterloo 发表于 2012-11-19 14:03
还是只是为了在这里给我证明lua有异常处理,实际开发时就甩得远远的?

您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP