跳至内容

Scheme 编程/抽象与数据

来自维基教科书,开放书籍,开放世界

复数介绍

[编辑 | 编辑源代码]

为了展示如何构建数据抽象,我们将逐步创建一个复数包。复数包含两个部分,实部和虚部。它们通常以两种方式之一表示,直角坐标形式

和极坐标形式

现在,我们可以对复数执行所有常见的算术运算,加法、减法、乘法和除法。它们有简单的公式;

加法

减法

乘法

除法

请注意,乘法和除法最好用极坐标形式表示,而加法和减法最好用直角坐标形式表示。这就提出了一个有趣的问题:如何最好地计算这些?我们是否使用一种内部表示?如果是,我们选择哪一种?有很多问题需要解决。这些可以通过尝试实现一种新的数据类型来解决:复数类型。

创建我们的通用“类型”变量

[编辑 | 编辑源代码]

首先,我们将创建一个通用“类型”变量

(define typed-variable
  (lambda (type value)
    (cons 'Typed (list type value))
  )
)

现在我们需要一种方法来判断给定变量是否具有类型

(define typed?
  (lambda (var)
    (and (list? var) (= 'Typed (car var)))
  )
)

现在,我们已经引入了两个重要的概念,“谓词”和“构造函数”。第一个是用于判断某些数据是否具有正确形式的结构,第二个是用于构建我们数据结构的程序。

我们必须有一种方法来提取我们的数据(在本例中,是类型)从这种结构中,一种“选择”它的方法

(define type-of
  (lambda (var)
    (if (typed? var)
      (car (cdr var)
    )
  )
)

创建我们的复数数据类型

[编辑 | 编辑源代码]

构建我们的构造函数

[编辑 | 编辑源代码]

使用此类型的值,我们可以继续为我们的复数形成更详细的数据结构

(define complex-rect
  (lambda (a b)
    (typed-variable 'Rect-Complex (list a b))
  )
)

现在让我们继续,并创建一个complex-polar

(define complex-polar
  (lambda (r thet)
    (typed-variable 'Polar-Complex (list r thet))
  )
)
(define complex
  (lambda (type first-var second-var)
    (if (equal? 'type Polar)
        (cons (complex-polar first-var second-var) 
              (complex-rect (sqrt (+ (expt first-var 2) 
                                     (expt second-var 2)
                                  )
                            ) 
                            0
              )
        )  ;; Change second half to be the calculated values.
        (cons (complex-polar 0 0) (complex-rect first-var second-var))
    )
  )
)

构建我们的谓词

[编辑 | 编辑源代码]

我们拥有了构造函数,现在我们需要谓词

(define is-complex?
  (lambda (var)
    (and (typed? (car var)) 
         (or (= 'Rect-Complex (type-of (car var))) 
             (= 'Polar-Complex (type-of (car var)))
         )
    )
  )
)


现在我们可以根据这些程序定义算术运算。

华夏公益教科书