Um momento
Todos os artigos
C++ 13 min de leitura

O Que É a Linguagem de Programação Objective-C? Um Guia Simples da Linguagem Que Construiu o Mac e o iPhone

Um guia simples e sem jargões sobre o Objective-C, a linguagem por trás do Mac, dos primeiros apps de iPhone e até do primeiro navegador da web. Entenda as mensagens entre colchetes, como ele cuidava da memória e por que o Swift o substituiu.

nbkhope
Nesta página

Se você usou um app de iPhone entre 2008 e 2014, ele quase certamente foi escrito em Objective-C. A mesma linguagem movia os apps do Mac, os computadores NeXT de Steve Jobs e, por incrível que pareça, o primeiríssimo navegador da web.

Hoje a Apple recomenda a sua linguagem mais nova, o Swift, para os apps novos. Mas o Objective-C continua por toda parte por baixo dos panos, e as ideias dele moldaram o funcionamento do software da Apple até hoje. Este artigo explica, em linguagem simples, o que é o Objective-C, por que o código dele é cheio de colchetes e por que ele foi tão importante.

A receita: C mais mensagens

No começo dos anos 1980, dois programadores, Brad Cox e Tom Love, queriam construir software com peças reutilizáveis, do jeito que os aparelhos eletrônicos são montados com chips padronizados. Cox chamava a ideia de "CIs de software" (circuitos integrados de software).

Eles juntaram dois ingredientes:

A receita: C mais mensagens no estilo do Smalltalk. C: rápido e perto do hardware, de 1972. Smalltalk: objetos que conversam mandando mensagens, dos anos 1970. Juntos, formam o Objective-C: todo programa C continua valendo, mais objetos e mensagens entre colchetes, dos anos 1980. O Objective-C é um "superconjunto" do C: ele mantém a linguagem C inteira e acrescenta um pequeno grupo de símbolos novos para objetos. Isso facilitou a adoção pelos programadores de C
  • O C, a linguagem rápida e popular que rodava em quase tudo (veja O Que É a Linguagem de Programação C?).
  • O Smalltalk, uma linguagem do laboratório de pesquisa Xerox PARC construída em torno de objetos: "coisas" independentes que guardam os próprios dados e conversam entre si mandando mensagens.

O Objective-C é o C com as mensagens do Smalltalk por cima. Todo programa C válido também é um programa Objective-C válido, então os programadores de C podiam começar a usar objetos sem jogar fora nada do que sabiam. (O C++ seguiu outro caminho para o mesmo objetivo; veja O Que É a Linguagem de Programação C++?)

Colchetes: mandando uma mensagem

A característica mais reconhecível do Objective-C são os colchetes. Escrever [algo facaIsto] quer dizer "mande a mensagem facaIsto para algo". Veja uma mensagem com duas informações:

Anatomia de uma mensagem em Objective-C, escrita entre colchetes: saudador digaOlaPara:@"Maria" vezes:2. "saudador" é quem recebe a mensagem. "digaOlaPara:" é o nome da mensagem, parte 1, e @"Maria" é o que vai junto. "vezes:" é o nome da mensagem, parte 2, e 2 é o que vai junto. Parece quase uma frase: "saudador, diga olá para Maria, 2 vezes." A saída real é "Olá, Maria!" duas vezes. Os colchetes querem dizer "mande uma mensagem". Cada informação tem um rótulo na frente, então você sempre sabe o que cada valor significa, mesmo meses depois

Repare que cada valor vem com um rótulo: digaOlaPara: antes do nome e vezes: antes do número. Em muitas linguagens, a mesma chamada ficaria como saudador.digaOla("Maria", 2), e você teria que lembrar o que o 2 significa. No Objective-C, o código se explica sozinho, e é por isso que os nomes de métodos dele são famosos por serem longos e descritivos.

Veja o código por trás disso:

1@interface Saudador : NSObject
2- (void)digaOlaPara:(NSString *)nome vezes:(int)quantidade;
3@end
4
5@implementation Saudador
6- (void)digaOlaPara:(NSString *)nome vezes:(int)quantidade {
7    for (int rodada = 0; rodada < quantidade; rodada++) {
8        NSLog(@"Olá, %@!", nome);
9    }
10}
11@end

