Pergunta

eu sei sobre o ALTO (o que é bastante útil!), mas quais práticas de programação você usa ao escrever Objective-C e, mais especificamente, ao usar Cocoa (ou CocoaTouch).

Foi útil?

Solução

Há algumas coisas que comecei a fazer que não considero padrão:

1) Com o advento das propriedades, não uso mais "_" para prefixar variáveis ​​de classe "privadas".Afinal, se uma variável pode ser acessada por outras classes, não deveria haver uma propriedade para ela?Sempre não gostei do prefixo "_" por tornar o código mais feio e agora posso deixá-lo de fora.

2) Falando em coisas privadas, prefiro colocar definições de métodos privados dentro do arquivo .m em uma extensão de classe como esta:

#import "MyClass.h"

@interface MyClass ()
- (void) someMethod;
- (void) someOtherMethod;
@end

@implementation MyClass

Por que sobrecarregar o arquivo .h com coisas com as quais pessoas de fora não deveriam se importar?O vazio() funciona para categorias privadas no arquivo .m, e emite avisos de compilação caso você não implemente os métodos declarados.

3) Comecei a colocar dealloc no topo do arquivo .m, logo abaixo das diretivas @synthesize.O que você desaloca não deveria estar no topo da lista de coisas que você deseja pensar em uma aula?Isso é especialmente verdadeiro em um ambiente como o iPhone.

3.5) Nas células da tabela, torne cada elemento (incluindo a própria célula) opaco para desempenho.Isso significa definir a cor de fundo apropriada em tudo.

3.6) Ao usar um NSURLConnection, como regra você pode querer implementar o método delegado:

- (NSCachedURLResponse *)connection:(NSURLConnection *)connection
                  willCacheResponse:(NSCachedURLResponse *)cachedResponse
{
      return nil;
}

Acho que a maioria das chamadas da Web são muito singulares e é mais uma exceção do que uma regra: você deseja que as respostas sejam armazenadas em cache, especialmente para chamadas de serviço da Web.A implementação do método conforme mostrado desativa o cache de respostas.

Também interessantes são algumas boas dicas específicas para iPhone de Joseph Mattiello (recebidas em uma lista de discussão do iPhone).Há mais, mas estes foram os mais úteis que pensei (observe que alguns bits foram ligeiramente editados do original para incluir detalhes oferecidos nas respostas):

4) Use precisão dupla apenas se for necessário, como ao trabalhar com CoreLocation.Certifique-se de terminar suas constantes em 'f' para fazer o gcc armazená-las como carros alegóricos.

float val = someFloat * 2.2f;

Isto é principalmente importante quando someFloat pode na verdade ser duplo, você não precisa da matemática do modo misto, pois está perdendo precisão em 'val' no armazenamento.Embora os números de ponto flutuante sejam suportados no hardware dos iPhones, ainda pode levar mais tempo para fazer aritmética de precisão dupla em oposição à precisão simples.Referências:

Nos telefones mais antigos, supostamente, os cálculos operam na mesma velocidade, mas você pode ter mais componentes de precisão simples nos registros do que duplos; portanto, para muitos cálculos, a precisão única acabará sendo mais rápida.

5) Defina suas propriedades como nonatomic.Eles estão atomic por padrão e após a síntese, o código do semáforo será criado para evitar problemas de multithreading.99% de vocês provavelmente não precisam se preocupar com isso e o código fica muito menos inchado e mais eficiente em termos de memória quando definido como não atômico.

6) SQLite pode ser uma maneira muito rápida de armazenar grandes conjuntos de dados em cache.Um aplicativo de mapa, por exemplo, pode armazenar seus blocos em arquivos SQLite.A parte mais cara é a E/S de disco.Evite muitas pequenas escritas enviando BEGIN; e COMMIT; entre grandes blocos.Usamos um cronômetro de 2 segundos, por exemplo, que é reiniciado a cada novo envio.Quando expirar, enviamos COMMIT;, o que faz com que todas as suas gravações sejam agrupadas em uma grande parte.SQLite armazena dados de transação em disco e fazer esse empacotamento inicial/final evita a criação de muitos arquivos de transação, agrupando todas as transações em um arquivo.

Além disso, o SQL bloqueará sua GUI se estiver no thread principal.Se você tiver uma consulta muito longa, é uma boa ideia armazenar suas consultas como objetos estáticos e executar seu SQL em um thread separado.Certifique-se de agrupar qualquer coisa que modifique o banco de dados para strings de consulta em @synchronize() {} blocos.Para consultas curtas, deixe as coisas no tópico principal para maior comodidade.

Mais dicas de otimização do SQLite estão aqui, embora o documento pareça desatualizado, muitos dos pontos provavelmente ainda são válidos;

http://web.utk.edu/~jplyon/sqlite/SQLite_optimization_FAQ.html

Outras dicas

Não use strings desconhecidos como cordas de formato

Quando métodos ou funções assumem um argumento de string de formato, você deve ter controle sobre o conteúdo da sequência do formato.

Por exemplo, ao registrar seqüências de registro, é tentador passar a variável da string como o único argumento para NSLog:

    NSString *aString = // get a string from somewhere;
    NSLog(aString);

O problema é que a string pode conter caracteres que são interpretados como seqüências de formatos. Isso pode levar a uma saída errônea, falhas e problemas de segurança. Em vez disso, você deve substituir a variável da string em uma string de formato:

    NSLog(@"%@", aString);

Use convenções e terminologia padrão de nomeação e formatação de cacau, em vez do que você está acostumado em outro ambiente. Lá são Muitos desenvolvedores de cacau por aí e, quando outro deles começa a trabalhar com seu código, será muito mais acessível se parecer e parecer semelhante a outro código de cacau.

Exemplos do que fazer e o que não fazer:

  • Não declare id m_something; na interface de um objeto e chamá -lo de variável de membro ou campo; usar something ou _something por seu nome e chame de um variável de instância.
  • Não cite um getter -getSomething; O nome de cacau adequado é apenas -something.
  • Não cite um setter -something:; deveria ser -setSomething:
  • O nome do método é intercalado com os argumentos e inclui dois pontos; Está -[NSObject performSelector:withObject:], não NSObject::performSelector.
  • Use inter-caps (camelcase) em nomes de métodos, parâmetros, variáveis, nomes de classe, etc. em vez de underbars (sublinhados).
  • Os nomes de classe começam com uma letra, variável e nomes de métodos com baixo caso.

Tudo o que você fizer, não Use a notação húngara no estilo Win16/Win32. Até a Microsoft desistiu disso com a mudança para a plataforma .NET.

Iboutlets

Historicamente, o gerenciamento de memória dos pontos de venda tem sido ruim. A melhor prática atual é declarar pontos de venda como propriedades:

@interface MyClass :NSObject {
    NSTextField *textField;
}
@property (nonatomic, retain) IBOutlet NSTextField *textField;
@end

O uso de propriedades deixa a semântica de gerenciamento de memória clara; Ele também fornece um padrão consistente se você usar a síntese variável da instância.

Use o analisador estático LLVM/CLANG

Nota: Em Xcode 4, agora está incorporado ao IDE.

Você usa o Analisador estático de clang Para-sem surpresa-analise seu código C e Objective-C (sem C ++ ainda) no Mac OS X 10.5. É trivial instalar e usar:

  1. Baixe a versão mais recente de esta página.
  2. Da linha de comando, cd para o seu diretório de projeto.
  3. Executar scan-build -k -V xcodebuild.

