簡體   English   中英

在有條件的 Scheme (R5RS) 上應用操作

[英]Applying operations on Scheme (R5RS) with a condition

我正在嘗試創建一個 Scheme 程序(Language R5RS),它將操作應用於一組列表,具體取決於列表上的數字有多大。

所以函數看起來像

(apply-function f g)

條件是,如果 f(ab) 其中 a < 5,則應用操作 f(ab)。

但如果 a 等於或大於 5,則應用 g(ab)。 (第二次操作)

這聽起來令人困惑,但一個直觀的例子應該會澄清它:所以,一個例子是

((apply-function '* '+) '((2 3) (8 6)))

會返回:

'(6 14)

另一個例子是

((apply-function '* '+) '((5 7) (2 3) (3 3))

退貨

'(12 6 9)

我以前處理過 Scheme 上的操作,但條件部分讓我失望,我不知道從哪里開始。 任何幫助表示贊賞!

版本 1 :如果您使用過程+*而不是符號'+'*

#lang r5rs

(define apply-function
  (lambda (f g)
    (lambda (lop)
      (map (lambda (p)
             (if (< (car p) 5)
                  (f (car p) (cadr p))
                  (g (car p) (cadr p))))
           lop))))

(display ((apply-function * +) '((2 3) (8 6))))
(newline) 
(display ((apply-function * +) '((5 7) (2 3) (3 3))))

版本 2 :您可以制作一個關聯列表,將符號與過程匹配

#lang r5rs

(define proc-list `((* . ,*) (+ . ,+)))

(define (get-proc s)
  (let ((p (assq s proc-list)))
    (if p (cdr p) s)))


(define apply-function
  (lambda (f g)
    (lambda (lop)
      (map (lambda (p) 
             (if (< (car p) 5)
                 ((get-proc f) (car p) (cadr p))
                 ((get-proc g) (car p) (cadr p))))
           lop))))

(display ((apply-function '* '+) '((2 3) (8 6))))
(newline) 
(display ((apply-function '* '+) '((5 7) (2 3) (3 3))))

版本 3 :使用 eval

#lang r5rs

(define (my-eval e)
  (eval e (scheme-report-environment 5)))

(define apply-function
  (lambda (f g)
    (lambda (lop)
      (map (lambda (p) (if (< (car p) 5)
                           (my-eval (list f (car p) (cadr p)))
                           (my-eval (list g (car p) (cadr p)))))
           lop))))

(display ((apply-function '* '+) '((2 3) (8 6))))
(newline) 
(display ((apply-function '* '+) '((5 7) (2 3) (3 3))))

假設程序以*+給出。

然后對一個這樣的子列表的操作看起來像

(lambda (e) (if (< (car e) 5) 
                (* (car e) (cadr e))
                (+ (car e) (cadr e)))

抽象給定的程序:

(define (apply-once f g)
        (lambda (e)
              (if (< (car e) 5) 
                  (f (car e) (cadr e))
                  (g (car e) (cadr e)))))

現在您可以使用*+轉換列表:

(lambda (ls) (map (apply-once * +) ls))

並再次抽象程序:

(define (apply-function f g) 
        (lambda (ls) (map (apply-once f g) ls)))

如果您假設您不必在函數名稱和函數之間進行映射,那么一個明顯的定義是使用apply

(define (apply-function f g)
  (lambda (l)
    (map (lambda (e)
           (apply (if (< (car e) 5) f g) e))
         l)))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM