Wie kann ich den Datentyp einer Variablen in C # abrufen?


92

Wie kann ich herausfinden, welchen Datentyp eine Variable enthält? (zB int, string, char usw.)

Ich habe jetzt so etwas:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Testing
{
    class Program
    {
        static void Main()
        {
            Person someone = new Person();
            someone.setName(22);
            int n = someone.getName();
            Console.WriteLine(n.typeOf());
        }
    }

    class Person
    {
        public int name;

        public void setName(int name)
        {
            this.name = name;
        }

        public int getName()
        {
            return this.name;
        }
    }
}

6
Sie haben den Typ bereits definiert -int
Jamiec

Dies ist unklar, was Sie unter "Datentyp herausfinden" verstehen. Normalerweise lautet die Antwort "Sie sehen sich nur die Signatur des Klassenmitglieds an und der Typ wird dort explizit angegeben". Ist Ihre Absicht, Klassenmitglieder zur Laufzeit zu inspizieren?
Wiktor Zychla

1
Außerhalb des Themas, aber was Sie hier geschrieben haben, ist besser so mit C # geschrieben: class Person { public string Name { get; set; } }oder class Person { private string m_Name; public string Name { get {return m_Name;} set { m_Name = value; } }. Lesen Sie die Dokumentation über Eigenschaften
Steve B

1
Jamiec hat recht. Statische Typisierung bedeutet, dass die Deklaration Ihren Typ für immer festlegt. Ihre Variable n kann nur von dem von Ihnen deklarierten Typ oder einem geerbten Typ sein. In Ihrem speziellen Fall haben Sie sich für die Anzeige eines Int entschieden. Dies ist ein Typ, von dem Sie nicht erben können. Daher kann n nur ein Int sein.
Ksempac

Antworten:


116

Es gibt ein wichtiges und subtiles Problem, das keiner von ihnen direkt anspricht. Es gibt zwei Möglichkeiten, den Typ in C # zu berücksichtigen: den statischen Typ und den Laufzeittyp .

Der statische Typ ist der Typ einer Variablen in Ihrem Quellcode. Es ist daher ein Konzept zur Kompilierungszeit. Dies ist der Typ, den Sie in einem Tooltip sehen, wenn Sie mit der Maus über eine Variable oder Eigenschaft in Ihrer Entwicklungsumgebung fahren.

Sie können einen statischen Typ erhalten, indem Sie eine generische Hilfsmethode schreiben, damit die Typinferenz dies für Sie erledigt:

   Type GetStaticType<T>(T x) { return typeof(T); }

Der Laufzeittyp ist der Typ eines Objekts im Speicher. Es ist daher ein Laufzeitkonzept. Dies ist der von der GetType()Methode zurückgegebene Typ .

Der Laufzeittyp eines Objekts unterscheidet sich häufig vom statischen Typ der Variablen, Eigenschaft oder Methode, die es enthält oder zurückgibt. Sie können beispielsweise folgenden Code verwenden:

object o = "Some string";

Der statische Typ der Variablen ist object, aber während der Laufzeit, die Art der Variable referent ist string. Daher wird in der nächsten Zeile "System.String" auf der Konsole gedruckt:

Console.WriteLine(o.GetType()); // prints System.String

Wenn Sie jedoch mit der Maus über die Variable oin Ihrer Entwicklungsumgebung fahren, wird der Typ System.Object(oder das entsprechende objectSchlüsselwort) angezeigt. Sie sehen dasselbe auch mit unserer Hilfsfunktion von oben:

Console.WriteLine(GetStaticType(o)); // prints System.Object

Für Value-Typen Variablen, wie int, double, System.Guid, wissen Sie , dass der Laufzeittyp immer gleich den statischen Typen sein, da die Value - Typen können nicht als Basisklasse für eine andere Art dienen; Der Werttyp ist garantiert der am meisten abgeleitete Typ in seiner Vererbungskette. Dies gilt auch für versiegelte Referenztypen: Wenn der statische Typ ein versiegelter Referenztyp ist, muss der Laufzeitwert entweder eine Instanz dieses Typs sein oder null.

Wenn umgekehrt der statische Typ der Variablen ein abstrakter Typ ist, ist garantiert, dass der statische Typ und der Laufzeittyp unterschiedlich sind.

Um dies im Code zu veranschaulichen:

// int is a value type
int i = 0;
// Prints True for any value of i
Console.WriteLine(i.GetType() == typeof(int));