(Existem algumas restrições adicionais etc., em particular, você deve analisar um projeto em sua configuração "Debug" - veja http://clang.llvm.org/staticanalysisusage.html Para detalhes-mas isso é mais ou menos o que se resume.)

O analisador produz um conjunto de páginas da Web para você que mostra provável gerenciamento de memória e outros problemas básicos que o compilador não consegue detectar.

Isso é sutil, mas útil. Se você está passando como um delegado para outro objeto, redefine o delegado desse objeto antes de você dealloc.

- (void)dealloc
{
self.someObject.delegate = NULL;
self.someObject = NULL;
//
[super dealloc];
}

Ao fazer isso, você garante que os métodos mais delegados sejam enviados. Como você está prestes a dealloc E desapareça no éter que você deseja garantir que nada possa enviar mais mensagens por acidente. Lembre-se de si mesmo. AlgumObject poderia ser retido por outro objeto (pode ser um singleton ou no pool de autorlease ou o que seja) e até que você diga "Pare de me enviar mensagens!", Ele pensa que é o seu objeto justo a ser divulgado é um jogo justo.

Entrar nesse hábito o salvará de muitos acidentes estranhos que são uma dor de depuração.

O mesmo principal se aplica à observação do valor -chave e também das NSNotificações.

Editar:

Ainda mais defensivo, mudança:

self.someObject.delegate = NULL;

em:

if (self.someObject.delegate == self)
    self.someObject.delegate = NULL;

@kendell

Em vez de:

@interface MyClass (private)
- (void) someMethod
- (void) someOtherMethod
@end

Utilização:

@interface MyClass ()
- (void) someMethod
- (void) someOtherMethod
@end

Novo no objective-C 2.0.

Classe extensões são descritos na Apple objective-C 2.0 de Referência.

"Classe extensões permitem que você declare adicionais API necessários para uma classe em outros locais do que dentro da classe da primária @interface bloco"

Então, eles são parte da classe real - e NÃO um (privado) categoria além da aula.Sutil mas importante diferença.

Evitar autorelease

Desde que você normalmente(1) não tem controle direto sobre sua vida, autoreleased objetos podem persistir por um relativamente longo período de tempo e aumentar desnecessariamente o consumo de memória do seu aplicativo.Enquanto no ambiente de trabalho podem ser de pouca conseqüência, mais restrita de plataformas isto pode ser um problema significativo.Em todas as plataformas, portanto, e especialmente em mais restrita de plataformas, é considerado como a melhor prática para evitar a utilização de métodos que levaria a autoreleased objetos e, em vez disso, você é encorajado a usar o alloc/init padrão.

Assim, em vez de:

aVariable = [AClass convenienceMethod];

onde possível, você deve usar:

aVariable = [[AClass alloc] init];
// do things with aVariable
[aVariable release];

Quando você estiver escrevendo seu próprio métodos que retornam um recém-criada objeto, você pode tirar vantagem de Cacau convenção de nomenclatura do para sinalizar ao receptor que deve ser lançado pela prefixar o nome do método com o "novo".

Assim, em vez de:

- (MyClass *)convenienceMethod {
    MyClass *instance = [[[self alloc] init] autorelease];
    // configure instance
    return instance;
}

você poderia escrever:

- (MyClass *)newInstance {
    MyClass *instance = [[self alloc] init];
    // configure instance
    return instance;
}

Desde o nome do método começa com "novos", os consumidores da sua API de saber que eles são responsáveis por liberar o recebeu objeto (ver, por exemplo, NSObjectController do newObject método).

(1) Você pode assumir o controle por meio de seu próprio local autorelease piscinas.Para mais informações, consulte Autorelease Piscinas.

Alguns desses já foram mencionados, mas aqui está o que eu posso pensar em cima da minha cabeça:

  • Siga o GOTEJAMENTO regras de nomenclatura. Mesmo se você não usar o GOTEJAMENTO agora, na minha experiência, muitas vezes, é ainda benéfico no futuro.E se você estiver usando o GOTEJAMENTO ou ligações, você precisa saber que as coisas vão funcionar da maneira que é suposto.Este abrange não apenas acessor de métodos e variáveis de instância, mas o para-muitos relacionamentos, validação, auto-notificar dependentes de chaves, e assim por diante.
  • Coloque métodos privados em uma categoria. Não apenas a interface, mas a implementação bem.É bom ter alguma distância conceptual entre o privado e o não-métodos privados.Posso incluir tudo na minha .m de arquivo.
  • Colocar thread de plano de fundo métodos em uma categoria. O mesmo que acima.Eu descobri que é sempre bom ter uma clara barreira conceitual quando você está pensando sobre o que está na thread principal e o que não.
  • Utilização #pragma mark [section]. Normalmente eu grupo pelos meus próprios métodos, cada subclasse do substituições, e qualquer informação ou formal de protocolos.Isso torna muito mais fácil para saltar para exatamente o que eu estou procurando.Sobre o mesmo tema, o grupo de métodos semelhantes (como uma tabela do modo de exibição métodos de delegado) juntos, não basta colocá-los em qualquer lugar.
  • Prefixo privado e métodos de ivars com _. Eu gosto do jeito que parece, e provavelmente não vou usar um ivar quando eu me refiro a propriedade por acidente.
  • Não use o modificador de métodos / propriedades em init & dealloc. Eu nunca tive nada de ruim acontecer por causa disso, mas eu posso ver a lógica, se você alterar o método para fazer algo que depende do estado de seu objeto.
  • Colocar IBOutlets em propriedades. Na verdade, eu só de ler isso aqui, mas vou começar a fazê-lo.Independentemente de qualquer memória benefícios, parece melhor estilisticamente (pelo menos para mim).
  • Evite escrever código não absolutamente necessário. Isso realmente cobre um monte de coisas, como fazer quando um ivars #define vai fazer, ou o cache de uma matriz em vez de ordenar que a cada vez que os dados são necessários.Há muito que eu poderia dizer sobre isso, mas a linha inferior é não escrever código até que você precisar, ou o criador de perfil diz que você.Isto torna as coisas muito mais fácil manter a longo prazo.
  • Terminar o que inicia. Ter um monte de semi-acabados, buggy código é a maneira mais rápida de matar um projeto morto.Se você precisa de um stub método que tudo bem, é só indicar-lo colocando NSLog( @"stub" ) no interior, ou no entanto, você deseja manter o controle das coisas.

Escrever testes de unidade.Você pode testar um monte das coisas que estão no Cacau que pode ser mais difícil em outros quadros.Por exemplo, com o código da INTERFACE do usuário, você pode verificar se as coisas estão ligadas como elas devem ser e confiar que eles vão trabalhar quando usado.E você pode configurar estado e invocar métodos de delegado facilmente testá-los.

Você também não tem público vs.protegido vs.método particular visibilidade ficando no jeito de escrever testes para seus internos.

Regra De Ouro:Se você alloc em seguida, você release!

ATUALIZAÇÃO:A menos que você estiver usando ARCO

Não escreva objective-C como se fosse Java/C#/C++/etc.

Uma vez eu vi uma equipe usou para escrever aplicações web em Java EE tentar escrever um Cacau aplicativo da área de trabalho.Como se fosse uma aplicação web Java EE.Havia um monte de AbstractFooFactory e FooFactory e IFoo e Foo voando ao redor, quando tudo o que realmente precisava era de uma classe Foo e, possivelmente, um Fooable protocolo.

Parte de garantir que você não faça isso, é compreender verdadeiramente as diferenças na língua.Por exemplo, você não precisa do abstract factory e factory classes acima, uma vez que o objective-C métodos de classe são despachados tão dinamicamente como métodos de instância, e pode ser substituído em subclasses.

Certifique-se de que você indicar as A Depuração De Magia página.Esta deve ser sua primeira parada quando bater com a cabeça contra uma parede enquanto a tentar encontrar a origem de um Cacau erro.

Por exemplo, ele irá dizer-lhe como encontrar o método onde você primeiro memória alocada que mais tarde é que falhas (como durante a aplicação do término).

Classificar cadeias de caracteres como o usuário quer

Quando você classificar cadeias de caracteres para apresentar ao usuário, você não deve usar o simples compare: o método.Em vez disso, você deve sempre usar localizados métodos de comparação, tais como localizedCompare: ou localizedCaseInsensitiveCompare:.

Para mais detalhes, consulte A pesquisa, Comparação e Ordenação de Seqüências de caracteres.

Tente evitar o que eu tenho agora decidiu chamar Newbiecategoryaholism.Quando os recém-chegados ao objective-C descobrir categorias que eles, muitas vezes, ir porco selvagem, a adição útil pouco de categorias para cada classe na existência ("O que?eu posso adicionar um método para converter um número em algarismos romanos para NSNumber rock on!").

Não faça isso.

Seu código será mais portátil e mais fácil de entender com dezenas de pouco categoria de métodos polvilhado em cima de duas dezenas foundation classes.

A maior parte do tempo quando você realmente pensa que você precisa de uma categoria de método para ajudar a simplificar o código que você vai achar que você nunca acabar reutilizar o método.

Há outros perigos também, a menos que você é espaço de nomes de sua categoria de métodos (e que, além de absolutamente insano ddribin é?) há uma chance de que a Apple, ou um plugin, ou alguma outra coisa em execução no seu espaço de endereço vai definir também a mesma categoria de método com o mesmo nome, com um pouco diferente efeito colateral....

OK.Agora que você já foi avisado, ignorar o "não fazer parte".Mas o exercício de extrema contenção.

Resistir a subclassificação do mundo.Em Cacau, muito é feito por meio de delegação e usar a base de tempo de execução do que em outros frameworks é feito por meio de subclassificação.

Por exemplo, em Java você usar instâncias de anônimo *Listener subclasses muito e em .NET você use o seu EventArgs subclasses muito.Cacau, você não quer — o-alvo-ação é usada em vez disso.

Propriedades Declaradas

Geralmente você deve usar o objective-C 2.0 Declarada Propriedades de recurso para todas as suas propriedades.Se eles não são públicos, adicioná-los em uma classe de extensão.Usando propriedades declaradas faz o gerenciamento de memória semântica é imediatamente clara, e torna mais fácil para você verificar o seu método dealloc -- se agrupar a sua propriedade declarações juntos, você pode rapidamente digitalizar-las e comparar com a aplicação de seu método dealloc.

Você deve pensar muito antes de não marcar as propriedades como 'nonatomic'.Como O Objetivo Da Linguagem De Programação C Guia notas, as propriedades são atômica por padrão, e implicam uma sobrecarga considerável.Além disso, basta fazer todas as suas propriedades atômicas não faça o seu pedido thread-safe.Observe também, é claro, que se você não especificar 'nonatomic' e implementar os seus próprios métodos de acesso (ao invés de sintetizar), você deve implementá-los de maneira atômica.

Pensar sobre valores nil

Como esta pergunta notas, mensagens para nil são válidos em Objective-C.Enquanto este é, frequentemente, uma vantagem -- levando a mais limpo e mais natural de código -- o recurso pode, ocasionalmente, levar à peculiar e difícil de controlar-se para baixo bugs se você obter um nil valor quando você não espera ele.

Use NSAssert e amigos.Eu uso nil como objeto válido o tempo todo ...especialmente o envio de mensagens para nil é perfeitamente válida em Obj-C.No entanto, se eu realmente quiser certificar-se sobre o estado de uma variável, eu uso NSAssert e NSParameterAssert, o que ajuda a rastrear problemas facilmente.

Simples, mas muitas vezes esquecido.De acordo com a especificação:

Em geral, os métodos em diferentes classes que tem o mesmo seletor (o mesmo nome) também devem compartilhar o mesmo retorno e os tipos de argumento.Este restrição é imposta pelo compilador para permitir a vinculação dinâmica.

nesse caso, todos com o mesmo nome de seletores, mesmo se em diferentes classes de, serão consideradas como iguais devolução/tipos de argumento.Aqui está um exemplo simples.

@interface FooInt:NSObject{}
-(int) print;
@end

@implementation FooInt
-(int) print{
    return 5;
}
@end

@interface FooFloat:NSObject{}
-(float) print;
@end

@implementation FooFloat
-(float) print{
    return 3.3;
}
@end

int main (int argc, const char * argv[]) {

    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];    
    id f1=[[FooFloat alloc]init];
    //prints 0, runtime considers [f1 print] to return int, as f1's type is "id" and FooInt precedes FooBar
    NSLog(@"%f",[f1 print]);

    FooFloat* f2=[[FooFloat alloc]init];
    //prints 3.3 expectedly as the static type is FooFloat
    NSLog(@"%f",[f2 print]);

    [f1 release];
    [f2 release]
    [pool drain];

    return 0;
}   