O Objective-C divide uma classe em duas partes: a @interface, que lista o que o objeto sabe fazer (como um cardápio), e a @implementation, que contém como ele faz (a cozinha). A arroba @ marca os acréscimos do Objective-C ao C, como @"Maria", que cria um objeto de texto, e o NSLog mostra uma linha (e ainda acrescenta a data e a hora na frente).

As mensagens são entregues enquanto o programa roda

No C, a chamada de uma função é ligada quando o programa é compilado. No Objective-C, a mensagem é procurada enquanto o programa roda: o objeto recebe a mensagem, confere a sua lista de métodos e executa o que combina. Isso torna o Objective-C muito dinâmico e traz algumas habilidades interessantes:

As mensagens são entregues enquanto o programa roda. Caso 1, o objeto conhece a mensagem: mandar digaOlaPara Maria vezes 2 mostra "Olá, Maria!", porque ele procura o método e o executa. Caso 2, dá para perguntar antes: perguntar ao saudador se ele responde à mensagem "voar" dá NO, não, porque dá para perguntar ao objeto o que ele entende. Caso 3, uma mensagem para ninguém: quando apelido é nil, perguntar o tamanho dele dá 0, porque nada acontece e a resposta é zero. Saídas reais. Como a decisão é tomada durante a execução, os programas em Objective-C são muito flexíveis. O outro lado: uma mensagem enviada para nil é ignorada em silêncio, o que evita travamentos mas pode esconder erros
  • Dá para perguntar a um objeto o que ele entende antes de mandar uma mensagem, com respondsToSelector:. O nosso saudador respondeu NO (não) quando perguntamos se ele sabe voar.
  • Mensagens para ninguém não fazem mal. No Objective-C, o "nada" se chama nil. Mandar uma mensagem para nil não trava: simplesmente nada acontece e a resposta é zero. Isso deixava os apps mais tolerantes, mas também podia esconder erros, um dos problemas que os opcionais do Swift foram criados para resolver.
  • Dá para ensinar truques novos a objetos que já existem. Um recurso chamado categorias permite acrescentar métodos até às classes prontas da Apple:
1@interface NSString (Gritando)
2- (NSString *)gritar;
3@end
4
5@implementation NSString (Gritando)
6- (NSString *)gritar {
7    return [[self uppercaseString] stringByAppendingString:@"!"];
8}
9@end

Depois disso, todo texto do app entende gritar: [@"olá" gritar] dá OLÁ!. Repare nos colchetes aninhados: [[self uppercaseString] stringByAppendingString:@"!"] primeiro deixa o texto em maiúsculas e depois acrescenta um ponto de exclamação.

Um carrinho, do jeito clássico

Veja uma classe que descreve um carro, escrita no estilo clássico que os programadores de Objective-C usaram por anos:

1@interface Carro : NSObject {
2    NSString *cor;
3    int velocidade;
4}
5@property (copy) NSString *cor;
6@property int velocidade;
7- (void)acelerar;
8@end
9
10@implementation Carro
11@synthesize cor, velocidade;
12
13- (void)acelerar {
14    self.velocidade = self.velocidade + 10;
15}
16@end

E usando a classe:

1Carro *meuCarro = [[Carro alloc] init];
2meuCarro.cor = @"vermelho";
3[meuCarro acelerar];
4[meuCarro acelerar];
5NSLog(@"O meu carro %@ anda a %d km/h", meuCarro.cor, meuCarro.velocidade);
6[meuCarro release];

Isso mostra O meu carro vermelho anda a 20 km/h. O [[Carro alloc] init] são duas mensagens numa só: alloc reserva memória para um carro novo, e init o prepara. O asterisco em Carro *meuCarro vem do C e quer dizer "um ponteiro", o endereço da memória onde o carro mora. E aquela última linha, [meuCarro release], nos leva a uma das maiores histórias do Objective-C.

Memória: contando fichas de biblioteca

Todo objeto ocupa memória, e o programa precisa devolver essa memória quando ninguém mais precisa do objeto. O Objective-C acompanha isso com a contagem de referências, que funciona como fichas de biblioteca para um livro:

