Quantcast
Channel: Найцікавіше на DOU
Viewing all articles
Browse latest Browse all 8115

Java vs. Kotlin для Android. День 1: спрыгиваем с Java

$
0
0

В очередной раз набирая на клавиатуре в Android Studioстрочки кода с циклом for, поймал себя на мысли, что делал это множество раз и уже знаешь каждый следующий оператор, который идет дальше. Задача простая: выбрать из списка множество элементов, удовлетворяющее поставленному условию. Вроде бы ничего сложного, все просто: цикл по списку, внутри условие и добавление нового элемента в результирующий список. Еще один стандартный статический метод в классе с утилитами. Какой он там по счету уже...- 5ый или 10ый? Буквально 3-4строки кода, которые сделают свое дело, НО почему-то удовлетворения от выполненной задачи нет. Где-то там глубоко есть ощущение, что можно делать это проще. Там же рядышком лежат классы-утилиты для работы со строками и датами. Сколько их уже было за все время?

А тут еще на днях Петя/Ваня/Дэвид сказал, что они начинают новый проект под Android и будут писать его исключительно на Kotlin. Kotlin, а не Java. Чем этот язык лучше Java? Сколько уже было этих пустых никому не нужных попыток писать код под Android на PHP/C/C++/С#/Python, и где все это сейчас? Возможно, в этот раз все по-другому, и стоит обратить на него внимание? Ну что же, посмотрим, хотя я очень слабо верю во что-то путнее.

Разрабатывает его JetBrainsи уже давненько, т.е. за это время их желание создать свой язык не иссякло. Это похвально и заслуживает уважения. Мне нравится их IDEA & AS. Более того, главной целью для себя они ставят полностью перевести разработку внутри компании с Java на Kotlin, и хотят, чтобы он, как и Java, использовался в industry. А вот некоторые называют его прямо «Swift под Android», вот же ж юмористы! И не просто люди с улицы, а сами разработчики Kotlin! Утверждают, что про NPE в рантайме можно забыть, что можно расширять стандартные классы из SDK, что можно лямбды и анонимные функции писать и даже передавать функции как параметры в методы! И даже точку с запятой убрали из синтаксиса (кстати, вот с этим я согласен на все 100%). А это прямо-таки из моего PHP-ного прошлого — String Templates — по таким вещам иногда скучаешь. Забавно, конечно, но вряд ли это все как-то может пригодиться в Android-разработке. Хм, у них есть плагин под IDEA/AS и даже специальный плагин под Андроид проекты. Вот это сейчас надо посмотреть.

Интересно выходит — Kotlin на 100% совместим с Java, и плагин позволяет java-код в один клик трансформировать в kotlin-код, и это как раз можно проверить достаточно быстро. Создадим-ка пустой Android-проект с одной Activity и Fragment внутри, и еще один простой дата-класс тоже не помешает.

Берем шаблонную Activity:

package com.testkotlin;

import ...

public class TestActivity extends AppCompatActivity {

   @Override
   protected void onCreate(Bundle savedInstanceState) {
       super.onCreate(savedInstanceState);
       setContentView(R.layout.activity_test);
       Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
       setSupportActionBar(toolbar);

       FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
       fab.setOnClickListener(new View.OnClickListener() {
           @Override
           public void onClick(View view) {
               Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                       .setAction("Action", null).show();
           }
       });
   }
}

и с помощью действия «Convert Java File to Kotlin File»:

на выходе получаем такой вот код:

package com.testkotlin;

import ...

class TestActivity : AppCompatActivity() {

   override fun onCreate(savedInstanceState: Bundle?) {
       super.onCreate(savedInstanceState)
       setContentView(R.layout.activity_test)
       val toolbar = findViewById(R.id.toolbar) as Toolbar
       setSupportActionBar(toolbar)

       val fab = findViewById(R.id.fab) as FloatingActionButton
       fab.setOnClickListener { view ->
           Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                   .setAction("Action", null).show()
       }
   }
}

Выглядит неплохо, и вроде как все понятно. Получается, что из-за 100%-ой совместимости с Java новая TestActivityна Kotlin спокойно наследуется от AppCompatActivity, которая лежит в Support Library, а не в SDK. Ну что же, это довольно-таки серьезно облегчает переезд на рельсы Kotlin и делает использование Java-библиотек безболезненным. Безусловно это плюс, пожалуй, стоит записать очко в пользу Kotlin.