Se você estiver usando o Leopard (Mac OS X 10.5) ou posterior, você pode usar os Instrumentos de aplicação para localizar e controlar vazamentos de memória.Após a construção de seu programa no Xcode, selecione Executar > Iniciar com a Ferramenta de Desempenho > Vazamentos.

Mesmo se o seu aplicativo não mostra qualquer vazamento, você pode manter os objetos em torno de muito tempo.Em Instrumentos, você pode usar o ObjectAlloc instrumento para isso.Selecione o ObjectAlloc instrumento em seus Instrumentos documento, e trazer o instrumento de detalhes (se já não estiver sendo mostrado) escolhendo Exibir > Detalhe (ele deve ter uma marca de seleção próxima a ele).Em "Alocação de Tempo" no ObjectAlloc detalhe, certifique-se de que você escolha o botão de opção ao lado de "Criado & Ainda Vivem".

Agora, sempre que você parar a gravação de seu aplicativo, selecionar o ObjectAlloc ferramenta irá mostrar-lhe como muitas referências existem para cada imóvel-objeto vivo em seu aplicativo, o " # " rede de coluna.Certifique-se de que você não apenas olhar para suas próprias classes, mas também as classes do seu NIB arquivos' objectos de nível superior.Por exemplo, se você não tem o windows na tela, e você verá referências a um ainda-vida NSWindow, você pode não ter lançou-o no seu código.

