开发者

How do I get the functions put and get in SICP, Scheme, Exercise 2.78 and on

开发者 https://www.devze.com 2023-02-20 19:34 出处:网络
I am trying to do exercise 2.78 in 开发者_运维知识库SICP, but the functions put and get are unknown. I have tried multiple languages, like pretty big, racket, r5rs, mit-scheme, mzscheme, etc. I even d

I am trying to do exercise 2.78 in 开发者_运维知识库SICP, but the functions put and get are unknown. I have tried multiple languages, like pretty big, racket, r5rs, mit-scheme, mzscheme, etc. I even downloaded the SICP support (http://www.neilvandyke.org/sicp-plt/), to no avail. How can I get these functions to work?


Yes, I found SICP a little annoying sometimes because of stuff like this. Functions that are assumed to exist but don't actually exist make it harder to try to the examples. I wrote my own (get) and (put) like so (this was in GNU guile):

(define global-array '())

(define (make-entry k v) (list k v))
(define (key entry) (car entry))
(define (value entry) (cadr entry))

(define (put op type item)
  (define (put-helper k array)
    (cond ((null? array) (list(make-entry k item)))
          ((equal? (key (car array)) k) array)
          (else (cons (car array) (put-helper k (cdr array))))))
  (set! global-array (put-helper (list op type) global-array)))

(define (get op type)
  (define (get-helper k array)
    (cond ((null? array) #f)
          ((equal? (key (car array)) k) (value (car array)))
          (else (get-helper k (cdr array)))))
  (get-helper (list op type) global-array))

Probably a naive implementation from the perspective of later in the book, but fairly simple and worked fine.


There is an implementation of put and get by Eli Bendersky. These functions could be implemented using builtin Basic Hash Table Operations. Here is my modified version of Eli's code to work properly with MIT-Scheme Release 9.1.1.

(define *op-table* (make-hash-table))

(define (put op type proc)
  (hash-table/put! *op-table* (list op type) proc))

(define (get op type)
  (hash-table/get *op-table* (list op type) '()))

UPDATED:

I've found bug with above mentioned code after time. Empty lists are interpreted as true in conditional clauses by Scheme, so correct get implementation should be following:

(define (get op type)
  (hash-table/get *op-table* (list op type) #f))


If you use Racket programming language please use these:

(define *op-table* (make-hash))

(define (put op type proc)
  (hash-set! *op-table* (list op type) proc))

(define (get op type)
  (hash-ref *op-table* (list op type) '()))


In subsection Creating local tables of 3.3.3 Representing Tables, there is an implementation.


mit-scheme has a built-in global table that you can use.

http://www.gnu.org/software/mit-scheme/documentation/mit-scheme-ref/The-Association-Table.html

simply define get and put to:

(define get 2d-get)
(define put 2d-put!)
0

精彩评论

暂无评论...
验证码 换一张
取 消