Se você quer descobrir alguma coisa, aprenda com os melhores. Hoje, minhas perguntas são respondidas pelo deus Corutin e simultaneidade, Roma
elizarov Elizarov. Conversamos não apenas sobre Kotlin, como você pode pensar, mas também sobre vários tópicos relacionados:
- Golang e goroutines;
- JavaScript e sua aplicabilidade para projetos sérios;
- Java e tear de projeto;
- programação de olimpíadas no Kotlin;
- como aprender a programar corretamente;
- e outras coisas interessantes.

Kotlin - muito bem!
Oi Primeiro, algumas palavras sobre você. Você faz Kotlin há muito tempo?
Eu tenho uma longa história com Kotlin. Em 2010, Kotlin começou como um projeto no JetBrains, onde eu não estava trabalhando na época. Mas Max Shafirov (ele estava envolvido em Kotlin e foi um dos iniciadores desse movimento dentro do JetBrains) me convidou para me tornar um especialista externo e analisar o design e o comentário. Inicialmente, a linguagem foi projetada para resolver seus problemas, porque o JetBrains possui sua própria grande base de código Java, com problemas compreensíveis que estão constantemente presentes no código, e eu queria criar a linguagem para mim, para que meu código pudesse ser escrito de forma mais agradável, eficiente e com menos erros. Basta realizar a modernização. Naturalmente, isso rapidamente se transformou na idéia de que, uma vez que temos esses problemas, significa que outros têm esses problemas e precisavam de confirmação de outras pessoas de que estavam seguindo o caminho certo.
Fui convidado como especialista para analisar e comparar o que está acontecendo com o que é necessário. Sobre a nulidade - insisti que isso fosse feito, porque naquele momento era óbvio para mim que se você escreve em Java, há muitos problemas, mas a nulidade é o principal problema que você encontra constantemente.
Não participei do trabalho da equipe, apenas olhei periodicamente, participei de competições na Kotlin (Copa Kotlin). Eu competi a vida toda, mas mesmo assim não participei ativamente. Por exemplo, eu não teria chegado à final de competições como a Copa do Hacker do Facebook, o formulário não é o mesmo porque eu não participo mais das competições de forma contínua. E participei da Copa Kotlin e, como não atraiu um grande público, cheguei facilmente à final.
Naquela época (2012-2013), Kotlin era uma visão triste do ponto de vista da sintonia, porque tudo diminuiu a velocidade ali. Desde então, a equipe fez um ótimo trabalho. Entrei para a equipe há dois anos, logo após o lançamento do 1.0 e antes do Google reconhecer oficialmente o idioma. Como equipe, assumi todos os tipos de assincronia e corotinas, só porque descobri que tinha a experiência certa, trabalhei muito em vários sistemas corporativos de grande porte na DevExperts, e há muita assincronia e comunicação. Portanto, imaginei bem as áreas problemáticas - o que precisa ser consertado e o que machuca as pessoas. Isso caiu muito bem nas necessidades de Kotlin, porque machuca não apenas conosco. Dói a todos. Até a JVM iniciou o Projeto Loom, o que, por assim dizer, sugere que dói a todos. Eu ainda lido com bibliotecas Kotlin, e nosso foco principal é em todos os tipos de aplicativos conectados e assincronia.
Ou seja, você está envolvido principalmente em bibliotecas, não em um compilador, e é tudo por isso?
Não, eu estou fazendo o compilador na medida em que. Eu me comunico com os caras e nossa equipe de bibliotecas pré-imprime tudo o que eles fazem no compilador. Também somos clientes, criamos muitas missões de recursos quando nos deparamos com algumas falhas, e somos testadores da primeira linha de tudo o que é lançado.
Acontece que, se você entrar no YouTrack, filtrar por você, poderá encontrar muitas coisas interessantes.
Sim, você pode encontrar um monte de todos os tipos de tarefas, porque sempre encontro alguma coisa.
Você mencionou o projeto tear. Foi feito pelo cara que fez o Quasar. Pelo lado, parece muito engraçado, eu só queria escrever um artigo sobre Habra sobre Loom. Você pode me dizer algo sobre ele?
Eu vi uma apresentação, a ideia é clara. Todo mundo precisa de corotinas e programação assíncrona. Por exemplo, no passado na JPoint, os caras do Alibaba contaram como invadiram a JVM e estragaram o ponto de acesso, apenas lançando um patch que eles nem escreveram, mas alguns caras antes deles. Mais tarde eles serraram sob si mesmos. Ótimo relatório. Eu recomendo.
Você recomenda fazer isso?
Por isso, é necessário fazer nas empresas. Cada grande empresa, acima de um determinado tamanho, quando vários milhares de pessoas começam a trabalhar para você (e para alguém menos), mantém seu hack do OpenJDK. E, é claro, se você tem casos de usuários críticos para os negócios, por que não hackear algo para si mesmo, não vejo nenhum grande problema nisso. Não que eu recomende, mas preciso. Se não houver threads leves no HotSpot, o que devo fazer? Isso, de fato, sugere que as pessoas precisam do que está maduro. E o feedback que recebemos sobre as rotinas também diz que sim, está atrasado, as pessoas precisam de fluxos leves, as pessoas precisam de uma carroça de yuzkeys para fluxos leves. O fato de que eles deviam, de alguma forma, ser suportados no JDK está muito atrasado e, nesse sentido, não tenho dúvidas de que, quando o Loom chegar à produção mais cedo ou mais tarde, ele estará em demanda. Há pessoas que precisam disso. Há pessoas que, mesmo por causa deste patch HotSpot.
Eu vi um problema comum - você tem algum tipo de servidor web, muitas pessoas estão batendo nele e ele começa a bloquear os threads.
Este é um problema bastante comum. E o servidor da web, o servidor de aplicativos e o back-end. Se você observar a mesma apresentação do Alibaba, por que isso era necessário, eles não têm um servidor da Web, uma arquitetura corporativa clássica, todos os tipos de serviços escritos no back-end Java, esses serviços estão sob carga. Trabalhei com o DevExperts da mesma maneira: os serviços estão sobrecarregados, você recebe solicitações que não processa, afinal - no mundo moderno, você tem tudo conectado. E você não processa essa solicitação sozinho, mas liga para 100500 todos os outros serviços e espera que eles respondam. E se esses serviços forem lentos, você terá muitos threads aguardando. Você não pode se dar ao luxo de ter dezenas de milhares desses fluxos de espera. E é apenas por causa de algumas bobagens que você obtém o seguinte: um serviço que você usa fica mais lento e muitos threads estão em espera. E agora este é um problema muito grande.
Uma das razões pelas quais as pessoas migram para o Go maciçamente não é porque a linguagem é boa, mas porque há fluxos leves e não há esse problema: goroutines podem esperar e não custam nada. No mesmo Alibaba, a solução que eles implementaram é geralmente burra de todas as estúpidas. Eles não são muito leves, no sentido em que alocam uma grande pilha de 2 megabytes para cada rotina, invadindo o HotSpot para que essas pilhas possam ser trocadas. Eles salvam o fluxo físico, mas não as pilhas. E para eles, a solução funciona - a propósito, é muito simples, eles têm um patch do HotSpot, pelo que entendi, não muito grande. Os caras do Loom começaram algo mais global. Eles decidiram economizar não apenas em fluxos físicos, mas também na pilha, para não gastar 2 megabytes por fluxo. No protótipo, a pilha atual passa pelo HotSpot e é copiada em uma pequena estrutura de quadril. E eles podem reutilizar essa pilha física para outros fins.
Mas existe um truque astuto: quando você volta ao desempenho, eles copiam não tudo, mas apenas o topo.
Sim, existem carros de hacks e otimizações. O que acaba resultando disso é muito difícil de dizer. Como no exemplo da abordagem de cópia, surge o seguinte problema: o que fazer com chamadas nativas? De dentro da chamada nativa, você não pode mais copiar a pilha da chamada nativa. A abordagem do Alibaba não tem esse problema. Nativo, não nativo - qual é a diferença, você simplesmente desengatou essa pilha e a deixou sozinha, pegou outra pilha, tudo funciona. E é muito cedo para dizer se será bem-sucedido ou não; às vezes, você pode viver com essa pilha nativa; às vezes, não; neste momento, é muito cedo para dizer. Por exemplo, como é implementado no Go é um mecanismo completamente diferente. Enquanto você executa o código gosh, pequenas pilhas gosh são usadas. Assim, quando um tempo de execução gosh chama uma função, ele analisa quanto a pilha precisa. Se a pilha atual não for suficiente, ela se realoca - aumenta o tamanho da pilha selecionada. Se, portanto, você fizer uma chamada nativa, eles já pegarão uma grande pilha nativa de um determinado pool e a usarão.
E para o código gosh também?
Isso não importa. Eles simplesmente podem mudar para uma pilha nativa grande se você precisar chamar alguma função externa, para a qual não está claro quanto é necessária uma pilha. E quando você executa o código gosh, você sabe quantas pilhas são necessárias, para que possamos executá-lo em uma pequena pilha. Esta é uma abordagem completamente diferente. Não copie, mas execute imediatamente em uma pequena pilha. De fato, não há muita diferença entre essas abordagens até você adormecer ocasionalmente.
Somos constantemente perguntados: “O que é mais rápido? O que é adequado? Como você faz isso nas corotinas? ” Nós nas corotinas não hackeamos a JVM. Nosso objetivo é que isso funcione sob a JVM normal. E para o Android funcionar também. Existe sua própria arte, que também não sabe nada sobre corotinas. E assim, naturalmente, temos que gerar bytes com canetas, o que faz algo muito semelhante a copiar a pilha que o Loom faz, apenas fazemos no bytecode. Tomamos quando já é tarde. Pegue uma pilha, relaxe e copie para o quadril. Não estamos em um tempo de execução que faria isso por nós, geramos um bytecode que faz isso. Ele preserva e restaura o estado da corotina. Devido ao fato de não executarmos o tempo de execução, é claro, temos mais sobrecarga disso. Em tempo de execução, você pode fazer tudo mais rápido. Por outro lado, se você usar corotinas para programação assíncrona, precisará adormecer, se tiver que esperar por uma resposta de algum serviço e enviar uma solicitação para algum serviço seja tão caro que toda a sobrecarga na cópia da pilha não incomode ninguém - seja lento ou rápido, isso não importa. Sim, se você o usar especificamente para programação assíncrona. Nas corotinas de Kotlin, a escala é notável, como mostra o protótipo Project Loom.
Outra diferença é que, como nós no Kotlin somos forçados a fazer isso no bytecode, temos um efeito colateral tão interessante. Por um lado, parece não ter êxito e, por outro, pelo contrário. Consiste no seguinte: é impossível sacrificar uma função arbitrária. Você precisa de funções que podem adormecer, sinalizar suspender com o modificador - observe explicitamente que a função pode pausar e esperar que algo demore. Por um lado, você não precisa disso no Loom, porque o tempo de execução pode colocar qualquer coisa para dormir. A solução do Alibaba é a mesma - você pode pegar uma pilha de qualquer thread. Ou no Go - tudo pode ser trancado lá em cima, qualquer código pode adormecer. Coisas gorutin e fazê-lo. Por um lado, essa abordagem é muito semelhante à programação com threads. É como se você estivesse programando como antes, somente agora os threads são chamados de fibra e se tornaram muito baratos. Se você observar atentamente a apresentação do mesmo tear, as fibras e os fios ainda são coisas diferentes. Como garantir que o código antigo que é escrito com threads acabe completamente fora da caixa nas fibras - não é óbvio e o que elas terão sucesso - ninguém sabe. Os problemas começam aí: o que fazer com os deadlocks, o que fazer com o código otimizado para os locais de encadeamentos, novamente alguns hashes locais ou ID de encadeamento realizam algumas otimizações de desempenho. E o Go tem o mesmo problema - quando os IDs de hardware não são expostos, escrever algum tipo de algoritmo de alto desempenho se torna não trivial.
Mas em Kotlin isso não é?
Em Kotlin, não estamos tentando fingir que fio e fibra são a mesma coisa. Nem tentamos executar o código antigo, não temos essa tarefa em princípio. Dizemos: "Desculpe, porque não temos tempo de execução, não podemos arbitrariamente pegar o código Java antigo e começar a mudar algo lá". E nós nem tentamos. Temos uma tarefa diferente. Dizemos que temos um recurso do idioma, adormecendo funções, você pode escrever código assíncrono com eles, e esse é um novo recurso do idioma. E nos distanciamos completamente desse problema (“como executar o código antigo”), dizemos: “Existe um novo código, bom, ortodoxo, você pode colocá-lo no sono”. Até certo ponto, isso facilita a vida, porque você não precisa se elevar nem a si mesmo nem às pessoas, mas o que acontece se algum velho govnokod que não sabia que o lançaria sobre as fibras se lançaria subitamente sobre eles.
Em nosso modelo, não temos nenhum código antigo, apenas um novo que está inicialmente pronto para o fato de que hoje ele está em um encadeamento, amanhã em outro, e se, por exemplo, precisar descobrir qual encadeamento está agora, ele saberá. Sim, você precisa de um thread local, mas ele pode reconhecê-los. No entanto, ele deve estar preparado para o fato de que hoje os locais de discussão são um e amanhã - outros. Se ele deseja que esses locais viajem com ele, existe outro mecanismo para isso, um contexto de rotina onde ele pode armazenar suas coisas, as quais, juntamente com a rotina, viajam de um fio para outro. Isso, de certa forma, facilita a vida para nós, porque não estamos tentando manter o código antigo.
Por outro lado, fazemos uma pessoa pensar explicitamente sobre sua API, dizer: aqui estou escrevendo uma função no Kotlin com corotinas. Se antes eu observar algum método no meu código, getO que não está claro, esse método funcionará rapidamente e retornará imediatamente ou ficará online e poderá funcionar por uma hora - só posso ler a documentação e entender com que rapidez ele funcionará. Ou talvez ele esteja trabalhando rápido agora, e amanhã o programador Vasya Pupkin virá e o fará ficar online agora. Com a Kotlin Coroutines, fornecemos um mecanismo garantido por idioma com um modificador de suspensão . Quando trabalho com corotinas, analiso algumas funções. Se não vejo o modificador de suspensão, significa que funciona rapidamente, faz tudo localmente. Existe um modificador de suspensão, o que significa que essa função é de alguma forma assíncrona; ela permanecerá na rede por um longo tempo. E isso ajuda a criar uma API de auto-documentação para que possamos ver imediatamente o que nos espera. Isso ajuda a evitar imediatamente erros estúpidos quando esqueci em algum lugar do código que chamei de algo longo sem suspeitar.
Na prática, isso é muito bom. Isso precisa marcar explicitamente essas funções adormecidas. No Go, por exemplo, não é, não preciso marcar nada por aí. Acontece que esse efeito colateral de nossa implementação (que deve ser marcado com o modificador de suspensão) ajuda a tornar a arquitetura correta, ajuda a controlar que você não causará algum jogo assíncrono aleatório e muito selvagem no local em que você inicialmente esperava que tudo acontecesse rapidamente.
Mas há algumas coisas que são difíceis de proibir, por exemplo, algum tipo de arquivo de E / S de rede.
Não, o IO da rede apenas proíbe com bastante facilidade. Aqui está o arquivo IO - complicado. Mas aqui novamente, um ponto delicado: para a maioria dos aplicativos, a E / S de arquivo é uma coisa rápida e, portanto, é perfeitamente normal que funcione de forma síncrona. Um aplicativo muito raro funciona tanto com IO que se torna um problema para demorar tanto. E aqui damos a uma pessoa a oportunidade de escolher: você pode criar diretamente um arquivo IO conosco e não tomar um banho de vapor, porque ele bloqueará o que está acontecendo (porque geralmente é rápido). Mas se o seu caso em particular tiver apenas um cálculo muito longo, não é assíncrono, mas consome muito tempo da CPU e você não deseja bloquear alguns de seus outros pools de threads, fornecemos um mecanismo simples e compreensível: você inicia um processo separado pool de threads para computação pesada e, em vez de escrever uma função regular divertida computeSomething () e escrever na documentação “Cara, com cuidado, essa função pode funcionar por muito tempo, então atenção - não use em nenhum lugar, não use UI ”, oferecemos um método mais simples Khanismo. Você simplesmente escreve essa função como suspender fun computeSomething () e, para sua implementação, usa uma função de biblioteca especial withContext , que lança o cálculo no pool de threads especial que você especificou. Isso é muito conveniente: o usuário não precisa mais sobrevoar o cérebro: ele imediatamente vê uma suspensão, sabe que essa chamada não bloqueia seu encadeamento e pode chamá-lo facilmente de um fluxo da interface do usuário e assim por diante.
Ele mudará para o fluxo desejado que já está dentro e seu fluxo não será bloqueado. Essa é a separação correta de preocupações: o usuário não se importa com a implementação, mas quem implementa pode transferir corretamente para o pool para o qual é necessário e distribuir corretamente os recursos de computação em seu aplicativo. Na prática, isso se mostra muito conveniente em termos de estilo de programação. Precisamos escrever menos documentação, o compilador irá verificar e corrigir mais.
Eu acho que é seguro. Alguém pode quebrar um pool de threads ou acessar os dados de outra pessoa?
Naturalmente, tudo é possível. É difícil proteger das mãos tortas. É claro que, por mais que escrevamos todos os tipos de sistemas de tipos e verificações no compilador, tudo sempre pode ser quebrado. A questão é que o compilador deve ajudar a escrever o código correto. Infelizmente, o sonho de proibir códigos ruins é utópico. Especificamente, não incluímos nenhum recurso no idioma. Não há coisas em Java no Kotlin se souber sobre elas que elas são usadas principalmente para outros fins e o código com elas é principalmente ruim. Mas qualquer bom recurso que esteja no Kotlin pode ser usado para outros propósitos de várias maneiras diferentes. Infelizmente não há opções. A linguagem pode ser abusada de muitas maneiras diferentes. Você não pode se proteger de mãos tortas.
Aprendi com os alunos de Kotlin que pergunta interessante você pode fazer. Eles desistiram e disseram que você é muito esperto e evita as perguntas de maneira flexível.
De que perguntas?
Por exemplo, uma pergunta sobreviveu a duas pessoas: por que no Kotlin não existem tipos brutos? Sem genéricos.
Porque você sempre pode escrever um asterisco.
E será compatível com Java?
Sim
Ou seja, você tem algum tipo de método java que requer algo sem um genérico. Lista, por exemplo.
Se existe um método java sem um genérico, você pode passar qualquer lista para lá. Você pode transferir a lista com um asterisco, com uma sequência de caracteres. O Kotlin permitirá que você transfira qualquer jogo para o método Java. raw List, platform type, , , List . raw type, , Java , . Java, , , , , , raw type. , — , . , — . — , , raw types. , migration story.
platform type ?
flexible. nullable-. , String. , String nullable String — . , String — nullable -nullable. Kotlin , , . String, nullable String. , - Java, .
?
, , , , . Flexible , dynamic. Flexible — , Java, String, nullable String, int.
- - , .
, , . . read only mutable. List MutableList. Java List, , Java- , , - List MutableList. , Java. , Java - , . , , . , , , List, , , MutableList, List . List, String, .
- , ? - ?
, . , . It just works. Java . nullability- , , nullable . , . , , , . , , , , - . , -. - JavaFx, - , JavaFx Java, , . , - , . . , , .
, .
Claro. , . Kotlin Native. : , seamless C- , , - .
, Native ?
, , Kotlin JavaScript, - - . «Write once, run anywhere», , . : , Common Kotlin Portable Kotlin, , . , - - , , . , , - . , .
JVM , Java, JS , JS, Native . , , , , . - JS, . -. - : double, String. JVM- 0 «0.0», JS . . JS , , — ? , . , , JS- . , -. , . - — , , — . , , , , JVM, JS, Native — , , - . .
?
Sim , , .
, …
, . , . Loom . - JVM. , .
, , Java?
, . . — . , . , - . , for ( i in 0..10 ) , for (int i = first . , , . . , .
- ?
, … , . . JVM JS.
Node.js?
! . , JS-. , , JS- . , . , - — , JS-, - — . , . .
« ». , ?
Claro. , , . JVM , Java, . JVM . legacy, enterprise, . , , . , JVM. , — , . , . , — JVM « ». . API , . , . , . , , . , , .
TechTrain « ?» . . , .
JS , Kotlin Java?
Java . «Kotlin in Action», , Java-. , Java- , , Kotlin-. , «by design». , Java- . . JPoint , Kotlin . , . , 60-70% Java. Java, , - . Java .
- — , , -. as-is. , , . Kotlin , , «», «». , «» — . while — . 100500 . Mas porque? , Java-. - , « Kotlin», , .
, . . , , . , .
, -, ?
, . . Java- . Android- — , . . , . — .
- , ?
, . , , . , , . — , , . Kotlin . , . - , , , . : , . C++, Java, Python. . Java - , Java, . , , puiblic static void main… -, . Java, , . ?
Kotlin : , , Python, . C++ , C++ . , , . , . , , . Kotlin — . — Python. . . , . , . . — , , , , — . , .
, — ?
, . must have. , — . . , . — . , , , .
?
… , , . . JS- — . — . JS, , . - JS, type checkers, Flow TypeScript. - JS . Python. - DSL, . Django , . , . , , , . . Django, , CRUD-. , - — . -, - , , . . . Kotlin, , Java, . core belief Kotlin, .
, - , Kotlin ?
Claro! , , - CRUD-. : , , — , . -, — , . , TypeScript Flow — JS.
Kotlin , Kotlin JS TypeScript , . TS Kotlin/JS, , TS , JS-, . Kotlin/JS , . , .
, — double…
, . , , .
- .
.
?
Eu tenho olimpíadas :-) E eu próprio participo, mas raramente.
Vejo que, nas Olimpíadas, o Java às vezes está disponível como uma das principais linguagens.
Agora está disponível quase sempre. Ela apareceu cerca de quinze anos atrás. Java e C ++ são duas linguagens padrão que suportam e, em seguida, variações, dependendo da concorrência.
É mais difícil vencer em Java, há alguma sobrecarga oculta?
Depende da competição. Em uma competição normal, é o mesmo se houver mais tarefas na ideia e no algoritmo correto. Mas há algum tipo de jogo em que as tarefas envolvem otimização não assintótica, em que você precisa otimizar tudo ao ritmo - é claro que será difícil em Java, você precisará tentar muito. Além disso, há um tempo de execução de teste muito curto. Grosso modo, se você tiver um limite de tempo de execução de vários segundos, o HotSpot aquecerá um código pequeno em um segundo e não se importará. E se você tem um limite para tudo - um segundo, em Java, você pode simplesmente perder devido ao fato de que enquanto o HotSpot está aquecendo e compilando - um segundo se passou.
Sim, existem competições loucas onde o Java é difícil. Mas competições normais (populares, suportadas por pessoas boas) - elas tentam executar as tarefas e o ambiente de tal maneira que Java e vantagens tenham chances iguais. E as razões são claras: embora o Java não cresça na educação, ele não diminui muito em lugar algum. Em algum lugar, algumas universidades se recusaram a aprender Java e mudaram para Python - e por isso, inclusive, agora muitas competições aprenderam Python. Este é um terceiro idioma tão estável suportado. As competições são principalmente estudantes. Existem competições profissionais e grandes empresas estão fazendo algo como a Copa Hacker do Facebook, onde todos podem participar, mas ainda assim, o principal tópico da programação esportiva é escola e aluno. Nos anos escolares e estudantis, as pessoas se exercitam e treinam constantemente. Mas depois da formatura, depois de ir trabalhar - muito poucas pessoas continuarão a participar. Portanto, a escolha dos idiomas é determinada pelo que é usado na educação. Se eles ensinam vantagens, Java e python, eles estarão nas competições. Para muitos programadores, Java é a primeira linguagem, respectivamente, todas as competições tentam suportar Java. Para o bem da concorrência, aprender C ++ - jogo. É para programação de sistema, programação de baixo nível, você não precisa ter um milhão de programadores em C ++, é inútil.
Como você gosta da ideia de adicionar o Kotlin à lista de idiomas padrão?
Bem, na verdade, estamos promovendo ativamente essa ideia. Existe um ICPC, que ocorre anualmente, reúne centenas de milhares de participantes em todo o mundo, mais de cem equipes vão para as finais. No ICPC, o Kotlin é suportado. Agora há uma lista de linguagens: C / C ++, Java, Python e Kotlin. Mas, por enquanto, é claro, ninguém realmente escreve sobre isso, pela razão desse problema: penetração na educação em um estágio muito inicial. Nas competições estudantis, essas línguas são usadas para ensinar os alunos.
Kotlin já é ensinado em algum lugar?
Em algum lugar exatamente ensinado. Por exemplo, no Politécnico de São Petersburgo. Mas estamos em um estágio muito inicial, no "passo 0" deste processo.
Não há falhas fatais?
Não, o Kotlin é melhor para o ensino fundamental do que outras línguas. Apenas a educação é conservadora. As pessoas têm um programa pronto, livros didáticos. Ninguém gosta de mudar. Por que um professor que ensina programação em seu primeiro ano de alunos muda seu idioma, qual é o bônus? Isso pode ser revisado a cada dez anos.
O bônus, por exemplo, é que a pessoa que o deixa será mais adaptada à realidade.
Não. Porque não é tão importante qual idioma você aprendeu primeiro. Um programador profissional em sua vida estudou uma dúzia de idiomas e usa cerca de três idiomas ativamente. Além disso, tudo isso está mudando constantemente. O que você aprenderá a programar primeiro não é tão importante. É importante quanta língua você possui ao se formar em uma universidade - esse é outro tópico, isso é importante. E aqui estamos diante de problemas em mercados conservadores focados na autoridade. Por exemplo, na China, há um problema que é esclarecido depois de conversar com os caras de lá. Você ocupa um escritório grande em que existem muitos programadores, você pergunta - por que você não usa o Kotlin? Mas porque agora, os caras não ensinaram Kotlin na universidade e não querem aprender nada de novo, mas por que ensinariam?
Não é assim com a gente?
Isto está em toda parte, apenas em uma escala diferente. Em diferentes culturas, de maneiras diferentes. Existem culturas nas quais, como o guru disse, ou como o professor disse, você o fará. Em algum lugar, as pessoas são mais independentes, mais propensas a experimentação, inovação. Em algum lugar as pessoas vão aprender tudo sozinhas. Em algum lugar, eles não levantam um dedo e fazem exatamente o que foram ensinados. Existem mais implementações de Kotlin na Rússia, mas também porque somos originalmente daqui, falamos mais em conferências e assim por diante.
Isso é da minha geração, os programadores são entusiastas. Cresci quando quem gostava do programa, estudava tudo por conta própria, porque não havia nada. E agora essa é a coisa da massa que está sendo ensinada. Pegue um programador moderno, a maioria faz isso não porque ele ama, mas porque eles lhe ensinaram isso e agora pagam muito dinheiro. Consequentemente, essas pessoas não estudarão a tecnologia que acaba de ser lançada. Por que eles precisam disso?
Porque você ganhará muito dinheiro usando os recursos interessantes desta tecnologia.
Claro que não! No Kotlin, é mais provável que você tenha mais prazer.
Existem coisas específicas que realmente têm valor comercial - falamos sobre a reutilização entre a frente e a parte de trás ...
Nem todo mundo precisa disso. Por outro lado, e prazer também. Nem todo mundo gosta de seu trabalho. Eles recebem dinheiro - eles trabalham, não faz diferença para eles, gostem ou não. O dia útil terminou - eles fecharam, esqueceram-se e começaram a fazer outras coisas.
Isso é de alguma forma muito chato, se não terrível.
Esta é a verdade da vida, infelizmente. Não importa o quão terrível ela seja. E essas pessoas, é claro, não se importam. Kotlin, não Kotlin.
Até onde eu entendi, muitas pessoas trabalham no JetBrains porque gostam de trabalhar.
O JetBrains a esse respeito é uma amostra não representativa, é claro. Pessoas especialmente selecionadas, motivadas, que realmente gostam dessa coisa.
Nosso tempo está lentamente chegando ao fim, então a pergunta é: você pode passar algo para nossos leitores sobre Habré? Alguma palavra de despedida, alguma revelação?
Posso transmitir saudações ardentes :-) Mas não direi revelação, que tipo de revelação pode ser? A única conclusão que podemos tirar da nossa conversa é que quem gosta de trabalhar é feliz. Eu li vários blogs de pessoas boas que programavam em Java, apenas trabalhavam sem nenhum prazer. E então, por algum motivo, eles ficaram curiosos, a vida os fez, tentaram Kotlin e descobriram inesperadamente por si mesmos que você pode gostar de trabalhar. Que você pode amar o que faz. O que você pode amar uma linguagem de programação. E não apenas para usar, sem emoção, como uma ferramenta. Obviamente, a linguagem é uma ferramenta, mas você pode se relacionar indiretamente ou pode amá-la. Essa é uma atitude diferente, incluindo uma atitude diferente em relação ao trabalho.
O Kotlin tem muitas pessoas que têm sentimentos calorosos comparáveis ao amor, precisamente porque o Kotlin é legal de programar, especialmente depois do Java. Talvez não apenas após o Java. Provavelmente, não há idiomas em que seja tão bom (exatamente essa palavra) programar. Existem idiomas com mais funcionalidade, com recursos mais fortes, existem idiomas com um sistema de tipos mais rigorosos, existem idiomas onde tudo é puro, é onde tudo é vice-versa - inseguro. Tome qualquer dimensão e você encontrará idiomas melhores que o Kotlin nesta propriedade. Mas Kotlin tem um equilíbrio tão grande que não é por acaso que ele no StackOverflow, na enquete deste ano, ficou em segundo lugar na lista dos idiomas mais amados. O primeiro, ao que parece, foi Rust. Mas o Rust não é um concorrente para nós, porque o Rust é uma linguagem de programação do sistema. Nós não entramos nesse nicho. Não é nada chato que Rust tenha ultrapassado Kotlin a esse respeito. Nós nos esforçamos para tornar o Kotlin a principal linguagem para programação de aplicativos, na qual é agradável resolver problemas de aplicativos. Nós não temos e nunca teremos alguns recursos do Rust, porque eles simplesmente não são necessários pelo programador de aplicativos. Ele não deve gerenciar manualmente a memória ou pensar nos meandros da propriedade; um programador de aplicativos deve resolver problemas de negócios. Ele deve transformar seu domínio em código. E essa deve ser a transformação mais direta, sem que nenhum fator interfira nela. Estamos tentando eliminar esses fatores interferentes. Para que você transforme sua tarefa de negócios o mais diretamente possível, sem água e código extra em uma solução.
Bem, essa é uma competição um tanto injusta - todas essas linguagens como Java foram inventadas há muitos anos, e você apenas.
Naturalmente, o Kotlin leva em consideração a experiência de seus antecessores. Como qualquer linguagem moderna. Isso é progresso - quando algo novo é criado, levando em consideração deficiências antigas. Por uma boa razão, tipos anuláveis são criados no Kotlin. Bem, longe, empreenda qualquer empresa, vá a qualquer escritório grande, veja os registros de falhas e verá que a exceção mais frequente é NullPointerException. Esse é um fato bem conhecido e, se você estiver criando um novo idioma, precisará resolvê-lo. Portanto, prestamos muita atenção no idioma à nulidade. E assim por diante Se você não cria o idioma de maneira abstrata, não como um exercício acadêmico, mas tenta resolver os problemas das pessoas que eles costumam encontrar, o idioma acaba sendo bom. Por que ele é amado? Porque ele resolve os problemas deles.