Gibt es eine Möglichkeit, wie ein Wörterbuch aller Schlüssel-Wert-Paare einer Klasse zu erhalten?Gibt es eine Möglichkeit, zur Laufzeit in Cocoa/Cocoa Touch die Ivars einer Klasse dynamisch zu bestimmen?
Antwort
Sie müssen Ihre eigenen mit der Objective-C Runtime functions rollen. Hier ist ein sehr einfacher Beispielcode. Beachten Sie, dass die Ivars einer Klasse nicht die Ivars der Superklasse erhalten. Sie müssten dies explizit tun, aber die Funktionen sind alle in der Laufzeit vorhanden.
#import <objc/objc-runtime.h>
#include <inttypes.h>
#include <Foundation/Foundation.h>
@interface Foo : NSObject
{
int i1;
}
@end
@implementation Foo
@end
@interface Bar : Foo
{
NSString* s1;
}
@end
@implementation Bar
@end
int main(int argc, char** argv)
{
NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
unsigned int count;
Ivar* ivars = class_copyIvarList([Bar class], &count);
for(unsigned int i = 0; i < count; ++i)
{
NSLog(@"%@::%s", [Bar class], ivar_getName(ivars[i]));
}
free(ivars);
[pool release];
}
Ich bin nur für ivars nicht sicher, aber wenn man sie als Eigenschaften definiert haben, ist es möglich, die verfügbaren Eigenschaften auf einer Klasse zuzugreifen.
Ich habe SQLitePersistentObjects für ein paar Projekte verwendet und es hat einige hilfreiche Code, der die Eigenschaften in der Klasse verwendet, um die Serialisierung zu und von SQLite herauszufinden.
Es verwendet die Funktion class_copyPropertyList, um die verfügbare Liste von Eigenschaften für eine Klasse abzurufen.
Genauer gesagt:
+(NSDictionary *)propertiesWithEncodedTypes
{
// DO NOT use a static variable to cache this, it will cause problem with subclasses of classes that are subclasses of SQLitePersistentObject
// Recurse up the classes, but stop at NSObject. Each class only reports its own properties, not those inherited from its superclass
NSMutableDictionary *theProps;
if ([self superclass] != [NSObject class])
theProps = (NSMutableDictionary *)[[self superclass] propertiesWithEncodedTypes];
else
theProps = [NSMutableDictionary dictionary];
unsigned int outCount;
objc_property_t *propList = class_copyPropertyList([self class], &outCount);
int i;
// Loop through properties and add declarations for the create
for (i=0; i < outCount; i++)
{
objc_property_t * oneProp = propList + i;
NSString *propName = [NSString stringWithUTF8String:property_getName(*oneProp)];
NSString *attrs = [NSString stringWithUTF8String: property_getAttributes(*oneProp)];
NSArray *attrParts = [attrs componentsSeparatedByString:@","];
if (attrParts != nil)
{
if ([attrParts count] > 0)
{
NSString *propType = [[attrParts objectAtIndex:0] substringFromIndex:1];
[theProps setObject:propType forKey:propName];
}
}
}
free(propList);
return theProps;
}
Dies gibt ein Wörterbuch der Eigenschaften - Sie werden Sie wieder bekommen einige Untersuchung der Ergebnisse tun müssen, aber Sie sollten in der Lage sein, was Sie brauchen, wenn Sie Verwenden von Eigenschaften.
Ja, durchaus möglich:
int numIvars = 0;
Ivar * ivars = class_copyIvarList([anInstanceOfAClass class], &numIvars);
NSMutableDictionary * pairs = [NSMutableDictionary dictionary];
for (int i = 0; i < numIvars; ++i) {
Ivar ivar = ivars[i];
NSString * ivarName = [NSString stringWithCString:ivar_getName(ivar) encoding:NSUTF8StringEncoding];
id ivarValue = [anInstanceOfAClass valueForKey:ivarName];
[pairs setObject:ivarValue forKey:ivarName];
}
free(ivars);
NSLog(@"%@", pairs);
- 1. Gibt es eine Möglichkeit, die Hintergrundfarbe eines Terminals zu bestimmen?
- 2. Gibt es eine Möglichkeit, den Bytecode für eine Klasse zur Laufzeit zu erhalten?
- 3. Gibt es zur Laufzeit in Perl eine tatsächlich abgeleitete Klasse?
- 4. Gibt es eine Möglichkeit, zur Laufzeit in GHC zu bestimmen, ob ein abstrakter Wert eine Funktion ist?
- 5. Gibt es eine Möglichkeit, eine Akka-Actor-Implementierung von einem ActorRef zu bestimmen?
- 6. Bestimmen Sie wsHttpBinding zur Laufzeit mit WCF
- 7. Gibt es eine Möglichkeit zu bestimmen, ob der aktuelle Bildschirm Touch unterstützt?
- 8. Gibt es eine Möglichkeit, den Typ eines Mountpoints zu bestimmen?
- 9. Gibt es eine Möglichkeit, die Bundle ID zur Laufzeit zu bekommen?
- 10. Gibt es eine Möglichkeit, das aktuelle Outlook-Aktivitätsniveau zu bestimmen?
- 11. Gibt es eine Möglichkeit zu bestimmen, ob Browser Telefonverbindungen
- 12. Gibt es eine Möglichkeit, die Varianz einer Schnittstelle/eines Delegaten in C# 4.0 zu bestimmen?
- 13. Gibt es eine Möglichkeit, den * tatsächlichen * Sitzungsspeicherpfad zu bestimmen?
- 14. Gibt es eine Möglichkeit, die Zeit zu bestimmen, die ein Client auf einer Webseite verbringt
- 15. Gibt es eine Möglichkeit, auf den Typ einer Scala Option Deklaration zur Laufzeit mit Reflektion zuzugreifen?
- 16. Gibt es eine Möglichkeit, die Unterklasse meiner Klasse zu verbieten?
- 17. Gibt es eine Möglichkeit, Baseurl dynamisch in require.js zu setzen?
- 18. Gibt es eine Möglichkeit, die Parserzeit in PHP zu messen?
- 19. Gibt es eine Möglichkeit, programmgesteuert die richtigen Größen für Apples integrierte Steuerelemente zu bestimmen?
- 20. C#: Gibt es eine Möglichkeit, den ausgewählten Index eines Elements zur Laufzeit in listview zu setzen?
- 21. Gibt es eine Möglichkeit, Svg-Daten zur Laufzeit in einem swf zu rendern?
- 22. Gibt es eine Möglichkeit, die allgemeine Kostenfunktion einer beliebigen Java-Methode zu bestimmen?
- 23. Gibt es eine einfache Möglichkeit zu bestimmen, welche Faktoren zur Größe eines HTML-Elements beitragen?
- 24. Gibt es eine Möglichkeit, d: DesignData xaml zur Laufzeit zu verwenden?
- 25. Gibt es eine Möglichkeit, ein Ziel dynamisch zu aktualisieren?
- 26. Welche Möglichkeiten gibt es, eine Methode zur Laufzeit aufzurufen?
- 27. Gibt es eine Möglichkeit, eine Klasse (nicht eine Instanz) dynamisch zu erstellen?
- 28. Gibt es eine Möglichkeit, Speicherlecks in einer abgeleiteten Klasse zu verhindern, ohne die Basisklasse zu ändern?
- 29. Gibt es eine Möglichkeit, eine versteckte Version eines Django-Feldes in einer Vorlage dynamisch zu rendern?
- 30. Dynamisch generieren Klassen zur Laufzeit in PHP?
Seit '' class_copyIvarList' hat im Namen copy', Sie sind verantwortlich für den Speicher aufzuräumen. Daher brauchen Sie auch 'free (ivars);' da drin. –
völlig richtig. Vielen Dank. – nall
Es ist nur Druck bar :: s1. Aber wo i1? –