// string is a sealed reference type
string s = "Foo";
// Prints True for any value of s
Console.WriteLine(s == null || s.GetType() == typeof(string));

// object is an unsealed reference type
object o = new FileInfo("C:\\f.txt");
// Prints False, but could be true for some values of o
Console.WriteLine(o == null || o.GetType() == typeof(object));

// FileSystemInfo is an abstract type
FileSystemInfo fsi = new DirectoryInfo("C:\\");
// Prints False for all non-null values of fsi
Console.WriteLine(fsi == null || fsi.GetType() == typeof(FileSystemInfo));

3
so variable.getType()gibt die Laufzeittyp (die rechte Seite - Typ), aber was gibt den statischen Typ (der linken Seite Typ einer Variablen)?
Barlop

@barlop, der zur Kompilierungszeit bekannt ist. Sie können verwenden typeof, um zur Laufzeit ein Typobjekt für den statischen Typ abzurufen.
Phoog

Ja, ich kenne statischen Typ = Kompilierungszeittyp und Laufzeittyp = dynamischer Typ. Wenn Sie den Typ der Variablen 'a' erhalten, können Sie dies nicht tun, typeof(a) wenn Sie typeof(int)int zurückgeben, aber die Variable 'a' nicht überprüfen und Ihnen den Typ 'a' anzeigen. Sie könnten sagen, dass Sie Der statische Typ von 'a' muss möglicherweise nicht angezeigt werden, aber Tatsache ist, dass er nicht angezeigt wird. Ich sehe also nicht, wie nützlich die Verwendung von typeof hier ist.
Barlop

4
@barlop Sie könnten dies tun, um Typinferenz für Sie erledigen zu lassen:Type GetStaticType < T > (T x) { return typeof(T); }
Phoog

1
Wie Sie vielleicht bemerkt haben, switchunterstützt @Jaquarh jetzt den Mustervergleich für Typprüfungen (vom Laufzeit-Typ, nicht statisch). Anstatt den von GetType () zurückgegebenen Wert einzuschalten, schalten Sie die Variable direkt ein.
Phoog

16

Es ist sehr einfach

variable.GetType().Name

Es wird Ihren Datentyp Ihrer Variablen zurückgeben


16

Im Allgemeinen müssen Sie kaum Typvergleiche durchführen, es sei denn, Sie tun etwas mit Reflexion oder Schnittstellen. Dennoch:

Wenn Sie den Typ kennen, mit dem Sie ihn vergleichen möchten, verwenden Sie die Operatoren isoder as:

if( unknownObject is TypeIKnow ) { // run code here

Der asOperator führt eine Umwandlung durch, die null zurückgibt, wenn dies fehlschlägt, und keine Ausnahme:

TypeIKnow typed = unknownObject as TypeIKnow;

Wenn Sie den Typ nicht kennen und nur Informationen zum Laufzeittyp wünschen, verwenden Sie die Methode .GetType ():

Type typeInformation = unknownObject.GetType();

In neueren Versionen von C # können Sie den isOperator verwenden, um eine Variable zu deklarieren, ohne Folgendes verwenden zu müssen as:

if( unknownObject is TypeIKnow knownObject ) {
    knownObject.SomeMember();
}

Zuvor mussten Sie Folgendes tun:

TypeIKnow knownObject;
if( (knownObject = unknownObject as TypeIKnow) != null ) {
    knownObject.SomeMember();
}

4

Halten Sie einfach den Mauszeiger über das Mitglied, an dem Sie interessiert sind, und sehen Sie den Tooltip - es wird der Typ des Mitglieds angezeigt:

Geben Sie hier die Bildbeschreibung ein



3

Eine Möglichkeit wäre die Verwendung einer Helfererweiterungsmethode wie folgt:

public static class MyExtensions
{
    public static System.Type Type<T>(this T v)=>typeof(T);
}

var i=0;
console.WriteLine(i.Type().FullName);

0

GetType() Methode

int n=34;
Console.WriteLine(n.GetType());
string name="Smome";
Console.WriteLine(name.GetType());

0

Schauen Sie sich einen der einfachen Wege an, dies zu tun

// Read string from console
        string line = Console.ReadLine(); 
        int valueInt;
        float valueFloat;
        if (int.TryParse(line, out valueInt)) // Try to parse the string as an integer
        {
            Console.Write("This input is of type Integer.");
        }
        else if (float.TryParse(line, out valueFloat)) 
        {
            Console.Write("This input is of type Float.");
        }
        else
        {
            Console.WriteLine("This input is of type string.");
        }
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.