Roughly cover the materials in Chapters 7 and 8.
## Strings
+ `String` is the data type for text.
+ A sequence of `Char`
+ `"Text"` and `"t"` are `String`.
+ `'T'` and `'t'` are `Char`.
+ Length: `.length`
+ Template:
+ `$val`
+ `$var`
+ `${expression}`
+ `str[i]`: Access the `i`-th `Char` in a `String` type variable/value `str`.
+ Kotlin is zero-based.
```kotlin
fun main() {
val str = "NCTU"
println("The string $str has length ${str.length}")
println(str[0])
println(str[1])
println(str[2])
println(str[3])
// intended to crash the program
// with StringIndexOutOfBoundsException
println(str[4])
}
```
+ Escape sequences
+ To represent special characters
+ Consider a `Char` to represent `'`
+ `'''` does not work!
+ Use `'\''`
+ Consider a `String` to represent `""`
+ `""""` does not work!
+ Use `"\"\""`
+ Consider a `Char` to represent `\`
+ `'\'` does not work!
+ Use `'\\'`
+ Consider a `String` to represent `$`
+ "$" does not work!
+ Use `"\$"`
+ `\'`: Single quote `'`
+ `\"`: Double quote
+ `\\`: Backslash
+ `\$`: Dollar sign
+ `\t`: Tab
+ `\b`: Backspace
+ `\n`: Newline
+ `\r`: Carriage return
+ `\uXXXX`: Unicode, see [Wikipedia](https://en.wikipedia.org/wiki/List_of_Unicode_characters).
+ [Kotlin Document for String](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-string/)
## Substring Operations
### `substring`
+ Give a slice of the string.
+ Argument:
+ `start: Int`
+ `start: Int, end: Int`
+ `range: IntRange`
```kotlin
fun main() {
val str = "National Chiao Tung University"
// Zero-based: drop the first character N
println(str.substring(1))
// [start, end): start at 't', end at 'i' and 'i' is not included
println(str.substring(2, 3))
// Should be ""
println(str.substring(4, 4))
// Should be "o"
println(str.substring(4..4))
// Does not work: IntProgression is not IntRange
// println(str.substring(10 downTo 0))
}
```
### Index
+ `indexOf`
+ Argument: `char: Char`
+ Return the index of the first occurence
+ `lastIndexOf`
+ Argument: `char: Char`
+ Return the index of the last occurence
+ `indexOfFirst`
+ Argument: `predicate: (Char) -> Boolean`
+ Return the index of the first occurence which satisfies the predicate
+ `indexOfLast`
+ Argument: `predicate: (Char) -> Boolean`
+ Return the index of the last occurence which satisfies the predicate
```kotlin
fun main() {
val str = "National Chiao Tung University"
println(str.indexOf(' '))
println(str.lastIndexOf('l'))
// The first character in lower case and at least 'm'
println(str.indexOfFirst{'m' <= it && it <= 'z'})
// The last character in upper case.
println(str.indexOfLast{'A' <= it && it <= 'Z'})
}
```
### `split`
+ Split the string into a list of substrings.
+ List access: use `[i]` to access the `i`-th element.
+ Destructure: if you know the number of pieces before compile, you may declare more than one variable / value in a line!
```kotlin
fun main() {
val str = "National Chiao Tung University"
val listOfPieces = str.split(" ")
println("String \"$str\" has ${listOfPieces.size} words.")
println("The first is ${listOfPieces[0]}")
println("The last is ${listOfPieces.last()}")
// "destructuring" declaration
// will crash if listOfPieces.size < 4
val (N, C, T, U) = listOfPieces
println("N is $N")
println("C is $C")
println("T is $T")
println("U is $U")
}
```
### `replace`
+ Replace all occurences
+ Usage
+ `(oldChar: Char, newChar: Char)`
+ `(oldString: String, newString: String)`
+ `(regex: Regex, replacement: String)`
+ `(regex: Regex, transform: (MatchResult) -> CharSequence)`
```kotlin
fun main() {
var str = "National Chiao Tung University"
// String is immutable, replace won't change str
// Use assignment to change str
str = str.replace('N', 'n')
println(str)
str = str.replace("Chiao", "Yang")
println(str)
str = str.replace("Tung", "Chiao")
println(str)
str = str.replace(Regex("[aeiou]"), " ")
println(str)
str = str.replace(Regex("[lv]")){
when(it.value) {
"l" -> "1"
"t" -> "7"
"v" -> "\\/"
else -> it.value
}
}
println(str)
}
```
### Type Conversion
+ [`toInt()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-int.html)
+ [`toIntOrNull()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-int-or-null.html)
+ [`toDouble()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-double.html)
+ [`toDoubleOrNull()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-double-or-null.html)
+ Note: [`toLowerCase()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-lower-case.html) is not a type conversion.
### Practice
+ Task 1: From leet to 1337
+ 請參考 [Wikipedia](https://zh.wikipedia.org/wiki/Leet),寫一個函數 `leet(str: String): String`,將字串中正常的英文字母,轉換成非英文字母的 leet 寫法。只要換出來沒英文就可以。
+ Task 2: Word count
+ 寫一個函數 `fun wordCount(str: String): Int` ,計算 `str` 之中有多少個英文字(Word),相同的英文字如果出現數次,按出現次數計算。保證 `str` 中只有英文字母、空白(`' '`)、逗號(`','`)、句號(`'.'`)。
+ Task 3: English number
+ 寫一個函數 `fun number(str: String): Int?`,將英文字 `str` 換算成對應的整數值,如 `one` 將換成 `1`, `zero` 換成 `0`。只需要處理零到九十九萬九千九百九十九之間的整數即可。輸入可能含有大寫字母,函數必須無視大小寫。如果 `str` 並非一個英文數字,請回傳 `null` 。
## Numbers
### Numeric Types
+ Integers
+ Binary numbers
+ Decimal: $1243_{10}=1\times 10^3 + 2\times 10^2 + 4\times 10^1+3\times 10^0$
+ Binary: $1011_2=1\times 2^3+0\times 2^2+1\times 2^1+1\times 2^0=11_{10}$
+ [Two's complement](https://en.wikipedia.org/wiki/Two%27s_complement)
+ `Byte`
+ 8-bit: `-128` to `127`
+ `Short`
+ 16-bit: `-32768` to `32767`
+ `Int`
+ 32-bit: `-2147483648` to `2147483647`
+ `Long`
+ 64-bit: `-9223372036854775808` to `9223372036854775807`
+ [Floating point numbers](https://en.wikipedia.org/wiki/IEEE_754)
+ [Scientific notation](https://en.wikipedia.org/wiki/Scientific_notation)
+ Decimal: $a\times 10^{b}$
+ $a$: significand
+ $b$: exponent
+ Normalized: $1\le a < 10$
+ Significant figures of $1.2304 \times 10^8$ is $5$.
+ We cannot express $\frac{1}{3}$ by scientific notation, since you don't have enough space for infinitely many $3$.
+ Binary: $f\times 2^e$
+ Normalized: $1\le f < 2$
+ Binary fraction number
+ $1.0011=1+2^{-3}+2^{-4}=1+\frac{1}{8}+\frac{1}{16}=\frac{19}{16}=1.1875$
+ $0.1_{10}=\frac{1}{10}=0.0\overline{0011}_2=1.\overline{1001}_2 \times 2^{-4}$
+ `Float`: 32-bit (Single precision)
+ Exponent: $−126\le e \le 127$
+ Significant figures: 24 bit (~7.22 digits)
+ `Double`: 64-bit (Double precision)
+ Exponent: $-1022\le e \le 1023$
+ Significant figures: 53 bit (~15.95 digits)
### Conversion
+ Convert `String` to number
+ With exception: `.toByte()`, `.toShort()`, `toInt()`, `toLong()`, `toFloat()`, `toDouble()`.
+ Without exception: `.toByteOrNull()`, `.toShortOrNull()`, ...
+ Convert `Int` to `Double`
+ Not working
+ Integer division: `1/2` is `0`
+ Working
+ Adds `0.0`
+ Times `1.0`
+ `.toDouble()`
+ Convert `Double` to `Int`
+ [`.toInt()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-double/to-int.html)
+ Try `1.9.toInt()` and `-1.9.toInt()`
+ [`.roundToInt()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.math/round-to-int.html)
+ `import kotlin.math.roundToInt` before use
+ Try
+ `1.5.roundToInt()`
+ `2.5.roundToInt()`
+ `-0.5.roundToInt()`
+ `-1.5.roundToInt()`
+ Convert numbers to `String`
+ Use [`.toString()`](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/to-string.html)
+ Integers: `radix=2` means binary, and `radix=10` means decimal.
+ Default `radix` is `10`
+ Use string template `"$val"`
+ Use formatting string
+ Example:
+ `"%.3f".format(0.12345678)`
+ `"%.4f".format(9.87654321)`
+ See the [doucument](https://docs.oracle.com/javase/8/docs/api/java/util/Formatter.html) for more.