
Android джедая путь
Ivan Balaksha
Что не так с Java?
Проверяемые исключения
public void readFileLineByLine(){
BufferedReader buffReader = null;
try {
...
} catch (IOException ioe){
...
} finally {
if (buffReader != null){
try {
buffReader.close();
} catch (IOException ioe1){
...
}
}
}
...
}
NPE HELL*
public void doSmth(JavaUser user){
if(user != null){
String login = user.getLogin();
if(login != null){
System.out.println("Hello " + login);
}
}
}*JSR 305: Annotations for Software Defect Detection
Синтаксис анонимных классов
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
...
}
});

Статически типизированный язык программирования для Android, JVM и веб разработки
100% совместимость с Java™

- Выразительность
- Безопасность
- Универсальность
- Совместимость
Почему Kotlin?
Выразительность
fun myFunction() {
var a: Int = 1
val b = 2
val s: String = "test"
val f = 2f
}
fun sum(first: Int, second: Int) : Int {
return first + second
}
val firstName : String = "Ivan"
val lastName : String = "Balaksha"
var age : Int = 21Свойства + Вывод типов*
val firstName = "Ivan"
val lastName = "Balaksha"
var age = 21*JEP 286: Local-Variable Type Inference
val i : Int = ...
val f : Float = ...
val d : Double = ...
Отсутствие примитивных типов
button.setOnClickListener(object : View.OnClickListener{
override fun onClick(v: View?) {
doAnything()
}
})
Лямбда выражения
button.setOnClickListener(object : View.OnClickListener{
override fun onClick(v: View?) {
doAnything()
}
})
button.setOnClickListener(View.OnClickListener {
doAnything()
})Лямбда выражения
button.setOnClickListener(object : View.OnClickListener{
override fun onClick(v: View?) {
doAnything()
}
})
button.setOnClickListener(View.OnClickListener {
doAnything()
})
button.setOnClickListener { doAnything() }
Лямбда выражения
button.setOnClickListener(object : View.OnClickListener{
override fun onClick(v: View?) {
doAnything()
}
})
button.setOnClickListener(View.OnClickListener {
doAnything()
})
button.setOnClickListener { doAnything() }
button.onClick { doAnything() } (Anko)Лямбда выражения
data class KotlinUser(val login : String,val password : String)
Дата классы
equals()
hashCode()
toString()
Автоматически генерируются:
Стандартные значения для параметров функции
...
addContact("Ivan", "Balaksha", email = "test@test.test")
}
fun addContact(firstName: String,
lastName: String,
phone: String = "",
email: String = ""){
...
}Именованный аргумент
"Single-expression" функции
fun findUser(id : Int) = dataStore.find(id)
fun findUser(id : Int) : User{
return dataStore.find(id)
}Строковые шаблоны
val user = KotlinUser("admin","pwd")
val userInfo = "Login: ${user.login} Password: ${user.password}"Умные преобразования
fun demo(x: Any) {
if (x is String) {
print(x.length)
}else if(x is Int){
print(x + x)
}
}Функции расширения
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
this.alert { }
alert { }
...
}
}
class BlankFragment : Fragment() {
override fun onCreateView(...): View? {
getActivity().alert { }
activity.alert { }
return super.onCreateView(inflater, container, savedInstanceState)
}
}fun Context.alert(init: AlertDialogBuilder.() -> Unit)
= AlertDialogBuilder(this).apply { init() }when
val type = ...
val imageUrl = when(type){
1 -> ...
2 -> ...
3 -> ...
else -> ...
}with
recyclerView.adapter = ...
recyclerView.layoutManager = ...
recyclerView.visibility = ...
recyclerView.addOnItemTouchListener(...)with(recyclerView) {
adapter = ...
layoutManager = ...
visibility = ...
addOnItemTouchListener(...)
}Коллекции
associate
binarysearch
count
distinct/distinctBy
drop
dropWhile
find
fold
first
filter
flatMap
forEach
groupBy
getOrElse
indexOfFirst
indexOfLast
map
max/min
reduce
take
takeWhile
sort/sortBy
zip
...
Коллекции
names
.filter { it.startsWith("A") }
.sortedBy { it }
.map { it.toUpperCase() }
.forEach { print(it) }Безопасность
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
String info = savedInstanceState.getString("info");
...
}Java небезопасна
Мое приложение упало.
Что случилось?
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
String info = savedInstanceState.getString("info");
...
}Java небезопасна
Caused by: java.lang.NullPointerException:
Attempt to invoke virtual method 'java.lang.String android.os.Bundle.getString(java.lang.String)'
on a null object reference
at pre.MainActivity.onCreate(MainActivity.java:17)Ошибка выполнения
Nullable типы
val user : User? = ...
var notification : Notification? = ...Оператор безопасного вызова
val name : String? = ...
val length = name?.lenghtЭлвис оператор
val name : String? = ...
val length = name?.length ?: 0val name : String = nullОшибка компиляции
val name : String? = null
println(name?.length)ничего не напечатает
var name : String = "testString"
name = nullОшибка компиляции
val name : String? = null
println(name!!.length)Ошибка выполнения
Error:(15, 47)
Only safe (?.) or non-null asserted (!!.)
calls are allowed on a nullable receiver of type android.os.Bundle?override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val info : String = savedInstanceState.getString("info")
...
}Ошибка компиляции
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val info : String? = savedInstanceState?.getString("info")
...
}Nullable строка
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val info : String? = savedInstanceState?.getString("info")
...
}Nullable строка
Оператор безопасного вызова
let
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val info : String? = savedInstanceState?.getString("info")
info?.let { process(it) }
...
}Безопасные преобразования
fun process(a : Any){
val aInt: Int? = a as? Int
...
}Универсальность
Многоцелевой язык программирования, позволяющий создавать приложения любых типов
- Android
- Back-end
- Front-end(Javascript)
- ...
Совместимость
Совместимость
Java code
Kotlin code
javac
kotlinc
bytecode
DEX


Время компиляции
Java
Kotlin
Scala
+
+/–
–
Размер стандартной библиотеки
+
–
(~7k методов)
(~50k методов)
Что-то еще?
- Ленивые свойства
- Интерфейсы с поддержкой "стандартных методов"
- Перезагрузка операторов
- Anko
- Android Extension Plugin
Что планируется в Kotlin 1.1
- async-await
- type aliases
- улучшенная поддержка Java 8
- поддержка Java 9 ( Jigsaw)
- Javascript backend
- закончить спецификацию языка
Хотите использовать у себя в проекте?
- Установить Kotlin плагин
- Tools->Kotlin->Configure Kotlin in Project
- Gradle sync
Ресурсы
https://kotlinlang.org/docs/reference/
http://try.kotlinlang.org
Q/A
Ivan Balaksha
@VanyaBalaksha
https://slides.com/ivanbalaksha
Kotlin - Android джедая путь(RUS)
By Ivan Balaksha
Kotlin - Android джедая путь(RUS)
- 1,453