Coding Memo

[C#] [해결] 사용자 dll에서 클래스 및 인터페이스 상속 시 에러 (CS0115, CS0534) 본문

메모

[C#] [해결] 사용자 dll에서 클래스 및 인터페이스 상속 시 에러 (CS0115, CS0534)

minttea25 2023. 8. 14. 20:28

문제

 

서버 코어를 만들고 빌드를 하여 dll 파일을 생성했다.

 

이 dll 파일을 Unity에서 그대로 사용하려고 넣어서 컴파일을 했다. 물론 문제가 없었다.

 

하지만, 서버 코어에 있는 추상 클래스를 상속받아서 클래스를 하나 작성하려고 했는데 참 보기에는 어이없는 에러가 나타났다.

 

CS0115: 재정의할 적절한 메서드를 찾을 수 없습니다.

CS0534: 상속된 추상 맴버를 구현하지 않습니다.

CS0115는 override 키워드가 적절하게 사용되지 않았을 때 (재정의할 메서드를 찾지 못했을 때) 나타나는 오류이고, CS0534는 추상 클래스를 상속 받았을 때, 반드시 구현해야 하는 맴버를 구현하지 않았을 때 나타나는 에러이다.

그래서 내가 구현을 안했을까? 난 구현했는데 계속 에러가 나타난다!

 

좀 더 간단하게 코드를 구성하고 테스트를 해보기 위해 다음과 같은 클래스를 만들고 dll로 빌드했다.

public abstract class A
{
    public abstract void Method(ReadOnlySpan<byte> span);
    public abstract void Method(Span<byte> span);
    public abstract void Method(ArraySegment<byte> segment);
    public abstract void Method(Memory<byte> memory);
}

 

그리고 이를 Unity로 넣고 코드를 작성해 보았다.

class C : A
{
    public override void Method(ReadOnlySpan<byte> span)
    {
    }

    public override void Method(Span<byte> span)
    {
    }

    public override void Method(ArraySegment<byte> segment)
    {
    }

    public override void Method(Memory<byte> memory)
    {
    }
}

 

하지만...

 

A는 public abstract void Method(ReadOnlySpan<byte> span)을 가지고 있는 추상 클래스이고 코어 라이브러이리의 dll에 포함되어 있다.

빨간 밑줄이 있는 부분이 각각 CS0115, CS0534에러가 나타나는 부분이다.

 

ReadOnlySpan, Span, Memory에 대해 왜 에러가 나타나는 것일까?

또 왜 ArraySegment에는 에러가 나지 않는 것일까?...


ReadOnlySpan, Span, Memory 등의 클래스나 구조체는 내가 코어 라이브러리를 만들 때 사용했던 Net에 포함되어 있는 버전과 Unity에서 사용하고 있는 버전이 달랐다.

라이브러리는 NetCore 3.1 버전으로 컴파일되어 빌드되었고, Unity는 현재 Net Standard 2.1를 사용중이었다.

 

실제로 라이브러리 프로젝트에 가서 ReadOnlySpan 타입에 F12를 눌러 메타데이터를 볼 수 있는데, 이 코드와 동일하게 Unity에서 ReadOnlySpan의 메타데이터 코드를 비교하면 차이가 나는 것을 알 수 있다.

또한 파일 첫번째 줄에 나타나 있는 어셈블리 참조위치도 다른 것을 알 수 있다.

 

라이브러리의 ReadOnlySpan<T>
Unity의 ReadOnlySpan<T>

 

처음에는 참조하는 어셈블리가 달라서 그런가? 라고 생각했는데 ArraySegment의 경우에는 에러가 나타나지 않은 걸로 보아 이 때문은 아닌것 같다. (ArraySegment도 참조하고 있는 어셈블리가 서로 달랐지만, overiding이 제대로 되었다.)

 

문제가 있는 타입은 Span, ReadOnlySpan, ArraySegment, Memory 인데 왜 이러는지 아직 그 이유를 모르겠다...ㅠㅠ

 

 

Unity는 Api Compatibility Level은 Net Standard 2.1이어서 Span, Memory를 다 지원한다. (2.0 부터 지원)


가장 유력한 이유는 Unity의 Span, ReadOnlySpan, ArraySegment가 런타임 환경에서 Net Framework와 다르게 동작하기 때문에 Unity에서 완전히 다르게 취급하는 것 같다.

 

일단 ArraySegment만을 이용해서 고치자...

...

 


해결했다.

 

예상했던 대로 .NET 버전 차이 때문이었다.

문제는 Visual Studio에서는 위의 2가지 에러만 표시되고 이 내용이 표시되지 않는다!!!!!!!!

라이브러리의 Span, ReadOnlySpan, ArraySegment의 런타임 버전이 Unity에서의 Span, ReadOnlySpan, ArraySegment 런타임 버전보다 높아서 생긴문제이다.

 

결국 2가지 버전에 대한 타입을 다르게 인식하고 "문자적"으로는 구현했음에도 불구하고 IDE는 인식하지 못하여 CS0115, CS0534 에러가 나타났던 것이었다.

라이브러리에서 구현되어 있는 Runtime 버전의 Span을 구현해야하지만, Unity에서 코드를 짤 때 사용하는 Span은 라이브러리에서 구현되어 있는 Runtime 버전의 Span보다 하위 버전을 사용하고 있기 때문에 호환이 안되어서 그런 것!

 

CS0115: 재정의할 적절한 메서드를 찾을 수 없습니다.

CS0534: 상속된 추상 맴버를 구현하지 않습니다.

 

다시 글로 정리해야 겠다.

'메모' 카테고리의 다른 글

Listen Backlog에 대한 Connection 주의사항  (1) 2024.02.02
Unity 간단한 메모  (0) 2024.01.22
게임 튜토리얼 구현 방식에 대해  (1) 2022.11.25
각종 정보 링크 모음 (private)  (0) 2022.08.19
Nodejs mysql, mysql2  (0) 2022.08.09