2016-08-02 13 views
1

Ich werde C als Beispielsprache verwenden, um zu zeigen, was ich meine.Sprache, in der Variablentypen selbst Variablen sind?

struct parent 
{ 
    int x; 
    char y; 
}; 
struct child 
{ 
    char y; 
    int x; 
}; 

int foo(void * s, type obj_type) 
{ 
    // the casting is done using a "type" variable 
    obj_type obj = (obj_type) s; 
    return obj->x; 
} 

int main(int argc, char** argv) 
{ 
    type obj_type = struct parent *; 
    struct parent p; 
    p.x = 0; 

    //returns 0 
    foo(&p, obj_type); 

    obj_type = struct child *; 
    struct child c; 
    c.x = 5; 

    // returns 5 
    foo(&c, obj_type); 

    return 0; 
} 

Wie Sie sehen können, x für beide Strukturen an verschiedenen Orten im Speicher abgelegt, so kann ich nicht nur eine statische im Speicher versetzt haben. Ist das in C überhaupt möglich (einige Präprozessormagie, an die ich nicht denken konnte)? Ich nehme an, nein, aber gibt es Sprachen, in denen Typen selbst als Variablen verwendet werden können? Ich würde gerne die Implikationen der Typ-zentrierten Programmierung erkunden

EDIT: wie itsme86 wies darauf hin, C# hat diese Fähigkeit mit der Klasse Type. Auch C++ Concepts und Haskell Type-Klasse sind von Interesse.

+0

Ich glaube nicht, ich folge Ihre Bitten. Willst du 'return obj-> x;' um 'int' zurückzugeben? –

+0

ja. Abhängig von dem Typ-Operator kann obj-> x an der Adresse von obj liegen oder es könnte ein Offset von 1 Byte entfernt sein (angesichts der Struktur-Einrichtung). Was ich will, ist eine Variable, die verwendet werden kann, um Typen anstelle von Werten zu identifizieren – m1cky22

+3

Die Funktion, die Sie suchen, ist [Typ Introspektion] (https://en.wikipedia.org/wiki/Type_introspection). Es ist in einigen objektorientierten Sprachen verfügbar, aber nicht in C (obwohl Sie es einbinden können, indem Sie ein 'type'-Mitglied als erstes Mitglied all Ihrer Strukturen hinzufügen). – user3386109

Antwort

2

Wenn Sie Typsicherheit hinter sich lassen Sie offsetof (von stddef.h) verwenden:

int foo(unsigned char * s, size_t offset) 
{ 
    int* ptr = (int*)(s + offset); 
    return *ptr; 
} 

foo((unsigned char*)&p, offsetof(struct parent, x)); 

Aber ich würde es nicht wirklich empfehlen.

+0

Das ist definitiv ein Weg, um einige interessante Ergebnisse zu bekommen, die ich gesucht habe. Der Hauptgrund, den ich stelle, ist jedoch, weil ich sehen möchte, ob Variablentypen Typen als ihre Werte enthalten können, d. H. "Type t = int". Ist das in jeder Sprache möglich? – m1cky22

0

In Java können Sie über die Reflektions-API auf Typinformationen zugreifen. Hier ein Beispiel:

package stackoverflow; 

import java.util.Arrays; 

public class MyClass { 
    public static void main(String[] args) { 
     MyClass myInstance = new MyClass(42, "foo"); 
     Class<MyClass> myClass = MyClass.class; 
     System.out.println(myInstance instanceof MyClass); 
     System.out.println(myInstance.getClass().equals(myClass)); 
     System.out.println(myClass.getName()); 
     System.out.println(Arrays.toString(myClass.getDeclaredFields())); 
     System.out.println(Arrays.toString(myClass.getDeclaredMethods())); 
    } 

    private final int i; 
    private final String s; 

    public MyClass(int i, String s) { 
     this.i = i; 
     this.s = s; 
    } 

    public int getI() { 
     return i; 
    } 

    public String getS() { 
     return s; 
    } 
} 

Ausgang:

true 
true 
stackoverflow.MyClass 
[private final int stackoverflow.MyClass.i, private final java.lang.String stackoverflow.MyClass.s] 
[public int stackoverflow.MyClass.getI(), public java.lang.String stackoverflow.MyClass.getS(), public static void stackoverflow.MyClass.main(java.lang.String[])] 

Wie Sie sehen können, MyClass.class ist ein Ziel der gattungs java.lang.Class<T>, die MyClass Zugang zu Informationen über die Klasse zur Verfügung stellt. Dieses Objekt kann auch über jede Instanz der Klasse abgerufen werden, siehe myInstance.getClass(). Ich habe ein paar Beispiele hinzugefügt, um zu zeigen, was zugänglich ist. Sie können auch neue Instanzen einer Klasse über ihr Objekt Class erstellen. Für weitere Informationen möchten Sie vielleicht auch das Javadoc des java.lang.reflect Pakets betrachten.


Bitte beachten Sie, dass Sie damit nur auf diese Informationen zugreifen können. Zum Beispiel erlaubt es Ihnen nicht, den Typ einer vorhandenen Instanz zu ändern, was ich für eine gute Sache halte. Dies scheint jedoch in Python möglich:

Can I dynamically convert an instance of one class to another?