负暄琐话

我的email: rot47('649@ 6(hF+`hd"w=92vhG{>}G3"@l M >:>6?4@56 \F')

囧囧ID:g9yuayon
[修改头像]
780538次访问,排名36好友9人,关注者11
g9yuayon的文章
原创 239 篇
翻译 4 篇
转载 48 篇
评论 790 篇
g9的公告
最近评论
alextooter:ff可是用的完全的自己内存管理。。

最近ff3非常好,值得试试看。
fferror:无比期待g9老大的model checking续集。
sprhawk:哈哈,太强了,最近刚听说有Erlang,了解一下。
看一下历史,比看语法有意思得多嘿嘿
lordchl:后面提示下不动点好了,跳得太大
lbaby:Do you mind if I jot down some notes on your chests ??


猛到无以复加
订阅我的博客
XML聚合  FeedSky
订阅到鲜果
订阅到Google
订阅到抓虾
订阅到BlogLines
订阅到Yahoo
订阅到GouGou
订阅到飞鸽
订阅到Rojo
订阅到newsgator
订阅到netvibes
文章分类
收藏
    相册
    旅游
    计算机科学
    Lambda the Ultimate
    软件开发
    Reddit编程专栏(RSS)
    正在读的书
    存档

    转载 漂亮代码

    新一篇: 代码工养成计划之选择作坊篇

    从 Joe Marshall论证编程是艺术的文章上看到的。编程到底是不是艺术已经快变成继编程语言和Emacs vs Vi之后另一Flame War话题。有兴趣的可以去看reddit的讨论。有意思的是一段漂亮的代码,实现SICP上一坨练习题1.3:

    实现一个带三个参数的函数。这个函数返回三个参数中最大的两个参数的平方和。

    题目用来训练学生对条件分支的理解。常规的解法是(迎合一下各位老大,改成C了):

    int sum_square_largest(int x, int y, int z){
        
    if(y > x && z > x){
            
    return y * y + z * z;
        }

        
    if(x > y && z > y){
            
    return x * x + z * z;
        }

        
    if(x > z && y > z){
            
    return x * x + y * y;
        }
    }

    但Joe老大给出了一个非常漂亮的解法。简洁直观,巧妙地利用递归大幅简化判断。

    int sum_square_largest(int x, int y, int z){
        
    if (x <= y && x <= z){
            
    return y * y + z * z;
        }

        
    return sum_square_largest(y, z, x); 
    }

    这段代码符合Joe对判断一件作品是否是艺术的四个标准:

    • 这段代码非人不能写出,富于想象力。
    • 这段代码除了实现既定功能外,具有高度的表现力。
    • 这段代码很美。
    • 这段代码传递的美感和思想超越了它自身。

    Joe Garvin给出了另外一个解法,不过没有Marshall的直观漂亮:

    int sum_square_largest(int x, int y, int z){
        
    if(x <= z) return sum_square_largest(z, y, x);
        
    if(y <= z) return sum_square_largest(x, z, y); 

        
    return x * x + y * y;
    }

     

    坚持要上Scheme的老大们,这里是原文里的代码:

    (define (sum-square-largest x y z)
      (cond ((and (> y x) (> z x)) ;; y and z are largest
             (+ (* y y) (* z z)))
            ((and (> x y) (> z y)) ;; x and z are largest
             (+ (* x x) (* z z)))
            ((and (> x z) (> y z)) ;; x and y are largest
             (+ (* x x) (* y y)))))
    (define (sum-square-largest x y z)
      (cond ((and (< x y) (< x z)) ;; x is smallest
             (+ (* y y) (* z z)))
            (else (sum-square-largest y z x))))
    (define (sls x y z) 
       (cond ((> z x) (sls z y x)) 
             ((> z y) (sls x z y)) 
             (else (+ (* x x) (* y y)))))

    发表于 @ 2007年05月16日 13:33:00|评论(loading...)|编辑

    旧一篇: Prolog小程序

    评论

    #pongba 发表于2007-05-16 14:41:44  IP: 222.94.3.*
    果然漂亮,靠。你说银与银之间怎么就这么大差距呢?!
    2007-05-17 10:16:15作者回复
    是啊,都是妈生的
    #dennis 发表于2007-05-17 14:00:57  IP: 220.162.145.*
    相当相当具有美感,牛人就是牛人
    #Track 发表于2007-05-17 17:14:30  IP: 59.64.187.*
    关键是利用了轮换对称性,将相同的代码提取出来了
    #googol 发表于2007-05-19 10:41:52  IP: 221.222.218.*
    C里可以写成这样:
    int func(int a, int b, int c)
    {
    int t;
    while ( (a>=b) || (a>=c) )
    t=a, a=b, b=c, c=t;
    return b*b + c*c;
    }

    可惜,int t看上去不那么的艺术,而且,希望我没有记错逗号表达式的求值顺序……
    2007-05-19 12:29:28作者回复
    哈哈,这难道就是传说中的人肉尾递归优化?
    #googol 发表于2007-05-19 10:42:36  IP: 221.222.218.*
    居然缩进被取消了,这就不那么的艺术了……

    幸亏不是python的代码。
    #googol 发表于2007-05-19 23:47:05  IP: 221.222.218.*
    用C写,还是遵循C的哲学更好些:)
    #metacpp 发表于2007-05-23 21:51:59  IP: 202.95.81.*
    to googol:
    你的代码有问题, 如果 a = b = c, 你的程序就死循环了.
    #hayate 发表于2007-05-24 14:20:57  IP: 222.20.92.*
    人肉尾递归优化......
    还真的是呢....哈哈
    #lgn21st 发表于2007-10-16 20:30:40  IP: 121.76.201.*
    还是用scheme写,如何写成想joe那样,按照条件递归调用自身的方式?我不知道scheme有没有类似return的表达式?
    #lgn21st 发表于2007-10-16 22:19:54  IP: 58.247.211.*
    自己尝试一下,这样写得到的结果一样:
    (define (sls x y z)
    (if (and (<= x y) (<= x z))
    (+ (* y y) (* z z))
    (sls y z x)
    )
    )
    #lgn21st 发表于2007-10-16 22:22:44  IP: 58.247.211.*
    自己尝试一下,这样写得到的结果一样:
    (define (sls x y z)
    (if (and (<= x y) (<= x z))
    (+ (* y y) (* z z))
    (sls y z x)
    )
    )
    #eag0628 发表于2007-12-19 22:57:20  IP: 10.167.141.*
    int sum_square_largest(int x, int y, int z)...{
    if(x <= z) return sum_square_largest(z, y, x);
    if(y <= z) return sum_square_largest(x, z, y);

    return x * x + y * y;
    }

    (define (sls x y z) (cond ((> z x) (sls z y x)) ((> z y) (sls x z y)) (else (+ (* x x) (* y y)))))

    lz笔误吧,c代码中<=要改成 < 吧
    发表评论  


    当前用户设置只有注册用户才能发表评论。如果你没有登录,请点击登录
    Csdn Blog version 3.1a
    Copyright © g9