2016-11-03 6 views
4

먼저 질문에 불분명 한 경우 사과 드리겠습니다. 나는 아직 스칼라 용어를 사용하지 않았기 때문에 아마도 용어를 모으고있을 것이다. 나는 나의 예가 더 분명 할 것이라고 생각한다.None-type 제약 조건으로 특성을 어떻게 전문화 할 수 있습니까?

그래프의 기본 정점 - 목록 부모 및 하위 목록을 가질 수있는 모든 개체를 설명하는 특성 Hierarchical을 만들려고합니다. 더 구체적으로

:

  • 1) Hierarchical 또는 부모가있을 수도 있고 없을 수도 있습니다.

  • 2) 만약 그렇다면, 부모는 Hierarchical입니다.

  • 3) HierarchicalHierarchical도 아이들을해야합니다.

여기 내 일반적인 특성이다 :

/* 
    Hierarchical takes two type parameters: Parent and Child. 
    These should be Hierarchicals with parameters Parent and Child as well. 
*/ 
trait Hierarchical[Parent <: Hierarchical[Parent, Child], 
        Child <: Hierarchical[Parent, Child]] { 

    // parents must be passed by constructor lest they are treated as None. 
    // (Requirement 1, 2) 
    val parents: Option[List[Hierarchical[Parent, Child]]] = None 

    // children can be added, so mutability needed (Requirement 3) 
    var children: List[Hierarchical[Parent, Child]] = List() 

    def addChild(child: Child) = children ++= List(child) 
} 

이에 대한 전문성은 부모가 존재하지 않습니다, 유형이 모두 지정해서는 안 "루트"정점이다 - thusly 히 , None입니다. 여기에 Hierarchical 특성을 전문으로 내 시도이다 :

/* 
    A RootHierarchical has no parents. It does, however, have 
    children whose parents are RootHierarchicals and whose children 
    are Child. 
    A parent can be none (Requirement 1) 
*/ 
trait RootHierarchical[Child <: Hierarchical[RootHierarchical, Child]] 
    extends Hierarchical[None.type, Child] { 
    override val parents = None 
} 

인 IntelliJ이 행복입니다,하지만 내가 쓴 테스트가 컴파일되지 않습니다

import org.scalatest.FlatSpec 

class TestHierarchy extends FlatSpec { 

    "A Hierarchical object" should "be constructable" in { 

    /* 
    Create a dummy 
    */ 
    class DummyHierarchical(override val parents: List[DummyParentHierarchical]) 
     extends Hierarchical[DummyParentHierarchical, DummyHierarchical] 

    class DummyParentHierarchical extends RootHierarchical[DummyHierarchical] 

    val dummyParent = new DummyParentHierarchical 
    val dummyChild = new DummyHierarchical(List(dummyParent)) 
    dummyParent.addChild(dummyChild) 

    assert(dummyParent.parents.isEmpty) 
    assert(dummyParent.children.nonEmpty) 
    } 
} 

을 오류가 여기에 있습니다 :

Error:(14, 11) type arguments [None.type,Child] do not conform to trait Hierarchical's type parameter bounds [Parent <: Hierarchical[Parent,Child],Child <: Hierarchical[Parent,Child]] 
    extends Hierarchical[None.type, Child] { 

내 질문은 이것입니다 : 어떻게이 전문화를 만들 수 있습니까? 나는 None.typeHierarchical 유형이 아니라는 것을 알고 있습니다. 어떻게 이것을 전문화 할 수 있습니까?

+0

:

// T is the type of children -- they should be Hierarchicals. trait Hierarchical[T <: Hierarchical[T]] { // The parents will be a list of some arbitrary Hierarchical val parents: List[Hierarchical[_]] = Nil var children: List[Hierarchical[T]] = List() } // Nodes that aren't root nodes will have parents specified by ctor class NonRootNode(override val parents: List[Hierarchical[_]]) extends Hierarchical[NonRootNode] {} // Roots will have no way to update their parents. class Root extends Hierarchical[NonRootNode] { final override val parents = Nil } 

여기 몇 가지 검사와 작은 드라이버입니다 :

여기 내 구현입니다. 'trait Hierarchical [Parent <: Option [Hierarchical [부모, 자식]], 자식 <: 계층 적 [Option [부모], 자식]] 이 항목은 부모 형식으로 매개 변수화되어 있습니다. 이 인스턴스와 동일한 부모 및 자식 유형과 부모 옵션 (옵션)으로 매개 변수화 된 자식 유형 및이 매개 변수의 자체 유형 (이 옵션은 자식의 부모가 옵션의 옵션 임)으로이 특성의 옵션 학부모의 –

+0

픽스 포인트 유형 (https://www.youtube.com/watch?v=7xSfLPD6tiQ)으로 순수 기능 데이터베이스 프로그래밍에 관한 Rob Norris의 강연을보실 것을 적극 권장합니다.이 이야기는 Doobie를 예로 들었지만 실제 재귀 적 데이터 구조에 적용됩니다. –

+0

@AngeloGenovese 비디오 주셔서 감사합니다. 매우 흥미 롭습니다. 유형에 크게 의존하는 범주 이론을 활용하기 때문에 사용할 수 있는지 확신 할 수 없습니다. 나는 특성에 의존하고있다. 즉, 부모와 자식은 모두 '계층 적'을 구현하는 한 다른 유형이 될 수 있습니다. – erip

답변

1

브레인 스토밍을 한 후에 부모 유형을 지정할 필요가 없음을 알았습니다. 임의의 계층 적 유형 일 수 있으며 기본값은 Nil입니다. 나는이 문제는 특성의 당신의 정의부터 생각 Ideone it