Microsoft MVP성태의 닷넷 이야기
글쓴 사람
정성태 (techsharer at outlook.com)
홈페이지
첨부 파일
 
(연관된 글이 2개 있습니다.)

Visual Studio 2019 Preview 4/RC - C# 8.0 Missing compiler required member 'System.Range..ctor'

현재 2019 (Preview 3은 괜찮고) Preview 4와 RC 버전에서 Range를 사용하면 다음과 같은 컴파일 오류가 발생합니다.

Program.cs(21,33,21,38): error CS0656: Missing compiler required member 'System.Range..ctor'

이 문제가 roslyn 이슈에도 올라와 있는데요.

CS0656: Missing compiler required member (.Net Core 3.0 Preview 2, Visual Studio 2019 Preview)  #2364 
; https://github.com/dotnet/core/issues/2364

문제의 원인은 Preview4/RC에 들어가 있는 C# 8.0 컴파일러가 System.Range의 생성자를 접근하도록 바뀌었는데 역시 Preview 버전의 .NET Core 3.0에 포함된 System.Runtime.System.Range 타입에는 없기 때문입니다. (아마도 C# 8.0 컴파일러 개발자들은 이미 업데이트된 .NET Core 3.0 preview 버전을 사용하고 있어서 에러가 없었을 것입니다.)

이 문제는 다음번 .NET Core 3.0 preview가 나오면 자연스럽게 해결되겠지만 그전까지는 지난 글의 방법에 따라,

C# 8.0의 Index/Range 연산자를 .NET Framework에서 사용하는 방법 및 비동기 스트림의 컴파일 방법
; https://www.sysnet.pe.kr/2/0/11835

다음과 같이 변경된 ranges.cs 파일을 추가해 빌드하는 식으로 우회할 수 있습니다. (2개의 변경 사항이 있습니다.)

namespace System
{
    public readonly struct Index
    {
        private readonly int _value;

        public int Value => _value < 0 ? ~_value : _value;
        public bool FromEnd => _value < 0;
        public bool IsFromEnd => _value < 0;

        public Index(int value, bool fromEnd)
        {
            if (value < 0) throw new ArgumentException("Index must not be negative.", nameof(value));

            _value = fromEnd ? ~value : value;
        }

        public static implicit operator Index(int value)
            => new Index(value, fromEnd: false);

        public int GetOffset(int length)
        {
            int num = this._value;
            if (this.IsFromEnd)
            {
                num = (int) (num + (length + 1));
            }
            return num;
        }
    }

    public readonly struct Range
    {
        public Index Start { get; }
        public Index End { get; }

        public Range(Index start, Index end)
        {
            this.Start = start;
            this.End = end;
        }

        public static Range Create(Index start, Index end) => new Range(start, end);
        public static Range FromStart(Index start) => new Range(start, new Index(0, fromEnd: true));
        public static Range ToEnd(Index end) => new Range(new Index(0, fromEnd: false), end);
        public static Range All() => new Range(new Index(0, fromEnd: false), new Index(0, fromEnd: true));
    }

    static class Extensions
    {
        public static int get_IndexerExtension(this int[] array, Index index) =>
            index.FromEnd ? array[array.Length - index.Value] : array[index.Value];

        public static int get_IndexerExtension(this Span<int> span, Index index) =>
            index.FromEnd ? span[span.Length - index.Value] : span[index.Value];

        public static char get_IndexerExtension(this string s, Index index) =>
            index.FromEnd ? s[s.Length - index.Value] : s[index.Value];

        public static Span<int> get_IndexerExtension(this int[] array, Range range) =>
            array.Slice(range);

        public static Span<int> get_IndexerExtension(this Span<int> span, Range range) =>
            span.Slice(range);

        public static string get_IndexerExtension(this string s, Range range) =>
            s.Substring(range);

        public static Span<T> Slice<T>(this T[] array, Range range)
            => array.AsSpan().Slice(range);

        public static Span<T> Slice<T>(this Span<T> span, Range range)
        {
            var (start, length) = GetStartAndLength(range, span.Length);
            return span.Slice(start, length);
        }

        public static string Substring(this string s, Range range)
        {
            var (start, length) = GetStartAndLength(range, s.Length);
            return s.Substring(start, length);
        }

        private static (int start, int length) GetStartAndLength(Range range, int entityLength)
        {
            var start = range.Start.FromEnd ? entityLength - range.Start.Value : range.Start.Value;
            var end = range.End.FromEnd ? entityLength - range.End.Value : range.End.Value;
            var length = end - start;

            return (start, length);
        }
    }
}

참고로 .NET Core 3.0 프로젝트에서는 위와 같은 소스 코드를 함께 포함하면 타입 충돌 경고가 뜨는데 일단은 무시하면 됩니다.