Limpar em dealloc.

Esta é uma das coisas mais fáceis de esquecer - esp.quando a codificação em 150mph.Sempre, sempre, sempre limpos, de seus atributos/variáveis de membro em dealloc.

Eu gosto de usar Objc 2 atributos - com a nova notação de ponto - de modo que este faz a limpeza indolor.Muitas vezes simples, como:

- (void)dealloc
{
    self.someAttribute = NULL;
    [super dealloc];
}

Este vai cuidar do lançamento para você e definir o atributo para um valor NULO (o que eu considero defensiva de programação - no caso de outro método mais para baixo no dealloc acessa a variável de membro novo - raro, mas poderia acontecer).

Com GC ligado em 10,5, isso não é necessário muito mais - mas você ainda pode precisar para limpar os outros recursos que você criar, você pode fazer isso no método finalize em vez disso.

Todos esses comentários são ótimos, mas eu estou realmente surpreso que ninguém mencionou Google objective-C Guia de Estilo que foi publicado há um tempo atrás.Eu acho que eles têm feito um trabalho minucioso.

Também, semi-tópico relacionado (com espaço para mais respostas!):

Que são aqueles pequenos Xcode dicas & truques que você deseja você sabia que há cerca de 2 anos?.

Não se esqueça de que NSWindowController e NSViewController vai liberar os objectos de nível superior do NIB arquivos que governam.

