2012-07-03 21 views
25

Tại sao điều này làm việcKhi nào và ở đâu để sử dụng GetType() hoặc typeof()?

if (mycontrol.GetType() == typeof(TextBox)) 
{} 

và điều này không?

Type tp = typeof(mycontrol); 

Nhưng công trình này

Type tp = mycontrol.GetType(); 

Bản thân tôi sử dụng is điều hành để kiểm tra loại nhưng hiểu biết của tôi thất bại khi tôi sử dụng typeof()GetType()

ở đâu và khi nào sử dụng GetType() hoặc typeof()?

+1

ý của bạn là gì bởi tác phẩm này ... và điều này không ...? –

+1

@ anouar204: Hãy thử chúng trong IDE của bạn. –

+4

Không 'biên dịch' sẽ phù hợp hơn là không hoạt động ' –

Trả lời

61

typeof là nhà điều hành để có loại được biết tại thời gian biên dịch (hoặc ít nhất là thông số loại chung). Toán hạng của typeof luôn là tên của thông số loại hoặc loại - không bao giờ một biểu thức có giá trị (ví dụ: biến). Xem C# language specification để biết thêm chi tiết.

GetType() là phương thức bạn gọi trên các đối tượng riêng lẻ, để có được loại đối tượng thời gian thực hiện.

Lưu ý rằng trừ khi bạn chỉ muốn chính xác các trường hợp TextBox (chứ không phải là trường hợp của lớp con), bạn thường muốn sử dụng:

if (myControl is TextBox) 
{ 
    // Whatever 
} 

Hoặc

TextBox tb = myControl as TextBox; 
if (tb != null) 
{ 
    // Use tb 
} 
+2

Dòng của bạn' 'Toán hạng của typeof luôn là tên của một kiểu hoặc kiểu tham số - không bao giờ một biểu thức có giá trị (ví dụ: biến)'' là câu trả lời hoàn hảo cho câu hỏi của tôi. Cảm ơn vì đã giúp tôi ra ngoài. –

5

Bạn có thể tìm thấy nó dễ dàng hơn để sử dụng số is keyword:

if (mycontrol is TextBox) 
+0

Câu trả lời này tôi đang tìm kiếm trên SO và tôi biết điều này. –

+5

@NikhilAgrawal: Nếu bạn đã biết điều gì đó là một câu trả lời rõ ràng cho câu hỏi của bạn, bạn nên nói như vậy trong câu hỏi để tránh lãng phí thời gian của mọi người. Vui lòng đọc http://tinyurl.com/so-hints –

+1

@JonSkeet: Tôi sử dụng là từ khóa nhưng bị phân vân trong typeof() và GetType() –

7

typeOf là từ khóa C# được sử dụng khi bạn có tên của lớp. Nó được tính toán tại thời gian biên dịch và do đó không thể được sử dụng trên một cá thể, được tạo ra trong thời gian chạy. GetType là một phương thức của lớp đối tượng có thể được sử dụng trên một cá thể.

23

typeof được áp dụng cho tên loại đã biết lúc biên dịch. Nó cũng có thể được áp dụng cho các tham số kiểu chung. GetType được áp dụng cho một đối tượng trong thời gian chạy. Trong cả hai trường hợp, kết quả là một đối tượng thuộc loại System.Type chứa siêu thông tin trên một loại.

Nếu bạn có

string s = "hello"; 

Hai dòng này có giá trị

Type t1 = typeof(string); 
Type t2 = s.GetType(); 

Và sự so sánh này sản lượng true

t1 == t2     ==> true 

Nhưng

object obj = "hello"; 

Hai dòng này có giá trị

Type t1 = typeof(object); 
Type t2 = obj.GetType(); // ==> string! 

Và sự so sánh này sản lượng false

t1 == t2     ==> false 

tức, loại thời gian biên dịch (loại tĩnh) của biến obj là không giống như thời gian chạy loại (loại động) của đối tượng được tham chiếu bởi obj. (Ở đây "năng động" không có gì để làm với các từ khóa dynamic!)


loại Testing

Tuy nhiên, nếu bạn chỉ muốn biết liệu mycontrol là một TextBox sau đó bạn chỉ có thể kiểm tra

if (mycontrol is TextBox) 

Lưu ý rằng điều này không hoàn toàn tương đương với

if (mycontrol.GetType() == typeof(TextBox))  

mycontrol có thể có loại có nguồn gốc từ TextBox. Trong trường hợp đó, so sánh đầu tiên mang lại true và số thứ hai false! Biến thể đầu tiên và dễ dàng hơn là OK trong hầu hết các trường hợp, vì điều khiển bắt nguồn từ TextBox thừa hưởng mọi thứ mà TextBox có, có thể thêm nhiều hơn cho nó và do đó gán tương thích với TextBox.

public class MySpecializedTextBox : TextBox 
{ 
} 

MySpecializedTextBox specialized = new MySpecializedTextBox(); 
if (specialized is TextBox)  ==> true 

if (specialized.GetType() == typeof(TextBox))  ==> false 

Đúc

Nếu bạn đã kiểm tra sau theo sau là một diễn viên và T là nullable ...

if (obj is T) { 
    T x = (T)obj; // The casting tests, whether obj is T again! 
    ... 
} 

... bạn có thể thay đổi nó. ..

T x = obj as T; 
if (x != null) { 
    ... 
} 

Kiểm tra xem một giá trị có thuộc loại đã cho và quá trình đúc (có liên quan đến thử nghiệm này một lần nữa) có thể tốn thời gian cho các chuỗi dài thừa kế hay không. Sử dụng toán tử as theo sau là một thử nghiệm cho null hoạt động hiệu quả hơn.

Bắt đầu với C# 7.0 bạn có thể đơn giản hóa mã bằng cách sử dụng mẫu phù hợp:

if (obj is T t) { 
    // t is a variable of type T 
    ... 
} 
Các vấn đề liên quan