Contagem de referências, como fichas de biblioteca para um livro. Criado com alloc e init: retainCount é 1, um dono. Depois de retain: 2, outra pessoa também quer. Depois de release: 1, um dono terminou. Depois de outro release: 0, ninguém precisa, e ele é liberado. Contagens reais mostradas pelo programa. Antes de 2011, os programadores escreviam cada retain e release à mão; um release esquecido vazava memória, um a mais derrubava o app. Então o ARC passou a escrevê-los automaticamente
  • alloc cria o objeto com a contagem em 1.
  • retain diz "eu também preciso disto", somando 1.
  • release diz "já terminei", subtraindo 1.
  • Quando a contagem chega a 0, o objeto é liberado.

Por anos, os programadores escreveram cada retain e release à mão. Esqueça um release, e o app vazava memória aos poucos; coloque um a mais, e ele travava. Em 2011, a Apple lançou a Contagem Automática de Referências (ARC): o compilador escreve essas mensagens por você. Foi um enorme alívio, e o Swift usa a mesma ideia até hoje.

Ele é rápido?

O Objective-C é C por baixo, então as partes em C rodam a toda velocidade. As mensagens flexíveis custam um pouco a mais, porque o programa precisa procurar qual método executar a cada vez. Medimos isso:

A flexibilidade tem um preço pequeno. Tempo de 100 milhões de chamadas que somam 1 a um número, medido para este artigo com clang 18 e o runtime GNU de Objective-C no Linux, como a mediana de 5 execuções. Chamada de função C: 0,046 segundo, cerca de 0,5 bilionésimo de segundo por chamada. Mensagem Objective-C: 0,500 segundo, cerca de 5 bilionésimos de segundo por chamada. Aqui, uma mensagem é cerca de 10 vezes mais lenta que uma chamada de função simples, porque o runtime precisa procurar qual método executar. Mas 200 milhões de mensagens por segundo ainda é muito para um app, e o runtime da própria Apple é ainda mais rápido

Uma mensagem levou cerca de 10 vezes mais tempo que uma chamada de função C simples no nosso teste, mas isso ainda dá umas 200 milhões de mensagens por segundo. O sistema de mensagens da própria Apple é muito otimizado e mais rápido que a versão livre que testamos, e quando uma tarefa precisa de cada gota de velocidade, os programadores de Objective-C podem simplesmente escrever aquela parte em C puro.

Da NeXT ao iPhone

A história do Objective-C está muito ligada a Steve Jobs:

  • Depois de sair da Apple em 1985, Jobs fundou a NeXT, que tornou o Objective-C a principal linguagem dos seus computadores em 1988.
  • Num computador NeXT, em 1990, Tim Berners-Lee escreveu o WorldWideWeb, o primeiro navegador da web, em Objective-C. As ferramentas usadas para construir as fases do famoso jogo Doom também foram escritas em máquinas NeXT, em Objective-C.
  • Em 1997, a Apple comprou a NeXT, e Jobs voltou. O software da NeXT virou a base do Mac OS X (2001) e do seu kit para apps, o Cocoa.
  • Em 2008, a Apple abriu o iPhone para desenvolvedores de fora e lançou a App Store. Para criar um app de iPhone, usava-se Objective-C, e de repente milhões de pessoas quiseram aprendê-lo. Ele foi eleito a "Linguagem de Programação do Ano" pelo índice de popularidade TIOBE em 2011 e 2012.
Onde o Objective-C vive hoje. A base da Apple: boa parte do código dentro do iOS e do macOS é Objective-C. Apps antigos: apps grandes e antigos ainda têm muito dele. Junto com o Swift: as duas linguagens convivem no mesmo app. O primeiro navegador: o WorldWideWeb, de 1990, foi escrito num NeXT em Objective-C. GNUstep: uma versão livre das bibliotecas da Apple para Linux. Vagas de manutenção: empresas precisam de quem saiba lê-lo. Os apps novos da Apple são escritos principalmente em Swift, mas o Objective-C está longe de sumir: ele é a base sobre a qual boa parte do mundo do Swift foi construída

Por que o Swift o substituiu

