Подтвердить что ты не робот

Как разрешить эту циклическую зависимость?

Я новичок в разработке iOS и сталкиваюсь с проблемой с моими заголовочными файлами. Я столкнулся с проблемой циклической зависимости с моими заголовочными файлами. Класс делегирования моего приложения содержит указатель на мой контроллер представления, так как я должен установить один из свойств контроллера представления в свой метод didFinishLaunchingWithOptions...

//appDelegate.h     //DISCLAIMER: THIS IS UNTESTED CODE AND WRITTEN ON THE FLY TO ILLUSTRATE MY POINT
#import <UIKit/UIKit.h>
#import "MyViewController.h"

@interface appDelegate

     NSManagedObjectContext *managedObjectContext;

     MyViewController *viewController;
     BOOL myFlag;

@end

//appDelegate.m
@implementation appDelegate

- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
     viewController.managedObjectContext = self.managedObjectContext;
     .
     .
     .
}
@end

И в моем представлении контроллер, я ссылаюсь на свойство myFlag, что в моем делете приложения...

//MyViewController.h                                        
#import "appDelegate.h"     //<---circular dependency, causing "Expected specifier-qualifier-list before MyViewController" errors in my appDelegate header file

@interface MyViewController: UIViewController
{
     NSManagedObjectContext *managedObjectContext;
}
@end

//MyViewController.m
@import "MyViewController.h"

@implementation MyViewController

- (void)viewWillAppear:(BOOL)animated
{
     [super viewWillAppear:animated];

     ((appDelegate*)[[UIApplication sharedApplication] delegate]).myFlag = NO;
}

@end

Но чтобы получить доступ к свойству myFlag в моем делете приложения, мне нужно импортировать файл заголовка делегата приложения. Это и вызывает циклическую зависимость. Не знаете, как это решить, может ли кто-нибудь столкнуться с этим?

Заранее благодарим за помощь!

4b9b3361

Ответ 1

Не #import "MyViewController.h" в appDelegate.h. Вместо этого forward-declare класс.

@class MyViewController;

@interface appDelegate

     NSManagedObjectContext *managedObjectContext;

     MyViewController *viewController;
     BOOL myFlag;

@end

Кроме того, вам не нужно #import "appDelegate.h" в MyViewController.h, если вам нужно всего лишь ссылаться на свойство myFlag в реализации . Вместо этого импортируйте его в файл MyViewController.m.

Ответ 2

@class - синтаксический подход, который вы ищете.

Многие кодеры стремятся избежать этой круглости (которая соединяет ваши классы в двух направлениях, то есть ваш контроллер просмотра может использоваться только в тех случаях, когда делегат приложения имеет этот BOOL). Есть несколько способов сделать это:

  • Переместить переменную состояния в одноэлементный
  • Попросите диспетчер представлений получить значение через интерфейс, который выполняет делегат
  • Наблюдение за ключевыми значениями (которое делегат вашего приложения будет настраивать на вашем контроллере представления)

Для небольших проектов такая зависимость, вероятно, не является проблемой, но по мере роста размера проекта и желательности повторного использования кода чистое функциональное разделение становится все более ценным.

Ответ 3

Не читал все, но вы можете пересылать объявления с помощью @class. Обычно я решаю круговые зависимости.