2012-02-03 46 views
8

Nếu một vòng qua một XmlNodeList như thế nàyTại sao đối tượng loại suy luận var chứ không phải XmlNode trong vòng lặp XmlNodeList?

foreach (XmlNode foo in xmlNodeList) {string baa = foo.Attributes["baa"].Value;} 

mọi thứ hoạt động như mong đợi - foo rõ ràng là kiểu XmlNode và IDE VS.NET cho thấy phương pháp và các lĩnh vực.

Mặt khác

foreach (var foo in xmlNodeList) { string baa = foo.Attributes["baa"].Value; } 

không được biên dịch vì đây foo là loại đối tượng. Nhập loại công việc suy luận nhưng nhập đối tượng.

Rõ ràng, các yếu tố của XmlNodeList không của một loại được xác định, nhưng gán chúng cho XmlNode thay vì var làm điều gì đó ngầm (đúc hoặc unboxing).

Câu hỏi đầu tiên: cơ chế đằng sau điều gì?

Câu hỏi thứ hai (có liên quan): cách tìm loại mà người ta có thể sử dụng trong loại vòng lặp này? VS.NET IDE có giúp ích gì không?

+1

Bạn có thể muốn sử dụng các lớp trong không gian tên system.xml.linq khi chúng thực hiện các phiên bản chung IEnumerable trong số các phiên bản khác. Các var nên được suy ra một cách chính xác khi sử dụng các lớp này. YMMV –

+0

@Chris: Cảm ơn bạn đã gợi ý - Tôi sẽ kiểm tra. – Olaf

+0

+1, tôi sẽ hỏi cùng một câu hỏi :-) –

Trả lời

9

XmlNodeList chỉ thực hiện giao diện IEnumerable không chung chung và không giống như giao diện IEnumerable<XmlNode> với hình ảnh đại diện. Điều này ngăn cản việc gõ mạnh các phần tử của nó cho đến khi bạn đưa ra một cách thích hợp, do đó trình biên dịch không có sự lựa chọn nào khác ngoài việc ánh xạ khai báo kiểu ngầm tới object trong foreach của bạn.

Nếu bạn nhấn mạnh vào sử dụng từ khóa var, bạn có thể cast các yếu tố của xmlNodeList như vậy:

foreach (var foo in xmlNodeList.Cast<XmlNode>()) 
{ 
    string baa = foo.Attributes["baa"].Value; 
} 

Nhưng đó là xấu xí, và đòi hỏi nhiều tổ hợp phím anyway. Bạn cũng có thể khai báo một cách rõ ràng XmlNode foo và để foreach truyền nó cho bạn khi đang di chuyển.

+0

Cảm ơn rất nhiều, đã hiểu! Tôi không muốn xấu xí, nhưng như tôi đã viết trong bình luận của tôi với Jon câu hỏi đã phần nào là một phần thực tế: nếu Resharper cho tôi 'var', cách nhanh nhất để tìm loại thật là gì? – Olaf

+1

Như Daniel Hilgarth chỉ ra, cách dễ nhất để làm điều đó là nhìn vào tài liệu. – BoltClock

4

Như ghi chú BoltClock, XmlNodeList chỉ thực hiện IEnumerable.

Vòng lặp foreach tự động không casting cho bạn đằng sau hậu trường, vì vậy đây:

List<object> values = new List<object> { "x", "y", "z" }; 
foreach (string x in values) 
{ 
    ... 
} 

là hoàn toàn hợp pháp, và thực hiện một dàn diễn viên (mà có thể ném một ngoại lệ, tất nhiên) trên mỗi giá trị.

Nó không thực sự rõ ràng với tôi những gì bạn có nghĩa là bởi câu hỏi thứ hai của bạn - nhưng tôi chỉ khuyên bạn nên sử dụng rõ ràng XmlNode trong vòng lặp của bạn. Nếu bạn thực sự muốn sử dụng var, bạn có thể viết:

foreach (var foo in xmlNodeList.Cast<XmlNode>()) 

nhưng mà cảm thấy như overkill với tôi ...

+0

Cảm ơn, IEnumerable và IEnumerable giải thích! Với câu hỏi thứ hai của tôi, ý tôi là: trong trường hợp như thế này, cách nhanh nhất để tìm loại mục tôi cần là gì, trong trường hợp này là 'XmlNode'? Resharper cho tôi 'var', vì vậy tôi đã tự hỏi nếu VS.NET có nó ở đâu đó ẩn trong intelliSense của nó. – Olaf

+3

@Olaf: Không, không thể có bất kỳ Intellisense nào về điều này, bởi vì thông tin đơn giản là không có. Bạn cần phải biết những gì bạn đang làm - mà bạn nên anyway, tất nhiên :) –

+0

Đó là những gì tôi muốn biết (thông tin chỉ đơn giản là không có). Cảm ơn vì đã giúp tôi biết tôi đang làm gì! – Olaf

4

XmlNodeList đã được trong .NET Framework trước khi nó được hỗ trợ Generics. Do đó, nó chỉ thực hiện giao diện không chung chung IEnumerable và không thực hiện chung IEnumerable<T>.
Để biết loại nào có thể nằm trong danh sách này, bạn cần đọc tài liệu. Cách tốt nhất là indexer.

BTW: IDE chưa được gọi là VS.NET kể từ khi Visual Studio 2005 được phát hành :-) Nó được gọi là VS chỉ từ đó.

+0

+1 để giải thích lý do. Tôi không quen thuộc với các API XML trong .NET ... – BoltClock

+0

Cảm ơn, cũng cho gợi ý VS.NET (chúng tôi vẫn đang sử dụng nó trong nội bộ)! – Olaf

Các vấn đề liên quan