Te warsztaty są częścią kursu Kotlin Bootcamp for Programmers. Najwięcej korzyści przyniesie Ci ukończenie wszystkich ćwiczeń w kolejności. W zależności od swojej wiedzy możesz pominąć niektóre sekcje. Ten kurs jest przeznaczony dla programistów, którzy znają język obiektowy i chcą nauczyć się Kotlin.
Wprowadzenie
W tym laboratorium dowiesz się podstaw języka programowania Kotlin: typów danych, operatorów, zmiennych, struktur sterujących oraz zmiennych dopuszczających i niedopuszczających wartości null. Ten kurs jest przeznaczony dla programistów, którzy znają język obiektowy i chcą nauczyć się Kotlina.
Lekcje w tym kursie nie są powiązane z jedną przykładową aplikacją. Zostały zaprojektowane tak, aby poszerzać Twoją wiedzę, ale jednocześnie były od siebie częściowo niezależne. Dzięki temu możesz przeglądać sekcje, które już znasz. Aby je ze sobą powiązać, w wielu przykładach użyto motywu akwarium. Jeśli chcesz poznać pełną historię akwarium, zapoznaj się z kursem Kotlin Bootcamp for Programmers na platformie Udacity.
Co warto wiedzieć
- Jak utworzyć projekt w IntelliJ IDEA
- Jak otworzyć i wykonać kod w środowisku REPL (Read-Eval-Print Loop) języka Kotlin w IntelliJ IDEA (Narzędzia > Kotlin > Kotlin REPL)
Czego się nauczysz
- Jak używać typów danych, operatorów i zmiennych w języku Kotlin
- Jak pracować z wartościami logicznymi i warunkami
- Różnica między zmiennymi dopuszczającymi wartość null a zmiennymi niedopuszczającymi wartości null
- Jak działają tablice, listy i pętle w Kotlinie
Jakie zadania wykonasz
- Praca z REPL języka Kotlin, aby poznać jego podstawy
W tym ćwiczeniu dowiesz się więcej o operatorach i typach w języku programowania Kotlin.
Krok 1. Poznaj operatory liczbowe
- Otwórz IntelliJ IDEA, jeśli nie jest jeszcze otwarty.
- Aby otworzyć REPL języka Kotlin, kliknij Narzędzia > Kotlin > Kotlin REPL.
Podobnie jak w innych językach, w Kotlinie do oznaczania dodawania, odejmowania, mnożenia i dzielenia używa się znaków +
, -
, *
i /
. Kotlin obsługuje też różne typy liczb, takie jak Int
, Long
, Double
i Float
.
- Wpisz w REPL te wyrażenia: Aby zobaczyć wynik, po każdym z nich naciśnij
Control+Enter
(Command+Enter
na komputerze Mac).
1+1 ⇒ res8: kotlin.Int = 2 53-3 ⇒ res9: kotlin.Int = 50 50/10 ⇒ res10: kotlin.Int = 5 1.0/2.0 ⇒ res11: kotlin.Double = 0.5 2.0*3.5 ⇒ res12: kotlin.Double = 7.0
Pamiętaj, że wyniki operacji zachowują typy operandów, więc 1/2 = 0, ale 1.0/2.0 = 0.5.
- Wypróbuj kilka wyrażeń z różnymi kombinacjami liczb całkowitych i dziesiętnych.
6*50 ⇒ res13: kotlin.Int = 300 6.0*50.0 ⇒ res14: kotlin.Double = 300.0 6.0*50 ⇒ res15: kotlin.Double = 300.0
- Wywoływanie niektórych metod na liczbach. W języku Kotlin liczby są traktowane jako typy proste, ale można wywoływać na nich metody tak, jakby były obiektami.
2.times(3) ⇒ res5: kotlin.Int = 6 3.5.plus(4) ⇒ res8: kotlin.Double = 7.5 2.4.div(2) ⇒ res9: kotlin.Double = 1.2
Krok 2. Ćwicz używanie typów
Kotlin nie konwertuje niejawnie typów liczbowych, więc nie możesz przypisać wartości typu short bezpośrednio do zmiennej typu long ani wartości typu Byte
do zmiennej typu Int
. Dzieje się tak, ponieważ niejawna konwersja liczb jest częstym źródłem błędów w programach. Zawsze możesz przypisać wartości różnych typów, używając rzutowania.
- Aby zobaczyć niektóre z możliwych rzutowań, zdefiniuj w REPL zmienną typu
Int
.
val i: Int = 6
- Utwórz nową zmienną, a następnie wpisz jej nazwę podaną powyżej i dodaj znak
.to
.
val b1 = i.to
IntelliJ IDEA wyświetli listę możliwych uzupełnień. Automatyczne uzupełnianie działa w przypadku zmiennych i obiektów dowolnego typu.
- Wybierz
toByte()
z listy, a potem wydrukuj zmienną.
val b1 = i.toByte()
println(b1)
⇒ 6
- Przypisz wartość
Byte
do zmiennych różnych typów.
val b2: Byte = 1 // OK, literals are checked statically
println(b2)
⇒ 1
val i1: Int = b2
⇒ error: type mismatch: inferred type is Byte but Int was expected
val i2: String = b2
⇒ error: type mismatch: inferred type is Byte but String was expected
val i3: Double = b2
⇒ error: type mismatch: inferred type is Byte but Double was expected
- W przypadku zadań, które zwróciły błędy, spróbuj je zamiast tego przesłać.
val i4: Int = b2.toInt() // OK!
println(i4)
⇒ 1
val i5: String = b2.toString()
println(i5)
⇒ 1
val i6: Double = b2.toDouble()
println(i6)
⇒ 1.0
- Aby długie stałe liczbowe były bardziej czytelne, Kotlin umożliwia umieszczanie w nich podkreśleń w miejscach, które uznasz za odpowiednie. Spróbuj wpisać inne stałe liczbowe.
val oneMillion = 1_000_000 val socialSecurityNumber = 999_99_9999L val hexBytes = 0xFF_EC_DE_5E val bytes = 0b11010010_01101001_10010100_10010010
Krok 3. Poznaj wartość typów zmiennych
Kotlin obsługuje 2 typy zmiennych: zmienne i niezmienne. Za pomocą val
możesz przypisać wartość tylko raz. Jeśli spróbujesz ponownie przypisać coś do tego konta, pojawi się błąd. Za pomocą var
możesz przypisać wartość, a potem zmienić ją w programie.
- Zdefiniuj zmienne za pomocą znaków
val
ivar
, a następnie przypisz im nowe wartości.
var fish = 1
fish = 2
val aquarium = 1
aquarium = 2
⇒ error: val cannot be reassigned
Możesz przypisać fish
wartość, a następnie przypisać jej nową wartość, ponieważ jest zdefiniowana za pomocą var
. Próba przypisania nowej wartości do zmiennej aquarium
powoduje błąd, ponieważ jest ona zdefiniowana za pomocą funkcji val
.
Typ przechowywany w zmiennej jest określany, gdy kompilator może go ustalić na podstawie kontekstu. Jeśli chcesz, możesz zawsze jawnie określić typ zmiennej, używając notacji z dwukropkiem.
- Zdefiniuj zmienne i określ ich typ.
var fish: Int = 12
var lakes: Double = 2.5
Gdy typ zostanie przypisany przez Ciebie lub kompilator, nie możesz go zmienić, ponieważ spowoduje to błąd.
Krok 4. Dowiedz się więcej o ciągach znaków
Ciągi znaków w Kotlinie działają podobnie jak w innych językach programowania, w których ciągi znaków są oznaczane symbolem "
, a pojedyncze znaki – symbolem '
. Ciągi znaków można łączyć za pomocą operatora +
. Szablony ciągów znaków możesz tworzyć, łącząc je z wartościami. Nazwa $
variable
jest zastępowana tekstem reprezentującym wartość. Jest to tzw. interpolacja zmiennych.
- Utwórz szablon ciągu znaków.
val numberOfFish = 5
val numberOfPlants = 12
"I have $numberOfFish fish" + " and $numberOfPlants plants"
⇒ res20: kotlin.String = I have 5 fish and 12 plants
- Utwórz szablon ciągu znaków z wyrażeniem. Podobnie jak w innych językach wartość może być wynikiem wyrażenia. Aby zdefiniować wyrażenie, użyj nawiasów klamrowych
{}
.
"I have ${numberOfFish + numberOfPlants} fish and plants"
⇒ res21: kotlin.String = I have 17 fish and plants
W tym ćwiczeniu dowiesz się więcej o wartościach logicznych i sprawdzaniu warunków w języku programowania Kotlin. Podobnie jak w innych językach, w Kotlinie występują wartości logiczne i operatory logiczne, takie jak mniejszy niż, równy, większy niż itp. (<
, ==
, >
, !=
, <=
, >=
).
- Napisz oświadczenie
if
/else
.
val numberOfFish = 50
val numberOfPlants = 23
if (numberOfFish > numberOfPlants) {
println("Good ratio!")
} else {
println("Unhealthy ratio")
}
⇒ Good ratio!
- Spróbuj użyć zakresu w instrukcji
if
. W języku Kotlin testowany warunek może też używać zakresów.
val fish = 50
if (fish in 1..100) {
println(fish)
}
⇒ 50
- Napisz
if
z wieloma zgłoszeniami. W przypadku bardziej skomplikowanych warunków użyj operatorów logicznych i&&
oraz lub||
. Podobnie jak w innych językach możesz użyćelse if
, aby utworzyć wiele przypadków.
if (numberOfFish == 0) {
println("Empty tank")
} else if (numberOfFish < 40) {
println("Got fish!")
} else {
println("That's a lot of fish!")
}
⇒ That's a lot of fish!
- Wypróbuj
when
oświadczenie. W języku Kotlin istnieje lepszy sposób na zapisanie tej serii instrukcjiif
/else if
/else
– za pomocą instrukcjiwhen
, która jest podobna do instrukcjiswitch
w innych językach. Warunki w instrukcjiwhen
mogą też używać zakresów.
when (numberOfFish) {
0 -> println("Empty tank")
in 1..39 -> println("Got fish!")
else -> println("That's a lot of fish!")
}
⇒ That's a lot of fish!
W tym ćwiczeniu dowiesz się, czym różnią się zmienne dopuszczające wartość null od zmiennych niedopuszczających wartości null. Błędy programowania związane z wartościami null były źródłem niezliczonych błędów. Kotlin ma na celu zmniejszenie liczby błędów przez wprowadzenie zmiennych, które nie mogą mieć wartości null.
Krok 1. Dowiedz się więcej o możliwości przyjmowania wartości null
Domyślnie zmienne nie mogą mieć wartości null
.
- Zadeklaruj
Int
i przypisz do niego wartośćnull
.
var rocks: Int = null
⇒ error: null can not be a value of a non-null type Int
- Użyj operatora znaku zapytania
?
po typie, aby wskazać, że zmienna może mieć wartość null. ZadeklarujInt?
i przypisz do niego wartośćnull
.
var marbles: Int? = null
W przypadku złożonych typów danych, takich jak lista:
- Możesz zezwolić na to, aby elementy listy miały wartość null.
- Możesz zezwolić na to, aby lista miała wartość null, ale jeśli nie ma wartości null, jej elementy nie mogą mieć wartości null.
- Możesz zezwolić na to, aby lista lub elementy miały wartość null.
Listy i niektóre inne złożone typy danych omówimy w dalszej części.
Krok 2. Dowiedz się więcej o ? i ?: operatory
Możesz testować warunek null
za pomocą operatora ?
, co pozwoli Ci uniknąć pisania wielu instrukcji if
/else
.
- Napisz dłuższy kod, aby sprawdzić, czy zmienna
fishFoodTreats
nie jest równanull
. Następnie zmniejsz wartość tej zmiennej.
var fishFoodTreats = 6
if (fishFoodTreats != null) {
fishFoodTreats = fishFoodTreats.dec()
}
- Teraz zobacz, jak można to zapisać w Kotlinie za pomocą operatora
?
.
var fishFoodTreats = 6
fishFoodTreats = fishFoodTreats?.dec()
- Możesz też łączyć testy wartości null za pomocą operatora
?:
. Przyjrzyj się temu przykładowi:
fishFoodTreats = fishFoodTreats?.dec() ?: 0
Jest to skrót od „jeśli fishFoodTreats
nie jest równe null
, zmniejsz wartość i użyj jej; w przeciwnym razie użyj wartości po znaku ?:
, czyli 0”. Jeśli wartość fishFoodTreats
to null
, ocena zostanie zatrzymana, a metoda dec()
nie zostanie wywołana.
Uwaga dotycząca wskaźników o wartości null
Jeśli naprawdę lubisz NullPointerExceptions
, Kotlin pozwala Ci ich używać. Operator potwierdzenia, że wartość nie jest zerowa, !!
(podwójny wykrzyknik), przekształca dowolną wartość w typ niezerowy i zgłasza wyjątek, jeśli wartość to null
.
val len = s!!.length // throws NullPointerException if s is null
W tym ćwiczeniu dowiesz się, czym są tablice i listy, oraz poznasz różne sposoby tworzenia pętli w języku programowania Kotlin.
Krok 1. Utwórz listy
Listy są podstawowym typem w Kotlinie i są podobne do list w innych językach.
- Zadeklaruj listę za pomocą znaku
listOf
i wydrukuj ją. Tej listy nie można zmienić.
val school = listOf("mackerel", "trout", "halibut")
println(school)
⇒ [mackerel, trout, halibut]
- Zadeklaruj listę, którą można zmieniać za pomocą
mutableListOf
. Usuń element.
val myList = mutableListOf("tuna", "salmon", "shark")
myList.remove("shark")
⇒ res36: kotlin.Boolean = true
Metoda remove()
zwraca wartość true
, gdy usunie przekazany element.
Krok 2. Tworzenie tablic
Podobnie jak w innych językach, w Kotlinie występują tablice. W przeciwieństwie do list w Kotlinie, które mają wersje modyfikowalne i niemodyfikowalne, nie ma modyfikowalnej wersji Array
. Po utworzeniu tablicy jej rozmiar jest stały. Nie możesz dodawać ani usuwać elementów, z wyjątkiem kopiowania do nowej tablicy.
Reguły dotyczące używania znaków val
i var
są takie same w przypadku tablic jak w przypadku list.
- Zadeklaruj tablicę ciągów znaków za pomocą
arrayOf
. Aby go wydrukować, użyj narzędzia do tworzenia tablicjava.util.Arrays.toString()
.
val school = arrayOf("shark", "salmon", "minnow")
println(java.util.Arrays.toString(school))
⇒ [shark, salmon, minnow]
- Tablica zadeklarowana za pomocą
arrayOf
nie ma typu powiązanego z elementami, więc możesz mieszać typy, co jest przydatne. Zadeklaruj tablicę z różnymi typami.
val mix = arrayOf("fish", 2)
- Możesz też deklarować tablice z jednym typem dla wszystkich elementów. Zadeklaruj tablicę liczb całkowitych za pomocą
intArrayOf()
. Istnieją odpowiednie konstruktory lub funkcje tworzenia instancji dla tablic innych typów.
val numbers = intArrayOf(1,2,3)
- Połącz 2 tablice za pomocą operatora
+
.
val numbers = intArrayOf(1,2,3)
val numbers3 = intArrayOf(4,5,6)
val foo2 = numbers3 + numbers
println(foo2[5])
=> 3
- Wypróbuj różne kombinacje zagnieżdżonych tablic i list. Podobnie jak w innych językach możesz zagnieżdżać tablice i listy. Oznacza to, że gdy umieścisz tablicę w tablicy, otrzymasz tablicę tablic, a nie spłaszczoną tablicę zawartości obu tablic. Elementami tablicy mogą być też listy, a elementami list mogą być tablice.
val numbers = intArrayOf(1, 2, 3)
val oceans = listOf("Atlantic", "Pacific")
val oddList = listOf(numbers, oceans, "salmon")
println(oddList)
⇒ [[I@89178b4, [Atlantic, Pacific], salmon]
Pierwszy element, numbers
, to Array
. Jeśli nie użyjesz narzędzia do obsługi tablicy, Kotlin wydrukuje adres zamiast zawartości tablicy.
- Jedną z zalet języka Kotlin jest możliwość inicjowania tablic za pomocą kodu zamiast inicjowania ich wartością 0. Wypróbuj ten przykład:
val array = Array (5) { it * 2 }
println(java.util.Arrays.toString(array))
⇒ [0, 2, 4, 6, 8]
Kod inicjowania znajduje się między nawiasami klamrowymi {}
. W kodzie it
odnosi się do indeksu tablicy, który zaczyna się od 0.
Krok 3. Tworzenie pętli
Gdy masz już listy i tablice, pętla przechodząca przez elementy działa zgodnie z oczekiwaniami.
- Utwórz tablicę. Użyj pętli
for
, aby wykonać iterację tablicy i wydrukować elementy.
val school = arrayOf("shark", "salmon", "minnow")
for (element in school) {
print(element + " ")
}
⇒ shark salmon minnow
- W Kotlinie możesz jednocześnie iterować po elementach i indeksach. Wypróbuj ten przykład:
for ((index, element) in school.withIndex()) {
println("Item at $index is $element\n")
}
⇒ Item at 0 is shark Item at 1 is salmon Item at 2 is minnow
- Wypróbuj różne rozmiary kroków i zakresy. Możesz określić zakresy liczb lub znaków w kolejności alfabetycznej. Podobnie jak w innych językach, nie musisz zwiększać wartości o 1. Możesz cofnąć się za pomocą przycisku
downTo
.
for (i in 1..5) print(i)
⇒ 12345
for (i in 5 downTo 1) print(i)
⇒ 54321
for (i in 3..6 step 2) print(i)
⇒ 35
for (i in 'd'..'g') print (i)
⇒ defg
- Wypróbuj kilka pętli. Podobnie jak inne języki, Kotlin ma pętle
while
, pętledo...while
oraz operatory++
i--
. Kotlin ma też pętlerepeat
.
var bubbles = 0
while (bubbles < 50) {
bubbles++
}
println("$bubbles bubbles in the water\n")
do {
bubbles--
} while (bubbles > 50)
println("$bubbles bubbles in the water\n")
repeat(2) {
println("A fish is swimming")
}
⇒ 50 bubbles in the water 49 bubbles in the water A fish is swimmingA fish is swimming
Kotlin jest bardzo podobny do innych języków, jeśli chodzi o podstawy, takie jak operatory, listy i pętle, ale istnieją pewne istotne różnice.
Te funkcje mogą działać w Kotlinie inaczej niż w innych językach:
- Typów Kotlin nie można konwertować niejawnie – używaj rzutowania.
- Zmienne zadeklarowane za pomocą
val
można przypisać tylko raz. - Zmienne w Kotlinie nie mogą mieć domyślnie wartości null. Użyj
?
, aby umożliwić przyjmowanie wartości null przez zmienne. - W języku Kotlin możesz jednocześnie iterować po indeksach i elementach tablicy w pętli
for
.
Te konstrukcje programistyczne w języku Kotlin są podobne do tych w innych językach:
- Tablice i listy mogą zawierać elementy jednego typu lub różnych typów.
- Tablice i listy można zagnieżdżać.
- Pętle możesz tworzyć za pomocą
for
,while
,do
/while
irepeat
. - Instrukcja
when
to wersja instrukcjiswitch
w języku Kotlin, alewhen
jest bardziej elastyczna.
Dokumentacja języka Kotlin
Jeśli chcesz uzyskać więcej informacji na dowolny temat w tym kursie lub jeśli napotkasz trudności, najlepszym punktem wyjścia będzie strona https://kotlinlang.org.
- Jawna konwersja typu
- Definiowanie zmiennych
- Szablony ciągów znaków
- Wartości dopuszczające wartość null
- Listy
- Tablice
if
,when
,for
,while
?:
(Elvis) operator!!
operator
Samouczki dotyczące języka Kotlin
Witryna https://try.kotlinlang.org zawiera rozbudowane samouczki Kotlin Koans, internetowy interpreter i pełny zestaw dokumentacji z przykładami.
Kurs Udacity
Aby obejrzeć kurs Udacity na ten temat, zobacz Kotlin Bootcamp for Programmers (w języku angielskim).
IntelliJ IDEA
Dokumentację IntelliJ IDEA znajdziesz w witrynie JetBrains.
W tej sekcji znajdziesz listę możliwych zadań domowych dla uczniów, którzy wykonują ten moduł w ramach kursu prowadzonego przez instruktora. Nauczyciel musi:
- W razie potrzeby przypisz pracę domową.
- Poinformuj uczniów, jak przesyłać projekty.
- Oceń zadania domowe.
Instruktorzy mogą korzystać z tych sugestii w dowolnym zakresie i mogą zadawać inne zadania domowe, które uznają za odpowiednie.
Jeśli wykonujesz ten kurs samodzielnie, możesz użyć tych zadań domowych, aby sprawdzić swoją wiedzę.
Odpowiedz na te pytania
Pytanie 1
Które z poniższych deklaracji tworzy niezmienną listę ciągów znaków?
▢ val school = arrayOf("shark", "salmon", "minnow")
▢ var school = arrayOf("shark", "salmon", "minnow")
▢ val school = listOf("shark", "salmon", "minnow")
▢ val school = mutableListOf("shark", "salmon", "minnow")
Pytanie 2
Jaki będzie wynik działania tego kodu?for (i in 3..8 step 2) print(i)
▢ 345678
▢ 468
▢ 38
▢ 357
Pytanie 3
Jaki jest cel znaku zapytania w tym kodzie?var rocks: Int? = 3
▢ Typ zmiennej rocks
nie jest stały.
▢ Zmienna rocks
może mieć wartość null.
▢ Zmiennej rocks
nie można ustawić na wartość null.
▢ Zmienna rocks
nie powinna być od razu inicjowana.
Przejdź do następnej lekcji:
Omówienie kursu, w tym linki do innych ćwiczeń, znajdziesz w artykule „Kotlin Bootcamp for Programmers: Welcome to the course” (w języku angielskim).