Em 2014, a Apple apresentou o Swift (veja O Que É a Linguagem de Programação Swift?). O Objective-C tinha servido bem por 30 anos, mas carregava os riscos do C e mostrava a idade:

  • Muitos símbolos. Colchetes, arrobas, asteriscos e dois arquivos por classe (um arquivo .h para a interface e um .m para a implementação) deixavam o código longo e intimidador para iniciantes.
  • Os perigos de memória do C. Por ser C por baixo, o Objective-C herda os erros arriscados de memória do C.
  • O nil silencioso. Mensagens para nil que não faziam nada podiam esconder erros difíceis de encontrar.
  • Difícil de modernizar. Corrigir esses problemas sem quebrar milhões de apps existentes era quase impossível, então a Apple começou do zero.

O Swift foi pensado para trabalhar lado a lado com o Objective-C, para que as empresas não precisassem reescrever os seus apps da noite para o dia. Muitos apps de hoje misturam as duas linguagens, e boa parte do código dentro dos próprios sistemas da Apple ainda é Objective-C.

Uma breve história

Uma breve história do Objective-C, numa linha do tempo. 1972: nasce o C no Bell Labs, e começa o trabalho no Smalltalk. 1984: Brad Cox e Tom Love criam o Objective-C. 1988: a NeXT o torna a sua linguagem principal. 1990: o primeiro navegador da web é feito com ele. 1997: a Apple compra a NeXT. 2001: Mac OS X e Cocoa. 2008: a App Store é aberta. 2011: o ARC automatiza a memória. 2014: chega o Swift

Vale a pena aprender Objective-C?

  • Bons motivos: você vai trabalhar num app de iPhone ou de Mac mais antigo, tem curiosidade sobre como os sistemas da Apple são construídos ou quer entender de onde vieram muitas ideias do Swift. Saber ler Objective-C é uma habilidade valiosa para desenvolvedores Apple, mesmo que escrevam Swift todos os dias.
  • Bom saber: para apps novos de iPhone e Mac, comece pelo Swift. Se quiser experimentar o Objective-C, o app gratuito Xcode, da Apple, no Mac, tem suporte completo, e no Linux ou no Windows você pode usar o clang com o GNUstep, como fizemos neste artigo.

Um pequeno glossário

  • Objective-C: uma linguagem de programação que acrescenta objetos e mensagens no estilo do Smalltalk ao C, criada no começo dos anos 1980.
  • Superconjunto: uma linguagem que contém outra linguagem inteira, mais recursos extras.
  • Mensagem: um pedido enviado a um objeto, escrito entre colchetes, como [saudador digaOlaPara:@"Maria" vezes:2].
  • @interface / @implementation: as duas metades de uma classe: o que ela sabe fazer e como faz.
  • nil: a palavra do Objective-C para "nenhum objeto". Mensagens enviadas para ele não fazem nada.
  • Categoria: um jeito de acrescentar métodos novos a uma classe que já existe, mesmo que não tenha sido você quem a escreveu.
  • Contagem de referências: contar quantas partes do programa precisam de um objeto e liberá-lo quando a conta chega a zero.
  • retain / release: as mensagens que somam e subtraem dessa contagem.
  • ARC: Contagem Automática de Referências, que escreve os retain e release por você (desde 2011).
  • NeXTSTEP: o sistema operacional dos computadores NeXT, origem do "NS" em nomes como NSString.
  • Cocoa: o kit da Apple para criar apps de Mac (o irmão dele para iPhone se chama Cocoa Touch).

Conclusão

O Objective-C foi uma mistura esperta: a velocidade do C com as mensagens amigáveis e flexíveis do Smalltalk, escritas entre colchetes que parecem quase frases. Ele carregou os computadores NeXT de Steve Jobs, o primeiro navegador da web, o Mac e a primeira onda de apps de iPhone, e ensinou uma geração inteira de desenvolvedores como o software da Apple funciona.

O Swift assumiu os apps novos, mas o Objective-C não desapareceu. Ele continua rodando discretamente dentro dos aparelhos no nosso bolso, e cada NS que você vê no código da Apple é um pequeno lembrete de onde tudo começou.

Obrigado pela leitura!

Conhece alguém que vai gostar? Mande para essa pessoa.

Mais artigos

Read next

Comentários

Be kind and specific. Comments with links from new accounts appear after a moderator reviews them.