Se você carregar manualmente uma transferência bancária para o NIB arquivo, você é responsável para a liberação de que o NIB de nível superior de objetos quando você está feito com eles.

Um tanto óbvia para um iniciante usar:utilizar o Xcode auto-indentação recurso para o seu código.Mesmo se você for copiar/colar a partir de outra fonte, depois de ter colado o código, você pode selecionar todo o bloco de código, clique direito sobre ele e, em seguida, escolher a opção de re-travessão tudo dentro desse bloco.

O Xcode irá, na verdade, analisar por meio de seção e de travessão-lo com base em suportes, loops, etc.É muito mais eficiente do que pressionar a barra de espaço ou a tecla tab para cada linha.

Eu sei que eu negligenciei isso ao primeiro, ficando em Cacau programação.

Certifique-se de que você compreende o gerenciamento de memória responsabilidades em relação NIB arquivos.Você é responsável por liberar os objectos de nível superior em qualquer NIB arquivo que você carregar.Leia Apple Documentação sobre o assunto.

Ligue todos GCC avisos, em seguida, desligue aqueles que são regularmente causada pela Apple cabeçalhos para reduzir o ruído.

Também executar Clang análise estática com frequência;você pode habilitá-lo para todas as compilações através do "Executar Estático Analisador de" construir definição.

