Сведения о вопросе

HOLY

06:49, 17th August, 2020

Теги

objective-c   cocoa    

Как вы называете свои значения экземпляра/параметра?

Просмотров: 477   Ответов: 10

Будучи новичком в Objective-C (но долгосрочный программист C/++) я ищу советы/рекомендации по соглашениям об именах для переменных.

Мое личное предпочтение было бы использовать префикс для переменных экземпляра как для Ясности внутри функций, так и для предотвращения затенения параметров функции. Однако я поклонник свойств, которые исключают префиксы (если вы также не добавляете префиксы именам свойств, что не слишком хорошо работает и выглядит глупо). Точно так же я мог бы использовать соглашение "self.variable", но только если я сделаю EVERYTHING свойством.

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

@interface GridItem : NSObject
{
    CGRect _rect;
    ...  
}
@end

-(void) initFromRect:(CGRect)rect
{
    _rect = rect;
    ...
}

Ваше здоровье!



  Сведения об ответе

KOMP

07:51, 10th August, 2020

Большинство проектов Cocoa используют underbar в качестве префикса переменной экземпляра не IBOutlet и не используют префикс для переменных экземпляра IBOutlet .

Причина, по которой я не использую underbars для переменных экземпляра IBOutlet , заключается в том, что при загрузке файла nib, если у вас есть метод setter для подключенной розетки, будет вызван setter. Однако этот механизм не использует кодирование ключ-значение, поэтому IBOutlet, чье имя имеет префикс нижней панели (например , _myField ), не будет установлен, если setter не будет назван точно так же, как розетка ( например , set_myField:), что является нестандартным и грубым.

Кроме того, имейте в виду, что использование свойств типа self.myProp -это не то же самое, что доступ к переменным экземпляра. Вы отправляете сообщение , когда используете свойство, точно так же, как если бы вы использовали скобочную нотацию, например [self myProp] . Все свойства дают вам краткий синтаксис для указания как getter, так и setter в одной строке, и позволяют синтезировать их реализацию; они фактически не замыкают механизм отправки сообщений. Если вы хотите получить доступ к переменной экземпляра напрямую, но префиксировать ее с помощью self , вам нужно рассматривать self как указатель, как self->myProp , который на самом деле является доступом к полю в стиле C.

Наконец, никогда не используйте венгерскую нотацию при написании кода Cocoa и уклоняйтесь от других префиксов, таких как "f" и "m_" — это будет означать, что код был написан кем-то, кто не знает "get it", и вызовет подозрение у других разработчиков Cocoa.

В общем, следуйте рекомендациям руководства по кодированию для документа Cocoa в Apple Developer Connection, и другие разработчики смогут подобрать и понять ваш код, и ваш код будет хорошо работать со всеми функциями Cocoa, которые используют интроспекцию среды выполнения.

Вот как может выглядеть класс контроллера окон, используя мои соглашения:

// EmployeeWindowController.h
#import <AppKit/NSWindowController.h>

@interface EmployeeWindowController : NSWindowController {
@private
    // model object this window is presenting
    Employee *_employee;

    // outlets connected to views in the window
    IBOutlet NSTextField *nameField;
    IBOutlet NSTextField *titleField;
}

- (id)initWithEmployee:(Employee *)employee;

@property(readwrite, retain) Employee *employee;

@end

// EmployeeWindowController.m
#import "EmployeeWindowController.h"

@implementation EmployeeWindowController

@synthesize employee = _employee;

- (id)initWithEmployee:(Employee *)employee {
    if (self = [super initWithWindowNibName:@"Employee"]) {
        _employee = [employee retain];
    }
    return self;
}

- (void)dealloc {
    [_employee release];

    [super dealloc];
}

- (void)windowDidLoad {
    // populates the window's controls, not necessary if using bindings
    [nameField setStringValue:self.employee.name];
    [titleField setStringValue:self.employee.title];
}

@end

Вы увидите, что я использую переменную экземпляра, которая ссылается на Employee непосредственно в моем методе -init и -dealloc , в то время как я использую свойство в других методах. Обычно это хороший шаблон со свойствами: только когда-либо касайтесь базовой переменной экземпляра для свойства в инициализаторах, в -dealloc и в getter и setter для свойства.


  Сведения об ответе

lool

14:31, 5th August, 2020

Я следую совету Криса Хансона в отношении префикса подчеркивания ivar, хотя признаю, что я также использую подчеркивание для IBOutlets. Однако недавно я начал перемещать свои объявления IBOutlet в строку @property , согласно предложению @mmalc's . Преимущество заключается в том, что все мои ивары теперь имеют символ подчеркивания и стандартные сеттеры KVC называются (т. е. setNameField: ). Кроме того, имена розеток не имеют подчеркивания в Построителе интерфейсов.

@interface EmployeeWindowController : NSWindowController {
@private
    // model object this window is presenting
    Employee *_employee;

    // outlets connected to views in the window
    NSTextField *_nameField;
    NSTextField *_titleField;
}

- (id)initWithEmployee:(Employee *)employee;

