Lisp语言:散列表(hash table)

散列表,也就是hash-table,在编程过程中会经常使用到,它以“关键字--数值”这样的对应关系保存数据,适合用于保存那些需要通过关键字查找数值的数据。

这里不打算详细介绍散列表的原理,希望深入了解散列表的同学请参考其它相关资料,这里只是介绍如何在Lisp中使用散列表。

再说,这种涉及理论的高深话题也不是我这种半途出家的人能说明白的,就是叫我讲我也不一定讲的清楚。说来惭愧,在刚开始工作的第一年中,我几乎是在完全无知的状态下异常开心地使用着散列表,直到有一天抓住一个实习的计算机研究生,以“不耻上问”的态度死缠烂打才问明白。


在Lisp中创建散列表很简单,简单到不需要参数,直接调用make-hash-table就可以了,如以下样例:

(setf my-hash-t (make-hash-table))
以上代码通过(make-hash-table)创建了一个散列表,再将它赋予变量my-hash-t。


如果需要获取散列表中某一个关键字对应的数值,可以使用gethash函数,如以下代码可以获取散列表my-hash-t中关键字NB001对应的数值:

(gethash 'NB001 my-hash-t)
当然,如果只是创建了散列表,并没有添加元素,以上代码会返回NIL的。


为了给散列表添加元素,可以直接使用setf函数,第一个参数是gethash获得的关键字位置,第二个参数是希望添加的数值,如:


(setf (gethash 'NB002 my-hash-t) "Tom")
以上代码为散列表my-hash-t添加了一对元素,其关键字为NB002,数值为“Tom”


需要注意的是散列表中一个关键字只能对应一个数值,同一个关键字无法赋予两个不同的值。如下面的代码会将NB001的数值设置为“Jerry”。后面那句setf生效,这个和变量的赋值的类似的。

      (setf (gethash 'NB001 my-hash-t) "Mike")
      (setf (gethash 'NB001 my-hash-t) "Jerry")

最后是有关散列表的遍历,Lisp中的散列表可以通过maphash函数进行迭代,形式如下:

        (maphash #'(lambda (key value) 
                (format *query-io* "key: ~a  value: ~a  ~%" key value))
                my-hash-t)
以上代码使用了lambda定义了一个匿名函数,该函数接受key和value两个参数,函数中输出key和value的值。

maphash函数调用的形式是:(maphash 匿名函数 散列表), maphash函数会将散列表中的关键字和对应数值逐对提取出来,赋予“匿名函数”的两个参数,然后调用匿名函数。

有关lambda的使用我们后面再详细讨论,这里简单把它看作是一个匿名函数就可以了。

下面是Lisp中使用散列表的完整样例和对应执行截图:

(defun hash-test ()
        (setf my-hash-t (make-hash-table))
        (setf (gethash 'NB001 my-hash-t) "Mike")
        (setf (gethash 'NB002 my-hash-t) "Tom")
        (setf (gethash 'NB003 my-hash-t) "Rose")
        (format *query-io* "key: NB001 value: ~a ~%" (gethash 'NB001 my-hash-t))
        (setf (gethash 'NB001 my-hash-t) "Jerry")
        (format *query-io* "key: NB001 value: ~a ~%" (gethash 'NB001 my-hash-t))
        (format *query-io* "going to print all the elements~%")
        (maphash #'(lambda (key value) 
                (format *query-io* "key: ~a  value: ~a  ~%" key value))
                my-hash-t)

)



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值