Escrever testes de unidade e executá-los com cada compilação.

Variáveis e propriedades

1/ Manutenção de seu cabeçalhos limpo, escondendo a implementação
Não incluir variáveis de instância em seu cabeçalho.Variáveis privadas colocar em classe continuação como propriedades.Variáveis públicas declarar como propriedades públicas em seu cabeçalho.Se ele deve ser apenas de leitura, declará-lo como somente leitura e substituí-lo como readwrite na classe continutation.Basicamente, eu não estou usando variáveis, apenas de propriedades.

2/ Dar as suas propriedades não-padrão de nome de variável, exemplo:


@synthesize property = property_;

Razão 1:Você vai pegar os erros causados por esquecimento "auto." ao atribuir a propriedade.Razão 2:A partir de minhas experiências, Vazamento de Analisador de Instrumentos tem problemas para detectar vazamento de propriedade com o nome padrão.

3/ Nunca usar reter ou liberar diretamente em propriedades (ou apenas em situações excepcionais).Em seu dealloc apenas a atribuir-lhes um nulo.Reter propriedades são destinadas a lidar reter/liberar por si mesmos.Você nunca sabe se um setter não é, por exemplo, a adição ou remoção de observadores.Você deve usar a variável diretamente apenas dentro de seu setter e getter.

Pontos de vista

1/ Colocar cada definição do modo de exibição em um xib, se você pode (a exceção é geralmente um conteúdo dinâmico e a camada de configurações).Ele economiza tempo (é mais fácil do que escrever código), é fácil alterar e mantém seu código limpo.

2/ não tente otimizar vistas diminuindo o número de pontos de vista.Não crie UIImageView em seu código em vez de xib só porque você deseja adicionar subviews para ele.Use UIImageView como plano de fundo em vez disso.O modo de exibição quadro pode lidar com centenas de pontos de vista sem problemas.

3/ IBOutlets não tem que ser sempre mantido (ou forte).Note que a maioria de seus IBOutlets são parte de sua visão de hierarquia e, portanto, implicitamente mantida.

4/ Lançamento de todos os IBOutlets em viewDidUnload

5/ Chamada viewDidUnload a partir do seu método dealloc.Ele não é chamado implicitamente.

Memória

1/ Autorelease objetos quando você criá-los.Muitos erros são causados por mover o lançamento de chamada em um if-else ramo ou depois de uma instrução de retorno.Release, em vez de autorelease deve ser usado somente em situações excepcionais - e.quando você está esperando por um runloop e você não deseja que o objeto seja autoreleased muito cedo.

2/ Mesmo se você estiver usando Authomatic Contagem de Referência, você precisa entender perfeitamente como manter-lançamento métodos de trabalho.Usando a reter-versão manualmente não é mais complicado do que ARCO, em ambos os casos, tem coisa sobre fugas e manter-ciclos.Considere o uso de manter-lançamento manualmente em projetos grandes ou complicadas hierarquias de objeto.

Comentários

1/ Faça o seu código autodocumented.Cada nome da variável e o nome do método deve dizer o que está fazendo.Se o código está escrito corretamente (você precisa de um monte de prática no presente), você não precisa de nenhum código de comentários (não o mesmo que os comentários de documentação).Algoritmos podem ser complicado, mas o código deve ser sempre simples.

