ฉันจะรับชื่อประเภทของอาร์กิวเมนต์ประเภททั่วไปได้อย่างไร


108

ถ้าฉันมีลายเซ็นวิธีเช่น

public string myMethod<T>( ... )

ฉันจะรับชื่อประเภทที่กำหนดเป็นอาร์กิวเมนต์ประเภทภายในเมธอดได้อย่างไร อยากทำอะไรคล้าย ๆ กันtypeof(T).FullNameแต่ได้ผลจริง ...


10
typeof(T).FullName ควรทำงาน เกิดอะไรขึ้นแทน?
Nathan Taylor

ฉันได้รับข้อผิดพลาดของคอมไพเลอร์ในคำสั่งนั้น - แต่เห็นได้ชัดว่าเกิดจากสิ่งอื่นเพราะตอนนี้มันใช้งานได้ ขอบคุณ!
Tomas Aschan

คำตอบ:


172

รหัสของคุณควรใช้งานได้ typeof(T).FullNameถูกต้องสมบูรณ์ นี่คือโปรแกรมที่รวบรวมและทำงานได้อย่างสมบูรณ์:

using System;

class Program 
{
    public static string MyMethod<T>()
    {
        return typeof(T).FullName;
    }

    static void Main(string[] args)
    {
        Console.WriteLine(MyMethod<int>());

        Console.ReadKey();
    }

}

การรันภาพพิมพ์ด้านบน (ตามที่คาดไว้):

System.Int32

ตรวจสอบให้แน่ใจว่าได้ทดสอบด้วย MyMethod <int>> () และดูว่าคุณได้อะไร ... คุณต้องคำนึงถึงประเภทที่เป็นโมฆะหากคุณสนใจประเภทที่อยู่ภายใต้สถานการณ์นั้น
GR7

1
คุณหมายถึง " <int?>" ถ้าเป็นเช่นนั้นก็ใช้ได้ แต่คุณได้รับSystem.Nullable<int>(ในรูปแบบของชื่อเต็ม) ซึ่งเป็นสิ่งที่คุณคาดหวัง ...
Reed Copsey

แม้ว่าฉันจะมีวิธีแก้ปัญหาอยู่แล้ว (แม้ว่าจะไม่ได้ผลด้วยเหตุผลบางประการ ... ) ฉันจะให้คะแนนตัวแทนสำหรับการเขียนคำตอบที่ดีที่สุดโดยไกล =)
Tomas Aschan

1
สิ่งนี้ช่วยฉันได้ตั้งแต่ฉันคิดแบบนั้นnameof(T)และtypeof(T).Nameจะทำในสิ่งเดียวกัน ปรากฎว่าnameof(T)เพิ่งกลับTมา
dahvyd

7

typeof(T).Nameและtypeof(T).FullNameกำลังทำงานให้ฉัน ฉันได้รับประเภทที่ส่งผ่านเป็นอาร์กิวเมนต์


1
อา. หากประเภทที่คุณส่งผ่านเป็น Nullable เพื่อให้ได้ประเภทพื้นฐานคุณจะต้องใช้บางสิ่งเช่น typeof (T) .GetGenericArguments () [0]
GR7

หากต้องการตรวจสอบว่าประเภทเป็นโมฆะหรือไม่คุณจะต้องใช้ typeof (T) .IsGenericType และหากเป็นเช่นนั้นคุณจะใช้สิ่งต่อไปนี้เพื่อรับชื่อหรือ FUllName ((Type) typeof (T) .GetGenericArguments () [0 ]). ชื่อ
GR7

1

สมมติว่าคุณมี T อยู่บ้างก็ไม่ต่างจากประเภทอื่น ๆ

var t = new T();

var name = t.GetType().FullName;

3
คุณไม่จำเป็นต้องมีอินสแตนซ์ของ T .... typeof (T) ทำงานได้ดีโดยไม่มีอินสแตนซ์ ... ของคุณจะให้พฤติกรรมที่แตกต่างออกไปหากคลาสย่อยถูกส่งไปยังเมธอด (เป็นอาร์กิวเมนต์) ..
Reed Copsey

1
ปัญหาของรหัสนั้นคือถ้า T ไม่มีตัวสร้างที่ไม่มีพารามิเตอร์มันจะไม่ทำงาน
Nathan Taylor

@ นาธาน - มันเป็นเพียงตัวอย่างเพื่อแสดงการรับอินสแตนซ์ของ T. ซึ่งน่าจะเป็นวิธีการทั่วไปที่เขาจะมีประเภท T ให้ใช้งาน @ รีด - คุณพูดถูกแน่นอนฉันคิดว่านั่นคือสิ่งที่เขาเป็น
womp

อีกปัญหาหนึ่งก็คือในกรณีที่ T เป็นคลาสนามธรรมหรืออินเทอร์เฟซ - โค้ดด้านบนจะไม่ทำงาน ในกรณีที่มีข้อ จำกัด ประเภททั่วไป ("ที่") รหัสประเภทนี้จะปลอดภัยเนื่องจากเรารู้จักตัวสร้างและอาจมีเหตุผลในการสร้างอินสแตนซ์ประเภท นอกเหนือจากการสร้างอินสแตนซ์นั้นสิ้นเปลือง
Andrew
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.