« Voltar
em .net core c# roslyn

C#: imitação ou inovação? - parte 2.

Na parte 1, vimos como o C# evoluiu desde seu nascimento em 2000 até o lançamento da versão 3.0 em 2008.

(Este post é uma tradução, você pode conferir o original aqui).

C# não introduziu síntaxe ou funcionalidades revolucionárias. Ao invés disso, imitou a maioria de suas funcionalidades do C++, Java, Scala e várias outras linguagens. Como já é de costume da Microsoft, as muitas das coisas que foram imitadas no C# na verdade ficaram melhores que as originais. O melhor exemplo disso são os Generics: apesar de já existirem no Java, a implementação do C# ficou muito melhor.

Mas C# não é só uma série de imitaçãoes. A versão 3.0 adicionou algumas funcionalidades incríveis e inovadoras como LINQ, tipost anonimos e auto implemented properties. Essas funcionalidades ajudaram a aumentar demais a popularidade da linguagem, especialmente em contraste com o Java, que não lançou grandes funcionalidades na linguagem de 2004 a 2008.

Por volta de 2008, C# já havia ganho bastante popularidade e era a sétima linguagem mais popular do mundo de acordo com o TIOBE (depois de Java, C, C++, PHP, Perl e Python). Conseguir essa popularidade em 8 anos de existência é um fato novável.

Neste artigo, vamos ver o que aconteceu com a linguagem a partir de 2008. Veremos que muitos competidores apareceram e ver onde C# se tornou ainda mais popular até 2015.

C# 4.0

Em Abril de 2010, o C# 4.0 foi lançado junto com o .NET 4.0, Visual Studio 2010 e muitas novas funcionalidades.

Dynamic binding – C# 4.0 introduziu a keyword dinamyc. Quando um tipo é definido como dynamic, o compilador ignora a checagem por tipo e essa verificação é feita durante a execução. A motivação aqui é a interoperabilidade com objetos COM.

Uma funcionalidade muito similar já existia no Visual Basic. Você pode usar um objeto VB com a opção Strict desligada e vai conseguir o mesmo resultado. Mas o funcionamento não é o mesmo. No VB, você precisa especificar essa opção por assembly ou por arquivo. Em C#, dinamyc é especificada por variável. Ainda assim, teremos que dizer que é uma imitação.

Parâmetros opcionais/nomeados – com parâmetros Named, podemos passar parÂmetros em qualquer ordem especificando seu nome.

PrintOrderDetails(orderNum: 31, productName: "Red Mug", sellerName: "Gift Shop");  

E com parâmetros opcionais podemos omitir alguns se quisermos, contanto que especifiquemos um valor padrão:

public void ExampleMethod(int required, string optionalstr = "default string", int optionalint = 10)  
...
ExampleMethod(12);  

Como você já deve ter imaginado, essas funcionalidades já existiam em outras linguagens. Como por exemplo, no Python 1.4.
E aqui há um artigo legal descrevendo como parâmetros opcionais funcional em 58 linguagens diferentes. Imitação.

Covariância e contravariância genérica – com covariância, podemos atribuir MinhaClasse a MinhaClasse. Por exemplo:

IEnumerable<Derived> d = new List<Derived>();  
IEnumerable<Base> b = d;  

Uma variável deste tipo pode ser usada tipo de retorno de métodos.

Contravariância é um pouco mais complexo. Um exemplo da documentação da Microsoft:

Action<Base> b = (target) => { Console.WriteLine(target.GetType().Name); };  
Action<Derived> d = b;  
d(new Derived());  

Covariância e contravariancia são suportados no C# para serem usados em delegates, arrays e generics. No Java por exemplo, arrays são covariantes mas generics não. Scala suporta covariância e contravariância, mas o suporte parede ter sido adicionado depois do C#. Pesquisei em outras linguagens com generics como C++ e Delphi, mas nenhuma delas suporta covariância.

Foi difícil pesquisar, mas parece que o C# foi a primeira linguagem a suportar covariância em tipos genéricos de delegates. Inovação.

Popularidade do C# até agora

É difícil dizer com certeza, mas aparentemente C# se tornou a terceira ou quarta linguagem de programação mais usada no mundo em 2012. O TIOBE mostra que entre 2010 e 2012 a linguagem ficou entre quarto e quinto lugar depois de Java, C, C++ e PHP, aparecendo em terceiro lugar em alguns momentos.

Outro índice de popularidade, o PYPL, coroou C# como linguagem do ano em 2012, colocando C# e C++ juntinhos na terceira posição de linguagens mais populares, depois de Java e PHP.

Ambos os índices se baseiam na frequência em que a linguagem é buscad no Google ou Yahoo para determinar a popularidade, o que eu acho que pode ser um fator enganoso.