2/ às Vezes, você vai precisar de um comentário.Geralmente para descrever um não aparente código de comportamento ou de hack.Se você sentir que você tem para escrever um comentário, primeiro tente reescrever o código para ser mais simples e sem a necessidade de comentários.

Recuo

1/ não aumentar recuo muito.A maioria de seu código de método deve ser recuado no nível de método.Blocos aninhados (se, por etc.) diminuir a legibilidade.Se você tem três blocos aninhados, você deve tentar colocar o interior de blocos em um método separado.Quatro ou mais blocos aninhados deve ser nunca usado.Se a maioria de seu código de método está dentro de um se negar a condição se, exemplo:


if (self) {
   //... long initialization code ...
}

return self;


if (!self) {
   return nil;
}

//... long initialization code ...

return self;

Entender o código C, principalmente estruturas em C

Note que o Obj-C é apenas uma luz OOP camada sobre linguagem C.Você deve entender como basic estruturas de código em C trabalho (enums, estruturas, matrizes, ponteiros, etc.).Exemplo:


view.frame = CGRectMake(view.frame.origin.x, view.frame.origin.y, view.frame.size.width, view.frame.size.height + 20);

é o mesmo que:


CGRect frame = view.frame;
frame.size.height += 20;
view.frame = frame;

E muitos mais

Manter os seus próprios padrões de codificação de documentos e atualizá-lo com frequência.Tente aprender com seus erros.Compreender por que um erro foi criada e tentar evitá-lo usando padrões de codificação.

Nossos padrões de codificação tem, atualmente, cerca de 20 páginas, uma mistura de Java, Padrões de Codificação, o Google Obj-C/C++ Padrões e a nossa própria addings.O código do documento, use o padrão de recuo, espaços em branco e linhas em branco no lugar certo, etc.

Ser mais funcional.

Objective-C é a linguagem orientada a objeto, mas de Cacau quadro funcional de estilo consciente, e é projetado estilo funcional, em muitos casos.

  1. Há uma separação da mutabilidade.Utilização imutável classes de principal, e mutável como objeto secundário.Por exemplo, o uso NSArray principalmente, e usar NSMutableArray somente quando você precisa.

  2. Lá é pura funções.Não para muitos, comprar muitas das APIs do framework são concebidos como pura função.Olhar para funções tais como CGRectMake() ou CGAffineTransformMake().Obviamente ponteiro forma parece mais eficiente.No entanto indireta argumento com ponteiros não pode oferecer e sem efeitos secundários.Projeto de estruturas puramente tanto quanto possível.Separado mesmo estado objetos.Utilização -copy em vez de -retain quando passar um valor para outro objeto.Porque o estado compartilhado pode influenciar a mutação de valor em outro objeto silenciosamente.Portanto, não pode ser sem efeitos colaterais.Se você tiver um valor externo do objeto, copiá-lo.Portanto, é importante, também, a concepção de estado compartilhado ao mínimo possível.

No entanto, não tenha medo de usar impuro funções também.

  1. Não é preguiça de avaliação.Ver algo como -[UIViewController view] propriedade.A vista não será criado quando o objeto é criado.Ele vai ser criado quando o chamador leitura view propriedade no primeiro tempo. UIImage não vai ser carregado até que ele realmente está sendo desenhado.Há muitos implementação como este projeto.Este tipo de modelos são muito úteis para a gestão de recursos, mas se você não sabe o conceito de avaliação lenta, não é fácil entender o comportamento deles.

  2. Não é o fechamento.Use C-blocos quanto possível.Isto irá simplificar a sua vida grandemente.Mas ler mais uma vez sobre o bloco de gerenciamento de memória antes de o utilizar.

  3. Não é semi-automático de GC.NSAutoreleasePool.Utilização -autorelease principal.Manual de utilização -retain/-release secundária, quando você realmente precisar.(ex:a otimização de memória explícita de exclusão do recurso)

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top