@property(readwrite, retain) Employee *employee;
@property(nonatomic, retain) IBOutlet NSTextField *nameField;
@property(nonatomic, retain) IBOutlet NSTextField *titleField;

@end


  Сведения об ответе

ITSME

20:51, 15th August, 2020

Вы можете использовать префикс underbar на вашем ivars и все еще использовать не-underbar имя для ваших свойств. Для синтезированных аксессоров просто сделайте это:

@synthesize foo = _foo;

Это говорит компилятору синтезировать свойство "Foo", используя the_foo Ивар.

Если вы пишете свои собственные методы доступа,то вы просто используете underbar ivar в своей реализации и сохраняете имя метода, не являющегося underbar.


  Сведения об ответе

prince

09:12, 4th August, 2020

Лично я следую соглашениям об именовании Cocoa, используя camel-casing для функций и переменных и заглавные camel-casing для имен объектов (без ведущего NS, конечно).

Я нахожу, что префиксация типов делает код более непрозрачным для тех, кто его не писал (так как все неизменно используют разные префиксы), и в современном IDE не так уж трудно определить тип чего-то.


  Сведения об ответе

COOL

14:36, 19th August, 2020

С введением свойств я не вижу необходимости в префиксе "_" к переменным экземпляра класса. Вы можете установить простое правило (описанное в вашем заголовочном файле), что любые переменные, которые будут доступны вне класса, должны быть доступны через свойство или с помощью пользовательских методов в классе, чтобы повлиять на значения. Это мне кажется гораздо чище, чем иметь имена с "_", наклеенными на них спереди. Он также правильно инкапсулирует значения, чтобы вы могли контролировать, как они изменяются.


  Сведения об ответе

DAAA

21:50, 15th August, 2020

Эндрю: на самом деле есть много разработчиков Cocoa, которые вообще не используют префиксы переменных экземпляра. Это также чрезвычайно распространено в мире Smalltalk (на самом деле, я бы сказал, что в Smalltalk почти неслыханно использовать префиксы для переменных экземпляра).

Префиксы переменных экземпляра всегда поражали меня как C++ - изм, который был перенесен в Java, а затем в C#., поскольку объективный мир C был в значительной степени параллелен миру C++, где, поскольку миры Java и C# являются его преемниками, это объясняет разницу "cultural", которую вы можете увидеть на этом между различными наборами разработчиков.


  Сведения об ответе

PHPH

07:56, 6th August, 2020

Я не люблю использовать подчеркивания в качестве префиксов для любых идентификаторов, потому что C и C++ оба оставляют определенные префиксы подчеркивания для использования реализацией.

Я думаю, что использование "self.variable" уродливо.

В общем случае, я использую не украшенные идентификаторы (то есть никаких префиксов или суффиксов) для переменных, например. Если ваш класс настолько сложен, что вы не можете запомнить переменные экземпляра, вы в беде. Поэтому для вашего примера я бы использовал "rect" в качестве имени переменной экземпляра и "newRect" или "aRect" в качестве имени параметра.


  Сведения об ответе

KOMP

20:45, 22nd August, 2020

Наряду с тем, что было сказано здесь, обязательно прочитайте документацию Cocoa по ключевому значению, соблюдающему совместимое именование. Строго следуя этой схеме, вы значительно поможете себе в долгосрочной перспективе.


  Сведения об ответе

pumpa

11:53, 5th August, 2020

Хотя я люблю использовать префикс подчеркивания для ivars, я ненавижу писать @synthesize строк из-за всего дублирования (это не очень DRY ). Я создал макрос, чтобы помочь сделать это и уменьшить дублирование кода. Таким образом, вместо:

@synthesize employee = _employee;

Я пишу это:

ddsynthesize(employee);

Это простой макрос, использующий вставку маркеров для добавления подчеркивания в правую сторону:

#define ddsynthesize(_X_) @synthesize _X_ = _##_X_

Единственным недостатком является то, что он будет путать инструмент рефакторинга Xcode, и он не будет переименован, если вы переименуете свойство с помощью рефакторинга.


  Сведения об ответе

JUST___

13:18, 2nd August, 2020

Мой стиль гибридный и действительно пережиток от PowerPlant дней:

THe наиболее полезными префиксами, которые я использую, являются "in" и "out" для параметров функции / метода. Это поможет вам сразу узнать, для чего предназначены параметры, и действительно поможет предотвратить конфликты между параметрами метода и переменными экземпляра (сколько раз вы видели конфликт параметра "table" с переменной экземпляра с тем же именем). E.g.:

- (void)doSomethingWith:(id)inSomeObject error:(NSError **)outError;

Затем я использую голое имя например переменные и имена свойств:

Затем я использую "the" в качестве префикса для локальных переменных: theTable, theURL и т. д. Опять же, это помогает различать локальные переменные и переменные экземпляра.

Затем, следуя стилю PowerPlant, я использую несколько других префиксов: k для констант, E для enums, g для глобалов и s для статики.

Я использую этот стиль уже около 12 лет.


Ответить на вопрос

Чтобы ответить на вопрос вам нужно войти в систему или зарегистрироваться