2017-05-20 24 views
4

표준 ML에서 간단한 이미지를 처리하는 라이브러리를 작성하고 있습니다. 각 픽셀의 색상으로 사용되는 다양한 유형을 지원해야합니다 (예 : bool, Word8.word 등SML은 서명이있는 abstype을 사용합니다.

abstype 'a image은 표현과는 별도로 정의 된 모든 공통 함수 ('a은 색상 표현)가 있지만 출력 형식이 다르므로 다른 구조를 갖고 싶습니다.

abstype을 구조 안에 "여는"방법이 있습니까? 난 단지 아주 추악한 방법으로이 작업을 얻을 수 있습니다 : 특히

abstype 'clr absimage = Image of {width : int, height : int, data : 'clr array array} 
with 
    fun createFunc (w, h) f = Image {width = w, height = h, data = ...} 
    fun createBlank (w, h) clr = createFunc (w, h) (fn _ => clr) 
    ... 
end 
signature IMAGE = sig 
    type colour 
    type image 
    val createFunc : (int * int) -> (int * int -> colour) -> image 
    val createBlank : (int * int) -> colour -> image 
    ... 
    val toBinPPM : image -> string -> unit 
end 
functor ImageFn(C : sig type colour end) = struct 
    open C 
    type image = colour absimage 
    val createFunc = createFunc 
    val createBlank = createBlank 
    ... 
end 
structure Image8 :> IMAGE = struct 
    structure T = ImageFn(struct type colour = Word8.word end) 
    open T 

    fun toBinPPM img filename = ... 
end 

는 펑터의 정의는 abstypewith ... end 부분에 정의 된 모든 기능에 대한 val name = name 같은 문을 작성해야합니다.

아니면 내 접근 방식이 완전히 잘못 되었습니까?

abstypesignature의 결합은 abstype에서 일반적인 방법으로 OOP의 추상 클래스를 다시 만들고 signature

P.S.를 사용하여 모든 구조에서 다른 방법의 구현을 필요로하는 나의 시도 왜 SML은 open (ImageFn(struct ... end)) 같은 문장을 허용하지 않고 위의 코드에서 임시 구조 ()를 사용합니까?

답변

5

오늘 SML에서 abstype을 사용할 이유가 없습니다. 사용 중지 된 것으로 간주합니다. 이것은 사전 모듈 시대의 잔재입니다. 구조, 서명 및 씰링 (:> 연산자) 유형의 생성자를 숨기는 것과 동일한 효과를 얻을 수 있지만보다 유연하고 일관된 방식으로 수행 할 수 있습니다. 또한 모듈과 잘 통합되지 않는 이유를 설명합니다. 모듈을 선행하고 본질적으로 모듈로 대체되었습니다. 당신의 구체적인 예에서

대신 abstype를 사용하는 간단과 같이, 서명 주석의 생성자를 직접 ImageFn 펑의 몸에 datatypeimage을 정의하고 숨기기 :

signature IMAGE = 
sig 
    type colour 
    type image 
    val createFunc : int * int -> (int * int -> colour) -> image 
    val createBlank : int * int -> colour -> image 
    ... 
end 

signature IMAGE8 = 
sig 
    include IMAGE 
    val toBinPPM : image -> string -> unit 
end 

functor ImageFn(type colour) :> IMAGE = 
struct 
    datatype image = Image of {width : int, height : int, data : colour array array} 
    fun createFunc (w, h) f = Image {width = w, height = h, data = ...} 
    fun createBlank (w, h) clr = createFunc (w, h) (fn _ => clr) 
    ... 
end 

structure Image8 :> IMAGE8 = 
struct 
    structure T = ImageFn(type colour = Word8.word) 
    open T 
    fun toBinPPM img filename = ... 
end 

편집 : 사실이 경우에 image을 데이터 유형으로 정의 할 필요조차 없습니다. 평범 유형은 단지뿐만 아니라 할 약간 간단한 코드를 만드는 것입니다 : 당신의 PS 질문에 관해서는

type image = {width : int, height : int, data : colour array array} 

: 그래, 나도 모른다. 특별한 이유는 없습니다. 일부 SML 사투리는이를 확장으로 구현합니다.

+0

고맙습니다. 나는 당신이 펑터와 함께':>'를 사용할 수 있다는 것을 깨닫지 못했습니다. 이미지를 데이터 유형으로 선언하는 것은 이전 구현에서 남은 것입니다. – zlotnleo