Por exemplo: algumas áreas, como agências militares, bloqueiam o acesso à internet para desenvolvedores. Talvez essas áreas façam com que o Java cresça indiretamente? Nós não temos como saber. O índice PYPL adiciona a palavra-chave "tutorial" em suas queries, o que pode adicionar uma popularidade falsa a novas linguagens e em ascensão. Mais uma vez, nós simplesmente não sabemos.

De qualquer forma, é claro que C# foi extremamente aceita e amplamente utilizada entre 2010 e 2012. Em 2012, atingiu seu pico de popularidade. Vamos ver o que vem a seguir.

C# 5.0

Em Agosto de 2012, C# 5 e .NET 4.5 foram lançados com uma nova incrível funcionalidade.

In August 2012, C# 5 and .NET 4.5 were released with a new incredible feature.

Membros assíncronos – a funcionalidade async/await revolucionou a programação assíncrona. Se tornou possível a escrita de métodos assíncronoes em estilo síncrono.

using (var client = new HttpClient())  
{
    var response = 
        await client.GetAsync(url, HttpCompletionOption.ResponseContentRead);
    return await response.Content.ReadAsStringAsync();
}

Não é mais necessário gerenciar Tasks e callbacks malucos. Esse modelo se tornou tão popular que muitas linguagens começaram a imitar. Hoje em dia podemos usar async/await em Javascript, Python, Kotlin e outras linguagens.

Então, async/await é uma inovação?

Pra minha surpresa, descobri que não. Essa funcionalidade é na verdade inspirada em fluxos assíncronos do F#, que foi lançado 3 anos antes. Há algumas diferenças na síntaxe, mas é muito parecido. Olha esse código F#:

let fetchAsync(name, url:string) =  
    async {
        try
            let uri = new System.Uri(url)
            let webClient = new WebClient()
            let! html = webClient.AsyncDownloadString(uri)
            printfn "Read %d characters for %s" html.Length name
        with
            | ex -> printfn "%s" (ex.Message);
    }

Portanto, imitação.

Caller info attributes – uma funcionalidade legal quando trabalhamos com frameworks que usam bastante o recurso de binding, como o WPF:

private void OnPropertyChanged([CallerMemberName] string propertyName = null)  
{
    PropertyChangedEventHandler handler = PropertyChanged;
    if (handler != null)
    {
        handler(this, new PropertyChangedEventArgs(propertyName));
    }
}

Faz o código parecer melhor e previne que você fique escrevendo reflection. Por mais que tenha pesquisado, não encontrei nada parecido em outra linguagem. Isso faz com que esse recurso seja uma *inovação * do C#.

C# 6.0

Em 2015 a versão 6.0 foi lançada com várias pequenas (porém interessantes) funcionalidades.

Imports estáticos – açúcar sintático que permite a utilização de métodos estáticos sem a necessidade de expecificar o nome da classe. Por exemplo:

using System;  
using static System.Math;

public class Circle  
{
   public double Radius { get; set; }

   public double Circumference
   {
      get { return 2 * Radius * PI; }      
   }
}

Posso chamar apenas PI ao invés de Math.PI.

Essa funcionalidade já existia nos módulos F#. Módulos F# são implementados como classes estáticas da CLR e podem ser usadas dessa maneira:

module Math = 

    let add x y  = x + y

//in another file
module Mod =  
    open Math

    let addFive x = add 5 x

Tenho certeza que há mais exemplos em outras linguagens, mas vamos parar por aqui. Imitação.

Exception filters – essa funcionalidade permitiu a inclusão de condições em um bloco catch, assim:

try  
{
    Foo.DoSomethingThatMightFail(null);
}
catch (MyException ex) when (ex.Code == 42)  
{
    Console.WriteLine("Error 42 occurred");
}

Essa já existia no VB.NET há algumas versões. Imitação.

Inicializadores de propriedades – Essa funcionalidade chegou bem atrasada na minha opinião.

    public bool Enabled { get; set; } = true;

Inicializadores de propriedades já existiam antes no F# 3.0, que foi lançado 3 anos antes:

memberval X = 0 with get, set  

Imitação.

Expression bodied members – Outro açucar sintático:

public string GetFullName() => FirstName + " " + LastName;  
public string FullNameProperty => FirstName + " " + LastName;  

Não posso chamr essa de inovação ou imitação já que é apenas uma síntaxe diferente para funcionalidades que já existiam.

Null propagator – uma ótima funcionalidade, que nos ajuda a não ter que ficar escrevendo milhões de verificações pra ver se algo é nulo:

var minPrice = product?.PriceBreaks?[0]?.Price;  
var result = myDelegate?.Invoke("someArgument");  

A linguagem Groovy já havia implementado isso alguns anos antes (2007). Imitação.

Interpolação de strings – uma síntaxe conveniente para misturar strings com expressões:

Console.WriteLine($"Hello, {name}! Today is {date.DayOfWeek}, it's {date:HH:mm} now.");  

Mais uma vez, Groovy chegou primeiro. Essa funcionalidade também já existie em Ruby, mas não sei quem fez primeiro. Mas sei que não foi o C#. Imitação.
Operador nameof – permite analisar o nome de uma variável, tipo ou membro em tempo de compilação.

void foo(int number) {  
    Console.WriteLine(nameof(foo));//-> "foo"
    Console.WriteLine(nameof(number));//-> "number"
}

Inovação.

Index initializers – qualquer classe que implemente um indexer (como Dictionary) pode ser inicializado dessa forma:

private Dictionary<int, string> webErrors = new Dictionary<int, string>  
{
    [404] = "Page not Found",
    [302] = "Page moved, but left a forwarding address.",
    [500] = "The web server can't come out to play today."
};

Não é uma funcionalidade revolucionária, mas bem conveniente. A inicialização de objetos no Javascript é bem parecida:

     var obj = {
      foo: 'some',
      bar: 32, 
      baz: {}
    };

Imitação.

Await em blocos catch/finally – tornou possível usar async/await em blocos catch e finally. Essa não é é uma funcionalidade que não vou marcar como imitação nem inovação, já que é algo que surtiu como uma solução para a funcionalidade original.

Valores default para propriedades somente leitura – transforma propriedades em um tipo de atributo somente leitura que será visto como uma propriedade de fora da classe:

public string Name { get; } = "Michael";  

Uma funcionalidade não tão inovadora, já que pode ser substituida em qualquer outra linguagem por um atributo somente leitura ou constante.

A essa altura, parece que o time C # está sem grandes idéias e decidem se concentrar em melhorar a síntaxe da linguagem. Isso não é verdade, como veremos na parte 3 da série. A verdade é que o novo compilador Roslyn foi desenvolvido junto com o C # 6. Roslyn permitiu que a equipe do C # incluísse com facilidade esses pequenos recursos de açúcar sintático na linguagem, o que era mais difícil de ser feito com o antigo compilador.

O que estava acontecendo no mundo quando o C # 6 foi lançado

O ano é 2015, e muito aconteceu nos últimos anos. O desenvolvimento mobile explodiu desde 2009 e, ao lado dele, o Objective-C, tornando-se a 3ª linguagem mais popular em 2015, de acordo com o índice TIOBE (depois de Java e C).

O desenvolvimento web é enorme e continua crescendo. Em 2015, a maioria dos desenvolvedores são desenvolvedores web de acordo com a pesquisa do Stack Overflow. Novas linguagens de programação agora assumem a liderança no topo. Especialmente JavaScript. Mas também, Ruby e Python, que ganham popularidade crescente.

C # fez várias tentativas de conquistar desenvolvedores web. Tentativas que incluem o Silverlight, o ASP.NET Web Forms, o MVC e Web API. A Microsoft era capaz de conquistar muito do mercado corporativo, mas perde a comunidade de startups.

Se tiver curiosidade sobre a classificação de popularidade em 2015, os resultados variam muito, dependendo de quem você está perguntando. O índice TIOBE de 2015 diz que C é a linguagem mais popular, seguida por Java, Objective-C, C ++, C # e PHP.
Por outro lado, pesquisa do Stack Overflow coloca o JavaScript como a linguagem mais usada, seguida por Java, C #, PHP, Python, C ++, C, Ruby e Objective-C, nessa ordem.

Conclusão

Cobrimos cerca de 5 anos de progresso do C# neste artigo, de 2010 a C# 6.0 em 2015. A linguagem certamente se distanciou das raízes iniciais inspiradas em Java e Delphi. As versões 4.0, 5.0 e 6.0 foram muito inspiradas por F# e Visual Basic .NET.

Outro grande destaque é a criação de Roslyn. O novo compilador agora atua como um serviço e fornece uma API, com a capacidade de adicionar analisadores de código personalizados. Talvez mais importante, o compilador antigo foi escrito em C# (suponho que com menos problemas), o que permite que a equipe de C # avance mais rápido. Um fato que já vimos com o C# 6.0 e continuaremos a ver em versões futuras.

Na parte 3, veremos as últimas versões do C# e o que esperar nas versões futuras.


Quer ficar em dia com os meus posts e novidades?
Participe do inscreva na minha newsletter, me segue no Twitter e na minha página!

comments powered by Disqus