Теперь проверим, как это сработает на обычном дата-классе:

public class Message {
   private String text;
   private boolean isRead;

   public Message(String text, boolean isRead) {
       this.text = text;
       this.isRead = isRead;
   }

   public String getText() {
       return text;
   }

   public boolean isRead() {
       return isRead;
   }
}

и конвертнем его в kotlin-файл:

class Message(val text: String, val isRead: Boolean)

Одна строка кода по сравнению с 14-юв Java-варианте! А если еще перед описанием класса добавить data, то автоматом получаем возможность делать копии объектов с помощью метода copy(). В качестве параметров он может принимать новые значения полей объекта. Запишите еще очко в пользу Kotlin.

Это ж на сколько время-то экономится?!?! Вот такого твиста я не ожидал, и, бегло (ну, как бегло...часика 2) пробежавшись по разделу «Classes and Objects»в документации, я узнал, что:

  • для создания экземпляра класса нам не нужно ключевое слово new;
  • никаких тебе extendsили implements, для этого теперь используется «:»;
  • класс может иметь один primary constructorи один/несколько secondary constructors;
  • у primary constructorнет тела, но внутри него можно описать блок инициализации init;
  • используются ключевые слова var (mutable property)/val (read-only property) для декларации и инициализации propertiesпрямо в объявлении конструктора. Ключевые слова val\varиспользуются и при объявлении обычных локальных переменных;
  • OMG!, здесь естьnamed argumentsи дефолтные значения для них;
  • можно описывать кастомные accessors — круть! очень полезная штука;
  • теперь не нужно явно вызывать getter/setterдля получения/присвоения значения проперти — обращение происходит просто по имени — тоже здОрово!
  • по умолчанию область видимости для классов/методов/пропертей — public;
  • по умолчанию все классы в Kotlin finalи нужно использовать open-аннотацию для класса, если необходимо иное поведение — к этому придется немного привыкать;
  • интерфейсы теперь могу реализовывать методы!!! Т.е. класс может имплементить два интерфейса, которые имеют различную реализацию метода с одинаковой сигнатурой, и я смогу выбрать, где какой из методов использовать. Вот это реально круто! Очень давно об этом мечтал;
  • вариативность женериков (generics) реализована с помощью in/out-кейвордов;
  • реализовать anonymous inner classes можно через object expressionsobject declarations;
  • всеми любимый Singleton легко и просто реализуется с помощью object declaration;
  • Java static methods == object declaration + companion object;
  • делегирование реализовано на уровне декларации класса с помощью by-clause, компилятор сам сгенерирует необходимые дублирующие методы — любители делегирования возрадуйтесь, теперь не нужно дублировать вручную методы!

Отдельно стоит отметить, что фичи, затрагивающие сигнатуры методов, также распространяются и на обычные функции.

А еще можно взять java-код и скопипастить его в kotlin-файл и IDE сама предложит его конвертнуть. Кстати, на Java можно и в kotlin-файлах спокойно писать код, и все будет работать — это как еще один бонус 100%-й совместимости. Там же с помощью IDE полученный код можно упростить и привести его к kotlin-style. Это здорово поможет ускорить обучение и сдвинуть мышление в сторону Functional Programming(FP).

Все это выглядит здорово, местами для закоренелого object-oriented developer непривычно, но ведь красиво же! И, главное, что на выходе я получаю максимально оптимизированный java-код. Да уж, пессимизма по отношению к этому языку во мне поубавилось.

И я уже было собирался ложиться спать (на часах около 3-хночи), но по глупости взял и посмотрел вот этот небольшой докладпо теме от Jake Wharton и понял, что слишком я перестарался с игнорированием функционального программирования. Но этот пробел я буду восполнять уже завтра, пардон, сегодня. Еще и выспаться нужно успеть, и на проекте ждет меня куча бизнес-логики — опять циклы/условия и статические методы — а дедлайны никто не отменял. К тому же, будет что рассказать хлопцам за чашечкой кофе по Kotlin-у и непрозрачно намекнуть моему РМ-у, что было бы неплохо для Waverley (компания, где я работаю) начинать подыскивать Android-проект, где заказчику будет все равно на Kotlin-е мы его напишем или на Java. И разработчикам профит, и компания может себе в копилку еще одну технологию записать.


Viewing all articles
Browse latest Browse all 8115

Trending Articles