[이 글에 대해서 여러분들과 의견을 공유하고 싶습니다. 틀리거나 미흡한 부분 또는 의문 사항이 있으시면 언제든 댓글 남겨주십시오.]

[연관 글]






[최초 등록일: ]
[최종 수정일: 7/12/2021]

Creative Commons License
이 저작물은 크리에이티브 커먼즈 코리아 저작자표시-비영리-변경금지 2.0 대한민국 라이센스에 따라 이용하실 수 있습니다.
by SeongTae Jeong, mailto:techsharer at outlook.com

비밀번호

댓글 작성자
 



2019-03-07 09시13분
2019-03-06일부터 배포되는 SDK 3.0.100-preview3-010431 버전을 설치하면 "Missing compiler required member 'System.Range..ctor'" 오류가 없어집니다.
정성태

[1]  2  3  4  5  6  7  8  9  10  11  12  13  14  15  ...
NoWriterDateCnt.TitleFile(s)
14025정성태10/14/2025648Linux: 126. eBPF (bpf2go) - tcp_sendmsg 예제
14024정성태10/14/2025647오류 유형: 984. Whisper.net - System.Exception: 'Cannot dispose while processing, please use DisposeAsync instead.'
14023정성태10/12/20251142닷넷: 2369. C# / Whisper 모델 - 동영상의 음성을 인식해 자동으로 SRT 자막 파일을 생성 [1]파일 다운로드1
14022정성태10/10/20251987닷넷: 2368. C# / NAudio - (AI 학습을 위해) 무음 구간을 반영한 오디오 파일 분할파일 다운로드1
14021정성태10/6/20252617닷넷: 2367. C# - Youtube 동영상 다운로드 (YoutubeExplode 패키지) [1]파일 다운로드1
14020정성태10/2/20252255Linux: 125. eBPF - __attribute__((preserve_access_index)) 활용 사례
14019정성태10/1/20252392Linux: 124. eBPF - __sk_buff / sk_buff 구조체
14018정성태9/30/20251745닷넷: 2366. C# - UIAutomationClient를 이용해 시스템 트레이의 아이콘을 열거하는 방법파일 다운로드1
14017정성태9/29/20252217Linux: 123. eBPF (bpf2go) - BPF_PROG_TYPE_SOCKET_FILTER 예제 - SEC("socket")
14016정성태9/28/20252485Linux: 122. eBPF - __attribute__((preserve_access_index)) 사용법
14015정성태9/22/20251941닷넷: 2365. C# - FFMpegCore를 이용한 MP4 동영상으로부터 MP3 음원 추출 예제파일 다운로드1
14014정성태9/17/20251919닷넷: 2364. C# - stun.l.google.com을 사용해 공용 IP 주소와 포트를 알아내는 방법파일 다운로드1
14013정성태9/14/20252579닷넷: 2363. C# - Whisper.NET Library를 이용해 음성을 텍스트로 변환 및 번역하는 예제파일 다운로드1
14012정성태9/9/20252830닷넷: 2362. C# - Windows.Media.Ocr: 윈도우 운영체제에 포함된 OCR(Optical Character Recognition)파일 다운로드1
14011정성태9/7/20253451닷넷: 2361. C# - Linux 환경의 readlink 호출
14010정성태9/1/20253281오류 유형: 983. apt update 시 "The repository 'http://deb.debian.org/debian buster Release' does not have a Release file." 오류
14009정성태8/28/20253730닷넷: 2360. C# 14 - (11) Expression Tree에 선택적 인수와 명명된 인수 허용파일 다운로드1
14008정성태8/26/20254299닷넷: 2359. C# 14 - (10) 복합 대입 연산자의 오버로드 지원파일 다운로드1
14007정성태8/25/20254706닷넷: 2358. C# - 현재 빌드에 적용 중인 컴파일러 버전 확인 방법 (#error version)
14006정성태8/23/20255014Linux: 121. Linux - snap 패키지 관리자로 설치한 소프트웨어의 디렉터리 접근 제한
14005정성태8/21/20253981오류 유형: 982. sudo: unable to load /usr/libexec/sudo/sudoers.so: libssl.so.3: cannot open shared object file: No such file or directory
14004정성태8/21/20254573오류 유형: 981. dotnet 실행 시 No usable version of the libssl was found
14003정성태8/21/20254843닷넷: 2357. C# 14 - (9) 새로운 지시자 추가 (Ignored directives)
14002정성태8/20/20254986오류 유형: 980. C# - appsettings.json 파일의 설정값이 적용 안 된다면?
14001정성태8/19/20259763닷넷: 2356. .NET SDK 10 - 단일 소스 코드 파일을 빌드/실행하는 기능을 "dotnet" 명령어에 추가 [1]
[1]  2  3  4  5  6  7  8  9  10  11  12  13  14  15  ...