C#의 where 유형 제약 조건에 대한 자세한 그래픽 및 텍스트 소개

黄舟
풀어 주다: 2017-03-03 13:17:47
원래의
1346명이 탐색했습니다.

유형 매개변수 제약 조건(C# 프로그래밍 가이드)

Visual Studio 2005





다른 버전

일반 클래스를 정의할 때 다음을 수행할 수 있습니다. 클래스를 인스턴스화할 때 클라이언트 코드가 유형 매개변수에 사용할 수 있는 유형의 종류에 제한을 둡니다. 클라이언트 코드가 제약 조건에서 허용하지 않는 형식을 사용하여 클래스를 인스턴스화하려고 하면 컴파일 시간 오류가 발생합니다. 이러한 제한을 제약 조건이라고 합니다. 제약 조건은 where 컨텍스트 키워드를 사용하여 지정됩니다. 다음 표에는 6가지 유형의 제약 조건이 나열되어 있습니다.

제약 조건 설명

T : 구조

유형 매개변수는 값 유형이어야 합니다. Nullable을 제외한 모든 값 유형을 지정할 수 있습니다. 자세한 내용은 nullable 형식 사용(C# 프로그래밍 가이드).

T: 클래스

유형 매개변수는 클래스, 인터페이스, 대리자 또는 배열 유형을 포함한 참조 유형이어야 합니다.

T: new()

유형 매개변수에는 매개변수가 없는 공개 생성자가 있어야 합니다. 다른 제약 조건과 함께 사용하는 경우 new() 제약 조건을 마지막에 지정해야 합니다.

T: <기본 클래스 이름>

유형 매개변수는 지정된 기본 클래스이거나 다음에서 파생되어야 합니다. 지정된 기본 클래스입니다.

T: <인터페이스 이름>

유형 매개변수는 지정된 인터페이스이거나 지정된 인터페이스를 구현해야 합니다. 여러 인터페이스 제약 조건을 지정할 수 있습니다. 제약조건 인터페이스는 일반적일 수도 있습니다.

T: U

T에 제공된 유형 매개변수는 U에 제공된 매개변수이거나 제공된 U 매개변수에서 파생되어야 합니다. . 이를 Naked 형식 제약 조건이라고 합니다.


제약 조건을 사용하는 이유


일반 목록의 항목을 확인하여 유효한지 확인하거나 다른 항목과 비교하려는 경우 비교를 하려면 컴파일러는 호출해야 하는 연산자나 메서드가 클라이언트 코드에서 지정할 수 있는 모든 형식 매개 변수에 의해 지원된다는 보장을 제공해야 합니다. 이 보장은 일반 클래스 정의에 하나 이상의 제약 조건을 적용하여 얻을 수 있습니다. 예를 들어 기본 클래스 제약 조건은 이 유형의 개체 또는 이 유형에서 파생된 개체만 유형 매개 변수로 사용할 수 있음을 컴파일러에 알립니다. 컴파일러가 이러한 보장을 받으면 일반 클래스에서 해당 유형의 메서드 호출을 허용할 수 있습니다. 제약 조건은 where 컨텍스트 키워드를 사용하여 적용됩니다. 다음 코드 예제에서는 GenericList 클래스에 기본 클래스 제약 조건을 추가하는 방법을 보여줍니다(Generic 소개(C#) 프로그래밍 가이드)) 기능.

public class Employee
{
    private string name;
    private int id;


    public Employee(string s, int i)
    {
        name = s;
        id = i;
    }


    public string Name
    {
        get { return name; }
        set { name = value; }
    }


    public int ID
    {
        get { return id; }
        set { id = value; }
    }
}


public class GenericList<T> where T : Employee
{
    private class Node
    {
        private Node next;
        private T data;


        public Node(T t)
        {
            next = null;
            data = t;
        }


        public Node Next
        {
            get { return next; }
            set { next = value; }
        }


        public T Data
        {
            get { return data; }
            set { data = value; }
        }
    }


    private Node head;


    public GenericList() //constructor
    {
        head = null;
    }


    public void AddHead(T t)
    {
        Node n = new Node(t);
        n.Next = head;
        head = n;
    }


    public IEnumerator<T> GetEnumerator()
    {
        Node current = head;


        while (current != null)
        {
            yield return current.Data;
            current = current.Next;
        }
    }


    public T FindFirstOccurrence(string s)
    {
        Node current = head;
        T t = null;


        while (current != null)
        {
            //The constraint enables access to the Name property.
            if (current.Data.Name == s)
            {
                t = current.Data;
                break;
            }
            else
            {
                current = current.Next;
            }
        }
        return t;
    }
}
로그인 후 복사

제약 조건 유형 매개변수를 사용하면 제약 조건 유형과 해당 상속 계층 구조의 모든 유형에서 지원하는 허용되는 작업 및 메서드 호출 수를 늘릴 수 있습니다. 따라서 제네릭 클래스나 메서드를 설계할 때 제네릭 멤버에 대한 단순 할당 이외의 작업을 수행하거나 System.Object에서 지원하지 않는 메서드를 호출하려면 유형 매개 변수 Apply가 필요합니다. 제약.

where T : class 제약 조건을 적용할 때 ==!= 연산자를 사용하지 않는 것이 좋습니다. 유형 매개변수입니다. 왜냐하면 이러한 연산자는 참조 ID만 테스트하고 값 동일성은 테스트하지 않기 때문입니다. 매개변수로 사용되는 유형에 이러한 연산자가 오버로드된 경우에도 마찬가지입니다. 아래 코드는 String 클래스가 == 연산자를 오버로드하더라도 이를 보여줍니다. 거짓.

C#

public static void OpTest<T>(T s, T t) where T : class
{
    System.Console.WriteLine(s == t);
}
static void Main()
{
    string s1 = "foo";
    System.Text.StringBuilder sb = new System.Text.StringBuilder("foo");
    string s2 = sb.ToString();
    OpTest<string>(s1, s2);
}
로그인 후 복사

그 이유는 컴파일러가 컴파일 타임에만 T가 참조 유형이라는 것을 알기 때문에 모든 참조 유형에 유효한 기본 연산자를 사용해야 하기 때문입니다. 값 동일성을 테스트해야 하는 경우 권장되는 접근 방식은 where T : IComparable 제약 조건을 적용하고 일반 클래스를 구성하는 데 사용되는 모든 클래스에 인터페이스를 구현하는 것입니다.

결합되지 않은 유형 매개변수



결합되지 않은 유형 매개변수(예: 공개 클래스 SampleClass< The T in T> ;{})은 바인딩되지 않은 유형 매개변수라고 합니다. 바인딩되지 않은 유형 매개변수에는 다음 규칙이 있습니다.

  • !=== 연산자와 함께 사용할 수 없습니다. 유형 매개변수 다음 연산자가 지원됩니다.

  • System.Object 사이에서 앞뒤로 변환되거나 모든 인터페이스 유형으로 명시적으로 변환될 수 있습니다.

  • 은 null과 비교할 수 있습니다. 바인딩되지 않은 매개변수를 null 과 비교할 때 유형 매개변수가 값 유형인 경우 비교는 항상 false를 반환합니다.

Naked 유형 제약 조건



제약 조건으로 사용되는 일반 유형 매개변수를 Naked 유형 제약 조건이라고 합니다. . Naked 유형 제약 조건은 다음 예제와 같이 자체 유형 매개 변수가 있는 멤버 함수가 해당 매개 변수를 포함 유형의 유형 매개 변수로 제한해야 할 때 유용합니다.

C#

class List<T>
{
    void Add<U>(List<U> items) where U : T {/*...*/}
}
로그인 후 복사

위의 예에서 TAdd 메서드 컨텍스트에서는 기본 유형 제약 조건이고 List 컨텍스트에서는 바인딩되지 않은 유형 제약 조건입니다. 클래스 특정 유형 매개변수.

Naked 유형 제약 조건은 일반 클래스 정의에도 사용할 수 있습니다. Naked 유형 제약 조건은 다른 유형 매개 변수와 함께 꺾쇠 괄호 안에 선언되어야 합니다.

C#
//naked type constraint
public class SampleClass<T, U, V> where T : V { }
로그인 후 복사

일반 클래스의 Naked 유형 제약 조건은 컴파일러가 특정 Naked 유형 제약 조건만 가정하기 때문에 사용이 매우 제한적입니다. System.Object 에서 파생된 것 외에는 어떠한 가정도 이루어지지 않습니다. 두 유형 매개변수 간의 상속 관계를 적용하려는 경우 제네릭 클래스에 Naked 유형 제약 조건을 사용할 수 있습니다.

위 내용은 C#의 where type 제약사항에 대한 그래픽과 텍스트 내용입니다. 더 많은 관련 내용은 PHP 중국어 홈페이지(www.php.cn)를 참고해주세요!


관련 라벨:
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