2013-03-27 2 views
4

x86 용 DMD 2.062를 사용하고 있습니다.Object.Error : std.algorithm.cartesianProduct의 결과를 인쇄 할 때 액세스 위반이 발생했습니다.

module test;  

private enum test1 
{ 
    one, 
    two, 
    three, 
} 

private enum test2 
{ 
    one, 
    two, 
    three, 
} 

auto ct = cartesianProduct([EnumMembers!test1], [EnumMembers!test2]); 

unittest 
{ 
    import std.stdio; 
    foreach (n, m; ct) 
    { 
     writeln(n, " ", m); 
    } 
} 

이 프로그램은 인쇄합니다 :

one one 
two one 
three one 

그런 다음 액세스 위반 오류가 발생합니다. cartesianProduct를 잘못 사용하고 있습니까? 아니면이 함수의 버그입니까?

답변

6

두 비트의 작은 비트입니다. 여기서 문제는 ct이 컴파일 타임에 계산되도록 시도되고 런타임에 사용되는 결과 범위를 생성한다는 것입니다. 나는 CTFE 나 CartesianProduct가 그런 시나리오를 기대하지 않는다고 생각하며 잘못된 메모리 사용과 관련된 나쁜 일이 일어난다. 난 중 하나가 작동해야하거나, 컴파일 타임 오류가 있어야한다고 생각하지만, 당신을 도울 것이고 버그 추적기에 속한다.

여기서 중요한 점은 ct 초기화를 단위 테스트 본문 또는 static this() 모듈 생성자로 이동하면 모든 것이 작동한다는 것입니다. 여러분이 놓치고있는 것처럼 보이는 점은 D가 프로그램 시작시 전역 변수 초기화를 지원하지 않는다는 것입니다. 전역에 할당 된 값은 컴파일 타임에 항상 평가됩니다. 종종 "그냥 작동합니다", 컴파일 타임 오류가 발생하며 (초기화가 CTFE 가능하지 않은 경우)이 경우 이상한 동작이 발생합니다.

현재 D 프런트 엔드 구현에 매우 까다로운 컴파일 시간 데이터 및 런타임 배열이나 연관 배열과 같은 복잡한 유형에 대한 데이터를 사이에 일반적으로

auto Test1Members = [ EnumMembers!test1 ]; 
auto Test2Members = [ EnumMembers!test2 ]; 
alias CT = typeof(cartesianProduct(Test1Members, Test2Members)); 
CT ct; 

static this() 
{ 
    ct = cartesianProduct(Test1Members, Test2Members); 
} 

, 상호 연결되어 많이 필요 할 수 있습니다 당신은이 코드 주의.

+0

http://d.puremagic.com/issues/show_bug.cgi?id=9822를 제출하면 개발자의 의견을 볼 수 있습니다. –

+0

@AlexanderMalakhov 감사합니다. –

관련 문제