在类方法中使用委托,objective-c

Mir*_*iro 3 delegates block objective-c class-method

我有一个想要使用CLLocationManager及其某些委托方法的类方法.

从类方法访问委托方法的最佳方法是什么,因为我没有真正的实例级别"self"?我可以实例化一个self并将其用作委托,这将使委托方法运行,但不会显示如何获取数据.什么是最好的方法?

// desired end function, which runs a block when location is found
[SFGeoPoint geoPointForCurrentLocationInBackground:^(SFGeoPoint *geoPoint, NSError *error) {
    if (!error) {
        // do something with the new geoPoint
        NSLog(@"GeoPoint: %@", geoPoint);
    }
}];


// SFGeoPoint class, key points
static CLLocationManager *_locationManager = nil;

// get geo point for current location and call block with it
+ (void) geoPointForCurrentLocationInBackground:( void ( ^ )( SFGeoPoint*, NSError* ) ) locationFound {

    SFGeoPoint *point = [[SFGeoPoint alloc] init];

    _locationManager = [[CLLocationManager alloc] init];

    // ?????????
    _locationManager.delegate = self;  // this gives a warning about incompatible pointer type assigning Delegate from Class; 
    _locationManager.delegate = point;  // could work, but how to get feedback?  

    _locationManager.distanceFilter = kCLDistanceFilterNone; // whenever we move
    _locationManager.desiredAccuracy = kCLLocationAccuracyBest;
    [_locationManager startUpdatingLocation];

    [_locationManager startUpdatingLocation];
    locationFound(point, nil);
}


/////////// Core Location Delegate
+ (void)locationManager:(CLLocationManager *)manager
didUpdateToLocation:(CLLocation *)newLocation
       fromLocation:(CLLocation *)oldLocation {

    [_locationManager stopUpdatingLocation];

    if (_locationBlock) {
        _locationBlock(newLocation);
    }
}
Run Code Online (Sandbox Code Playgroud)

Dim*_*ima 13

我会重做你正在做的事情,而不是使用类方法.相反,使用共享实例单例,这将允许您几乎完全相同地编写代码,但为您提供了一个实例,因此可以存储变量并分配代理.

以防您不熟悉语法:

+ (instancetype) shared
{
    static dispatch_once_t once;
    static id sharedInstance;
    dispatch_once(&once, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}
Run Code Online (Sandbox Code Playgroud)

然后只需将所有+(类)方法更改为-(实例)方法并使用[[MyClass shared] doWhatever];

使用可选包装器编辑:

如果你真的想在没有实例的情况下调用该方法,你可以编写一个包装器来执行类似这样的操作:

+ (void) doWhatever
{
    [[self shared] doWhatever];
}
Run Code Online (Sandbox Code Playgroud)

这就是说我通常不会建议这样做,因为你没有节省太多的代码,并且在将来可能会混淆从调用者的角度来看这实际上是什么样的方法.