Simulacrum, từ simulacrum Latin, là một sự bắt chước, giả mạo hoặc hư cấu. Khái niệm này được liên kết với mô phỏng, đó là hành động mô phỏng .Một...
Học ngôn ngữ lập trình Kotlin | Android Developers
Khai báo biến
Kotlin sử dụng hai từ khoá để khai báo các biến: val
và var
.
- Sử dụng
val
cho biến có giá trị không bao giờ thay đổi. Bạn không thể gán lại giá trị
cho biến đã khai báo bằngval
. - Sử dụng
var
cho biến có giá trị có thể thay đổi.
Trong ví dụ bên dưới, count
là biến thuộc loại Int
được gán
giá trị ban đầu là 10
:
var count: Int = 10
Int
là loại dữ liệu biểu thị một số nguyên, là một trong nhiều loại dạng số có thể biểu thị bằng Kotlin. Giống như các ngôn ngữ khác, bạn cũng có thể sử dụng
Byte
, Short
, Long
, Float
và Double
tuỳ thuộc vào dữ liệu dạng số của mình.
Bạn đang đọc: Học ngôn ngữ lập trình Kotlin | Android Developers
Từ khoá var
có nghĩa là bạn có thể gán lại các giá trị cho count
nếu cần. Ví
dụ: bạn có thể thay đổi giá trị của count
từ 10
thành 15
:
var count: Int = 10
count = 15
Tuy nhiên, bạn không được thay đổi một số giá trị. Hãy cân nhắc dùng một String
có tên là
languageName
. Nếu muốn đảm bảo rằng languageName
luôn có giá trị “Kotlin”, thì bạn có thể khai báo languageName
bằng cách sử dụng từ khoá val
:
val languageName: String = "Kotlin"
Các từ khoá này cho phép bạn nêu rõ những gì có thể thay đổi. Hãy tận dụng các từ khoá này nếu cần. Nếu một tham chiếu biến phải có khả năng chỉ định lại giá trị, thì hãy khai báo tham chiếu đó là var
. Nếu không, hãy sử dụng val
.
Suy luận loại dữ liệu
Tiếp tục ví dụ trước, khi bạn chỉ định giá trị ban đầu cho
languageName
, trình biên dịch Kotlin có thể suy ra loại dữ liệu dựa trên loại giá trị
được chỉ định.
Vì giá trị của "Kotlin"
là thuộc loại String
, nên trình biên dịch suy ra rằng languageName
cũng là một String
. Xin lưu ý rằng Kotlin là một ngôn ngữ loại tĩnh. Điều này có nghĩa là loại dữ liệu này sẽ được phân giải tại thời điểm biên dịch và không bao giờ
thay đổi.
Trong ví dụ sau, languageName
được suy ra là String
. Vì vậy, bạn không thể
gọi bất kỳ hàm nào không thuộc lớp String
:
val languageName = "Kotlin"
val upperCaseName = languageName.toUpperCase()
// Fails to compile
languageName.inc()
toUpperCase()
là một hàm chỉ có thể được gọi trên các biến thuộc loại
String
. Vì trình biên dịch Kotlin đã suy ra languageName
là String
,
nên bạn có thể gọi toUpperCase()
một cách an toàn. Tuy nhiên, inc()
là hàm toán tử Int
nên không thể gọi hàm này trên String
. Phương pháp suy luận loại dữ liệu của Kotlin giúp mã của bạn súc tích và an toàn cho loại dữ liệu.
Kiểm tra an toàn của giá trị rỗng
Ở 1 số ít ngôn ngữ, bạn hoàn toàn có thể khai báo biến thuộc loại tham chiếu mà không phân phối giá trị rõ ràng bắt đầu. Trong những trường hợp này, những biến thường chứa một giá trị rỗng. Theo mặc định, những biến Kotlin không hề chứa giá trị rỗng. Điều này có nghĩa là đoạn mã sau đây không hợp lệ :
// Fails to compile
val languageName: String = null
Để chứa được giá trị rỗng, biến phải thuộc loại có thể nhận giá trị rỗng (nullable). Bạn có thể chỉ định một biến là có thể mang giá trị rỗng bằng cách thêm ?
vào hậu tố của loại dữ liệu đó, như trong ví dụ sau:
val languageName: String? = null
Với loại String?
, bạn có thể gán giá trị String
hoặc null
cho languageName
.
Bạn phải xử lý cẩn thận các biến có thể nhận giá trị rỗng hoặc có nguy cơ bị lỗi
NullPointerException
. Ví dụ: trong Java, nếu bạn cố gọi một phương thức
trên một giá trị rỗng, thì chương trình của bạn sẽ gặp sự cố.
Kotlin phân phối một số ít chính sách để giải quyết và xử lý bảo đảm an toàn những biến hoàn toàn có thể nhận giá trị rỗng. Để biết thêm thông tin, hãy xem Các mẫu Kotlin thông dụng trên Android : Tính chất rỗng .
Câu lệnh có điều kiện
Kotlin có một số cơ chế để triển khai logic có điều kiện. Cách phổ biến nhất trong số này là câu lệnh if-else. Nếu một biểu thức được bao bọc trong
dấu ngoặc vuông bên cạnh một từ khoá if
có giá trị là true
, thì mã trong nhánh đó (tức là mã đứng sau được bọc trong dấu ngoặc nhọn) sẽ thực thi. Nếu không, mã trong nhánh else
sẽ được thực thi.
if (count == 42) {
println("I have the answer.")
} else {
println("The answer eludes me.")
}
Bạn có thể biểu thị nhiều điều kiện bằng cách sử dụng else if
. Cách này cho phép bạn biểu thị logic chi tiết và phức tạp hơn trong một câu lệnh đơn có điều kiện, như trong ví dụ sau:
if (count == 42) {
println("I have the answer.")
} else if (count > 35) {
println("The answer is close.")
} else {
println("The answer eludes me.")
}
Câu lệnh có điều kiện rất hữu ích trong việc thể hiện logic trạng thái, nhưng có thể bạn sẽ nhận ra mình phải lặp lại mã khi viết. Trong ví dụ trên, bạn
chỉ cần xuất String
ở mỗi nhánh ra màn hình. Để tránh phải lặp lại mã, Kotlin cung cấp
các biểu thức có điều kiện. Bạn có thể viết lại ví dụ trước như sau:
val answerString: String = if (count == 42) {
"I have the answer."
} else if (count > 35) {
"The answer is close."
} else {
"The answer eludes me."
}
println(answerString)
Mỗi nhánh có điều kiện sẽ ngầm trả về kết quả của biểu thức trên dòng cuối cùng, vì vậy, bạn không cần sử dụng từ khoá return
. Do kết quả của cả 3 nhánh đều thuộc loại String
, nên kết quả của biểu thức if-else cũng
thuộc loại String
. Trong ví dụ này, answerString
được gán một giá trị ban đầu
từ kết quả của biểu thức if-else. Bạn có thể dùng thông tin dự đoán loại để
bỏ mục khai báo rõ ràng cho loại của answerString
, nhưng bạn nên đưa thông tin đó vào cho minh bạch.
Lưu ý:Kotlin không gồm có thuộc tính truyền thống lịch sử toán tử ba ngôi, thay vào đó, Kotlin ưu tiên sử dụng biểu thức có điều kiện kèm theo .
Khi độ phức tạp của câu lệnh có điều kiện kèm theo tăng lên, bạn hoàn toàn có thể xem xét thay thế sửa chữa biểu thức if-else bằng biểu thức when, như trong ví dụ sau :
val answerString = when {
count == 42 -> "I have the answer."
count > 35 -> "The answer is close."
else -> "The answer eludes me."
}
println(answerString)
Mỗi nhánh trong biểu thức when
được biểu thị bằng một điều kiện, một mũi tên
(->
) và một kết quả. Nếu điều kiện ở phía bên trái của mũi tên đạt giá trị true, thì kết quả của biểu thức ở bên phải sẽ được
trả về. Xin lưu ý rằng quá trình thực thi không nói tiếp từ nhánh này sang nhánh kia.
Mã trong ví dụ về biểu thức when
có chức năng tương đương với mã trong ví dụ trước nhưng được đánh giá là dễ đọc hơn.
Các câu điều kiện kèm theo của Kotlin làm điển hình nổi bật một tính năng can đảm và mạnh mẽ hơn của ngôn ngữ này, đó là smart casting ( truyền thông minh ). Thay vì sử dụng toán tử bảo đảm an toàn cho lệnh gọi hoặc toán tử xác nhận khác rỗng để thao tác với những giá trị hoàn toàn có thể rỗng, bạn hoàn toàn có thể kiểm tra xem một biến có chứa tham chiếu đến giá trị rỗng hay không bằng cách sử dụng câu lệnh có điều kiện kèm theo, như trong ví dụ sau :
val languageName: String? = null
if (languageName != null) {
// No need to write languageName?.toUpperCase()
println(languageName.toUpperCase())
}
Trong nhánh có điều kiện, languageName
có thể được coi là không thể nhận giá trị rỗng.
Kotlin đủ thông minh để nhận ra rằng điều kiện để thực thi nhánh
là languageName
không chứa giá trị rỗng. Vì vậy, bạn không phải coi
languageName
là có thể rỗng trong nhánh đó. Smart casting hoạt động
để kiểm tra giá trị rỗng,
kiểm tra loại
hoặc bất kỳ điều kiện nào đáp ứng
contract.
Hàm
Bạn hoàn toàn có thể nhóm một hoặc nhiều biểu thức vào một hàm. Thay vì lặp lại cùng một chuỗi biểu thức mỗi khi cần tác dụng, bạn hoàn toàn có thể phủ bọc biểu thức trong một hàm và gọi hàm đó .
Để khai báo hàm, hãy sử dụng từ khoá fun
đứng trước tên hàm.
Tiếp theo, hãy xác định các loại dữ liệu đầu vào mà hàm của bạn lấy (nếu có) và khai báo
loại dữ liệu đầu ra mà hàm trả về. Phần body của hàm là nơi bạn xác định biểu thức được gọi khi hàm được kích hoạt.
Dựa trên các ví dụ trước, dưới đây là một hàm Kotlin hoàn chỉnh:
fun generateAnswerString(): String {
val answerString = if (count == 42) {
"I have the answer."
} else {
"The answer eludes me"
}
return answerString
}
Hàm trong ví dụ trên có tên generateAnswerString
. Hàm này không lấy dữ liệu đầu vào nào. Hàm này xuất ra kết quả thuộc loại String
. Để gọi một hàm, hãy sử dụng tên của hàm đó, theo sau là toán tử kích hoạt (()
). Trong
ví dụ dưới đây, biến answerString
được khởi tạo bằng kết quả từ
generateAnswerString()
.
val answerString = generateAnswerString()
Các hàm hoàn toàn có thể lấy đối số làm dữ liệu nguồn vào, như trong ví dụ sau :
fun generateAnswerString(countThreshold: Int): String {
val answerString = if (count > countThreshold) {
"I have the answer."
} else {
"The answer eludes me."
}
return answerString
}
Khi khai báo một hàm, bạn có thể chỉ định số lượng đối số và loại
đối số bất kỳ. Trong ví dụ trên, generateAnswerString()
lấy một đối số có tên là
countThreshold
thuộc loại Int
. Trong hàm, bạn có thể tham chiếu đến đối số
bằng cách sử dụng tên của đối số đó.
Khi gọi hàm này, bạn phải gồm có một đối số trong dấu ngoặc đơn của lệnh gọi hàm :
val answerString = generateAnswerString(42)
Đơn giản hoá việc khai báo hàm
generateAnswerString()
là một hàm khá đơn giản. Hàm này khai báo một biến rồi trả về ngay lập tức. Khi kết quả của một biểu thức đơn được trả về từ một hàm, bạn có thể bỏ qua việc khai báo biến cục bộ bằng cách trực tiếp trả về kết quả của biểu thức if-else có trong hàm, như trong ví dụ sau:
fun generateAnswerString(countThreshold: Int): String {
return if (count > countThreshold) {
"I have the answer."
} else {
"The answer eludes me."
}
}
Bạn cũng hoàn toàn có thể thay thế sửa chữa từ khóa trả lại bằng toán tử chỉ định :
fun generateAnswerString(countThreshold: Int): String = if (count > countThreshold) {
"I have the answer"
} else {
"The answer eludes me"
}
Hàm ẩn danh
Không phải hàm nào cũng cần đặt tên. Một số hàm được xác lập trực tiếp bằng tài liệu nguồn vào và đầu ra. Những hàm này được gọi là hàm ẩn danh. Bạn hoàn toàn có thể giữ lại tham chiếu đến một hàm ẩn danh bằng cách sử dụng tham chiếu này để gọi hàm ẩn danh sau này. Bạn cũng hoàn toàn có thể truyền tham chiếu trong khắp ứng dụng của mình, giống như những loại tham chiếu khác .
val stringLengthFunc: (String) -> Int = { input ->
input.length
}
Giống như những hàm có tên, hàm ẩn danh hoàn toàn có thể chứa số lượng biểu thức bất kể. Giá trị được trả về của hàm là hiệu quả của biểu thức ở đầu cuối .
Trong ví dụ trên, stringLengthFunc
chứa tham chiếu đến một hàm ẩn danh. Hàm ẩn danh này
lấy String
làm dữ liệu đầu vào, rồi trả về dữ liệu đầu ra là độ dài của dữ liệu đầu vào
String
, thuộc loại Int
. Vì vậy, loại hàm được biểu thị là (String) -> Int
. Tuy nhiên, mã này không có khả năng kích hoạt hàm đó.
Để truy xuất kết quả của hàm, bạn phải kích hoạt hàm này như cách bạn thực hiện với hàm có tên. Bạn phải cung cấp String
khi gọi stringLengthFunc
, như
trong ví dụ sau:
val stringLengthFunc: (String) -> Int = { input ->
input.length
}
val stringLength: Int = stringLengthFunc("Android")
Hàm bậc cao
Một hàm hoàn toàn có thể nhận một hàm khác làm đối số. Các hàm sử dụng những hàm khác làm đối số được gọi là hàm bậc cao hơn. Mẫu này rất có ích trong việc tiếp xúc giữa những thành phần, giống như cách bạn sử dụng giao diện gọi lại trong Java .
Dưới đây là ví dụ về một hàm bậc cao :
fun stringMapper(str: String, mapper: (String) -> Int): Int {
// Invoke function
return mapper(str)
}
Hàm stringMapper()
lấy String
cùng với một hàm
lấy giá trị Int
từ String
mà bạn truyền vào.
Bạn có thể gọi stringMapper()
bằng cách truyền String
và một hàm thoả mãn
thông số đầu vào còn lại, tức là một hàm lấy String
làm
dữ liệu đầu vào và xuất Int
. như trong ví dụ sau:
stringMapper("Android", { input ->
input.length
})
Nếu hàm ẩn danh là tham số cuối được xác lập trong một hàm, thì bạn hoàn toàn có thể truyền hàm đó bên ngoài dấu ngoặc đơn dùng để kích hoạt hàm, như trong ví dụ sau :
stringMapper("Android") { input ->
input.length
}
Các hàm ẩn danh có trong thư viện chuẩn của Kotlin. Để biết thêm thông tin, hãy xem bài viết Các hàm bậc cao và Lambda .
Lớp
Tất cả các loại dữ liệu được đề cập đến nay đều được tích hợp vào ngôn ngữ lập trình Kotlin. Nếu muốn thêm loại của riêng mình, bạn có thể xác định một lớp
bằng cách sử dụng từ khoá class
như trong ví dụ sau:
class Car
Thuộc tính
Lớp biểu thị trạng thái bằng thuộc tính. Thuộc tính là một biến ở cấp độ lớp, nó có thể bao gồm một phương thức getter, setter và trường dự phòng.
Giống như ô tô phải có bánh xe mới chạy được, bạn có thể thêm danh sách các đối tượng Wheel
dưới dạng một
thuộc tính của Car
, như trong ví dụ sau:
class Car {
val wheels = listOf()
}
Xin lưu ý rằng wheels
là một public val
, có nghĩa là bạn có thể truy cập vào wheels
từ
bên ngoài lớp Car
và bạn không thể chỉ định lại thuộc tính này. Nếu muốn có
một thực thể của Car
, trước tiên, bạn phải gọi hàm dựng của thực thể đó. Từ đó, bạn có thể truy cập mọi thuộc tính cho phép truy cập.
val car = Car() // construct a Car
val wheels = car.wheels // retrieve the wheels value from the Car
Nếu muốn kiểm soát và điều chỉnh bánh xe của mình, bạn hoàn toàn có thể xác lập một hàm dựng tùy chỉnh có trách nhiệm chỉ định cách khởi tạo những thuộc tính trong lớp của bạn :
class Car(val wheels: List)
Trong ví dụ ở trên, hàm dựng lớp lấy List
làm đối số hàm dựng và sử dụng đối số đó để khởi tạo thuộc tính wheels
.
Hàm trong lớp và đóng gói lớp
Lớp sử dụng những hàm để thiết kế xây dựng quy mô hành vi. Hàm hoàn toàn có thể sửa đổi trạng thái, giúp bạn chỉ cung ứng tài liệu mà bạn muốn phân phối. Khả năng trấn áp quyền truy vấn này thuộc về một khái niệm rộng hơn trong lập trình hướng đối tượng người dùng, đó là đóng gói .
Trong ví dụ sau, thuộc tính doorLock
được đặt ở chế độ riêng tư, tách khỏi mọi nội dung
bên ngoài lớp Car
. Để mở khoá xe ô tô, bạn phải gọi hàm unlockDoor()
, hàm này truyền một khoá hợp lệ, như trong ví dụ sau:
class Car(val wheels: List) {
private val doorLock: DoorLock = ...
fun unlockDoor(key: Key): Boolean {
// Return true if key is valid for door lock, false otherwise
}
}
Nếu muốn tuỳ chỉnh cách tham chiếu một thuộc tính, bạn có thể cung cấp phương thức getter và setter tuỳ chỉnh. Ví dụ: nếu muốn cung cấp phương thức getter
của một thuộc tính, đồng thời hạn chế quyền truy cập vào phương thức setter của thuộc tính đó, bạn có thể chỉ định phương thức setter đó là
private
:
class Car(val wheels: List) {
private val doorLock: DoorLock = ...
var gallonsOfFuelInTank: Int = 15
private set
fun unlockDoor(key: Key): Boolean {
// Return true if key is valid for door lock, false otherwise
}
}
Với sự phối hợp giữa thuộc tính và hàm, bạn hoàn toàn có thể tạo lớp kiến thiết xây dựng quy mô cho toàn bộ những loại đối tượng người tiêu dùng .
Khả năng tương thích
Một trong những tính năng quan trọng nhất của Kotlin là năng lực tương tác linh động với Java. Vì mã Kotlin tổng hợp thành mã byte VM, nên mã Kotlin của bạn hoàn toàn có thể gọi trực tiếp vào mã Java và ngược lại. Điều này có nghĩa là bạn hoàn toàn có thể tận dụng những thư viện Java hiện có ngay trên Kotlin. Ngoài ra, phần nhiều API của Android được viết bằng Java và bạn hoàn toàn có thể gọi trực tiếp những API đó trên Kotlin .
Các bước tiếp theo
Kotlin là một ngôn ngữ linh động và trong thực tiễn với năng lực tương hỗ và khuynh hướng tăng trưởng ngày càng tăng. Nếu chưa dùng Kotlin khi nào, bạn nên thử ngay. Để biết những bước tiếp theo, hãy xem tài liệu chính thức về Kotlin và hướng dẫn cách vận dụng những mẫu Kotlin phổ cập trong ứng dụng Android của bạn .
Source: https://vh2.com.vn
Category : Tin Học