2013-03-08 3 views
0

D에 classe 참조 시스템이 있습니까? 현재 내가 할D에 메타 클래스 또는 클래스 참조가 있습니까?

// ideally 
void AddNew(*TBaseClass APtr, /*?class_ref_type?*/ AClassType) 
{ 
    *APtr = new AClassType; 
} 

: 나는 (단지 Object처럼하지만 클래스 이름을 사용하지 않고) 공장을 위해 사용되는 델파이

TMyClassRef = class of TMyClass; 

이 동등한를 찾아 더 정확합니다 이 :

void AddNew(*TBaseClass APtr) 
{ 
    *APtr = new typeof(*APtr); 
} 

그러나 문제는 typeof() 반환 항상 TBaseClass 결코 TBaseClass의 하위 클래스 (하위 제공자 라이선스 계약 매개 변수로 전달됩니다. 클래스 참조가 델파이에서 사용되지만 D 언어는 그런 시스템을 갖고 있지 않은 경우가 분명합니다.

+0

아마도 도움이 될 것입니다. http://forum.dlang.org/thread/CAEyOLyDZaL2[email protected] – sigod

+0

컴파일 타임 매개 변수를 살펴보십시오. http://ddili.org/ders/d.en/templates.html – sigod

답변

2

은 어쩌면 내가 완전히 델파이의 아이디어를 누락, 그러나 이것은 템플릿을 위해 무엇을 것 같다 :

import std.stdio; 

class Parent { 
    string inherited() { 
     return "Hello from parent"; 
    } 

    override string toString() { 
     return "Hello from parent"; 
    } 
} 

class Child : Parent { 
    override string toString() { 
     return "Hello from child"; 
    } 
} 

void add(C, P)(P* ptr) { 
    *ptr = new C; 
} 

void main() { 
    Parent t; 
    writeln(t); // prints null 

    add!Child(&t); 
    writeln(t); // prints Hello from child 
    writeln(t.inherited()); // prints Hello from parent 
} 

당신의 인스턴스화 된 객체 대신 인스턴스화 할 당신이 유형 전달이 방법 그 타입. add()에서 C가 P의 하위가 아니면 컴파일 오류가 발생합니다.

편집 :

추가로 더 구체적으로 할 경우, 당신은이 작업을 수행 할 수 있습니다 :

void add(T : Parent)(Parent* ptr) { 
    *ptr = new T; 
} 

물건 좋네요하려면 더 관용적 수하는 out 매개 변수를 사용 :

void add(T : Parent)(out Parent ptr) { 
    ptr = new T; 
} 
void main() { 
    Parent p; 
    add!Child(p); 
} 
+0

Thx이 작업을 완벽하게 수행합니다. 이제 형식을 전달할 수 있습니다 whashed 및 공장 오른쪽 하위 형식을 만듭니다. – babu67

2

D에는 델파이 개념을 이해하는 한 델파이 방식에서는 클래스 참조가 없습니다. 객체 생성에 대한 런타임 결정을 내리려면 object.TypeInfo이 도움이됩니다.

당신은 typeid 구조를 통해 변수에 대한 TypeInfo를 검색 할 수 있습니다

import std.stdio; 

class Base 
{ 
    void f() 
    { 
     writeln("Base"); 
    } 
} 

class Descendant : Base 
{ 
    override void f() 
    { 
     writeln("Descendant"); 
    } 
} 

Base makeNew(Base other) 
{ 
    // cast is needed because create() returns plain Object 
    // we can be sure it is Base at least, though, because it was crated from Base 
    return cast(Base)typeid(other).create(); 
} 

void main() 
{ 
    Descendant source = new Descendant; 
    Base target = makeNew(source); 
    // prints "Descendant" 
    target.f(); 
} 

당신이 원하는 것과 비슷한이 코드 샘플인가?

D에는 일반적으로 런타임 작업과 컴파일 타임 액션이 매우 구분됩니다. typeof은 컴파일 타임에 작동하므로 계층의 경우 "실제"클래스 유형을 쿼리 할 수 ​​없습니다.

+0

코드 샘플도 비슷하지만 유효한 소스가 없기 때문에 제 경우에는 위와 같이 작동하지 않습니다. ..so ̉'typid (other)'는 AV를 유발합니다. 이것은 정확하게 클래스 참조가 도움이 될 것입니다 ... 형식 ID를 쿼리하는 다른 방법은 없으므로 런타임에, unitialized Object에서? – babu67

+0

그러나 객체가 초기화되지 않은 경우 런타임 유형을 알 수 없습니다 (기본 클래스 또는 하위 클래스 중 하나 일 수 있습니다). 객체를 아직 초기화하지 않으려면 '대상 정보 '다른 변수에서. 당신이 분명하지 않다면, 나는 약간의 코드를 게시 할 것이다. – yaz

+0

물론 컴파일 타임에 필요한 모든 정보를 사용할 수 있다면 템플릿을 사용할 수 있습니다. – yaz