序对的一种过程性表示

来源:互联网 发布:网络销售员招聘信息 编辑:程序博客网 时间:2024/04/30 23:52

      考虑这样一个问题,设计一个数据结构,使其表示有理数。

      So easy!

     

typedef struct rat{    int num;    int den;}rat;

其中,num表示该有理数的分子,den表示该有理数的分母,而整个数据结构rat即可表示为有理数。如果要得到该有理数的分子,可用rat.num表示,而rat.den则表示分母。


那么,如果不用数据结构,完全用过程来表示这样的数据,可行吗?


“一般而言,我们总可以将数据定义为一组适当的选择函数和构造函数,以及为使这些过程成为一套合法表示,它们就必须满足的一组特定条件。”--------------SICP


我们定义这样三个过程, cons--------------将两个对象粘接到一起

                                             car----------------取出第一个对象

                                             cdr----------------取出第二个对象

其中,cons为构造函数,car和cdr为选择函数,而这些操作满足的条件就是:对任何对象x和y,如果z是(cons x y),则(car z)为x,(cdr z)为y。


这样,我们确实能够完全不用任何数据结构,只使用过程就可以实现序对。如下:

(define (cons x y)     (define (dispatch m)            (cond ((= m 0) x)                  ((= m 1) y)                  (else (error "Argument not 0 or 1 ---------CONS" m))))     dispatch)(define (car z) (z 0))(define (cdr z) (z 1))

上面是采用Lisp实现的,但是用C呢?


#include "stdio.h"typedef int (*pFunToDispatch)(int);pFunToDispatch pairConstructor(int x, int y){int dispatch(int m){return (m == 0) ? x : y;}return dispatch;}int firstOfPair(pFunToDispatch pair){return (*pair)(0);}int secondOfPair(pFunToDispatch pair){return (*pair)(1);}int main(int argc, char** argv){pFunToDispatch pair = pairConstructor(11, 12);int first = (*pair)(0);int second = (*pair)(1);printf("%d, %d\n", first, second);return 0;}

注意,由于ANSI C并不支持函数的嵌套定义,所以上述函数只适用在GCC中,而且可能会出问题,见http://tieba.baidu.com/p/1192690362?pn=1。


补充:

序对用过程性表示的另一种方法:

(define (cons x y)      (lambda (m) (m x y)))(define (car z)      (z (lambda (p q) p)))(define (cdr z)      (z (lambda (p q) q)))