5.3.6 过滤操作函数
take(n: Int): List<T> 挑出该集合前n个元素的子集合
函数定义:
1. public fun <T> Iterable<T>.take(n: Int): List<T> {
2. require(n >= 0) { "Requested element count $n is less than zero." }
3. if (n == 0) return emptyList()
4. if (this is Collection<T>) {
5. if (n >= size) return toList()
6. if (n == 1) return listOf(first())
7. }
8. var count = 0
9. val list = ArrayList<T>(n)
10. for (item in this) {
11. if (count++ == n)
12. break
13. list.add(item)
14. }
15. return list.optimizeReadOnlyList()
16. }
如果n等于0,返回空集;如果n大于集合size,返回该集合。
代码示例:
1. >>> val list = listOf("a","b","c")
2. >>> list
3. [a, b, c]
4. >>> list.take(2)
5. [a, b]
6. >>> list.take(10)
7. [a, b, c]
8. >>> list.take(0)
9. []
11. ```#### `takeWhile(predicate: (T) -> Boolean): List<T>` 挑出满足条件的元素的子集合
13. 函数定义:
15. ```kotlin
16. public inline fun <T> Iterable<T>.takeWhile(predicate: (T) -> Boolean): List<T> {
17. val list = ArrayList<T>()
18. for (item in this) {
19. if (!predicate(item))
20. break
21. list.add(item)
22. }
23. return list
24. }
从第一个元素开始,判断是否满足predicate为true,如果满足条件的元素就丢到返回ArrayList中。只要遇到任何一个元素不满足条件,就结束循环,返回list 。
代码示例:
1. >>> val list = listOf(1,2,4,6,8,9)
2. >>> list.takeWhile({it%2==0})
3. []
4. >>> list.takeWhile({it%2==1})
5. [1]
7. >>> val list = listOf(2,4,6,8,9,11,12,16)
8. >>> list.takeWhile({it%2==0})
9. [2, 4, 6, 8]
11. ```#### `takeLast` 挑出后n个元素的子集合
13. 函数定义:
15. ```kotlin
16. public fun <T> List<T>.takeLast(n: Int): List<T> {
17. require(n >= 0) { "Requested element count $n is less than zero." }
18. if (n == 0) return emptyList()
19. val size = size
20. if (n >= size) return toList()
21. if (n == 1) return listOf(last())
22. val list = ArrayList<T>(n)
23. if (this is RandomAccess) {
24. for (index in size - n .. size - 1)
25. list.add(this[index])
26. } else {
27. for (item in listIterator(n))
28. list.add(item)
29. }
30. return list
31. }
从集合倒数n个元素起,取出到最后一个元素的子集合。如果传入0,返回空集。如果传入n大于集合size,返回整个集合。如果传入负数,直接抛出IllegalArgumentException。
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.takeLast(0)
3. []
4. >>> list.takeLast(3)
5. [11, 12, 16]
6. >>> list.takeLast(100)
7. [2, 4, 6, 8, 9, 11, 12, 16]
8. >>> list.takeLast(-1)
9. java.lang.IllegalArgumentException: Requested element count -1 is less than zero.
10. at kotlin.collections.CollectionsKt___CollectionsKt.takeLast(_Collections.kt:734)
12. ```#### `takeLastWhile(predicate: (T) -> Boolean)` 从最后开始挑出满足条件元素的子集合
14. 函数定义:
16. ```kotlin
17. public inline fun <T> List<T>.takeLastWhile(predicate: (T) -> Boolean): List<T> {
18. if (isEmpty())
19. return emptyList()
20. val iterator = listIterator(size)
21. while (iterator.hasPrevious()) {
22. if (!predicate(iterator.previous())) {
23. iterator.next()
24. val expectedSize = size - iterator.nextIndex()
25. if (expectedSize == 0) return emptyList()
26. return ArrayList<T>(expectedSize).apply {
27. while (iterator.hasNext())
28. add(iterator.next())
29. }
30. }
31. }
32. return toList()
33. }
反方向取满足条件的元素,遇到不满足的元素,直接终止循环,并返回子集合。
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.takeLastWhile({it%2==0})
3. [12, 16]
4. ```#### `drop(n: Int)` 去除前n个元素返回剩下的元素的子集合
6. 函数定义:
8. ```kotlin
9. public fun <T> Iterable<T>.drop(n: Int): List<T> {
10. require(n >= 0) { "Requested element count $n is less than zero." }
11. if (n == 0) return toList()
12. val list: ArrayList<T>
13. if (this is Collection<*>) {
14. val resultSize = size - n
15. if (resultSize <= 0)
16. return emptyList()
17. if (resultSize == 1)
18. return listOf(last())
19. list = ArrayList<T>(resultSize)
20. if (this is List<T>) {
21. if (this is RandomAccess) {
22. for (index in n..size - 1)
23. list.add(this[index])
24. } else {
25. for (item in listIterator(n))
26. list.add(item)
27. }
28. return list
29. }
30. }
31. else {
32. list = ArrayList<T>()
33. }
34. var count = 0
35. for (item in this) {
36. if (count++ >= n) list.add(item)
37. }
38. return list.optimizeReadOnlyList()
39. }
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.drop(5)
3. [11, 12, 16]
4. >>> list.drop(100)
5. []
6. >>> list.drop(0)
7. [2, 4, 6, 8, 9, 11, 12, 16]
8. >>> list.drop(-1)
9. java.lang.IllegalArgumentException: Requested element count -1 is less than zero.
10. at kotlin.collections.CollectionsKt___CollectionsKt.drop(_Collections.kt:538)
11. ```#### `dropWhile(predicate: (T) -> Boolean)` 去除满足条件的元素返回剩下的元素的子集合
13. 函数定义:
15. ```kotlin
16. public inline fun <T> Iterable<T>.dropWhile(predicate: (T) -> Boolean): List<T> {
17. var yielding = false
18. val list = ArrayList<T>()
19. for (item in this)
20. if (yielding)
21. list.add(item)
22. else if (!predicate(item)) {
23. list.add(item)
24. yielding = true
25. }
26. return list
27. }
去除满足条件的元素,当遇到一个不满足条件的元素时,中止操作,返回剩下的元素子集合。
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.dropWhile({it%2==0})
3. [9, 11, 12, 16]
5. ```#### `dropLast(n: Int)` 从最后去除n个元素
7. 函数定义:
9. ```kotlin
10. public fun <T> List<T>.dropLast(n: Int): List<T> {
11. require(n >= 0) { "Requested element count $n is less than zero." }
12. return take((size - n).coerceAtLeast(0))
13. }
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.dropLast(3)
3. [2, 4, 6, 8, 9]
4. >>> list.dropLast(100)
5. []
6. >>> list.dropLast(0)
7. [2, 4, 6, 8, 9, 11, 12, 16]
8. >>> list.dropLast(-1)
9. java.lang.IllegalArgumentException: Requested element count -1 is less than zero.
10. at kotlin.collections.CollectionsKt___CollectionsKt.dropLast(_Collections.kt:573)
11. ```#### `dropLastWhile(predicate: (T) -> Boolean)` 从最后满足条件的元素
13. 函数定义:
15. ```kotlin
16. public inline fun <T> List<T>.dropLastWhile(predicate: (T) -> Boolean): List<T> {
17. if (!isEmpty()) {
18. val iterator = listIterator(size)
19. while (iterator.hasPrevious()) {
20. if (!predicate(iterator.previous())) {
21. return take(iterator.nextIndex() + 1)
22. }
23. }
24. }
25. return emptyList()
26. }
代码示例:
1. >>> val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list.dropLastWhile({it%2==0})
3. [2, 4, 6, 8, 9, 11]
4. ```#### `slice(indices: IntRange)` 取开始下标至结束下标元素子集合
6. 函数定义:
8. ```kotlin
9. public fun <T> List<T>.slice(indices: IntRange): List<T> {
10. if (indices.isEmpty()) return listOf()
11. return this.subList(indices.start, indices.endInclusive + 1).toList()
12. }
代码示例:
1. val list = listOf(2,4,6,8,9,11,12,16)
2. >>> list
3. [2, 4, 6, 8, 9, 11, 12, 16]
4. >>> list.slice(1..3)
5. [4, 6, 8]
6. >>> list.slice(2..7)
7. [6, 8, 9, 11, 12, 16]
8. >>> list
9. [2, 4, 6, 8, 9, 11, 12, 16]
10. >>> list.slice(1..3)
11. [4, 6, 8]
12. >>> list.slice(2..7)
13. [6, 8, 9, 11, 12, 16]
14. ```#### `slice(indices: Iterable<Int>) `返回指定下标的元素子集合
16. 函数定义:
18. ```kotlin
19. public fun <T> List<T>.slice(indices: Iterable<Int>): List<T> {
20. val size = indices.collectionSizeOrDefault(10)
21. if (size == 0) return emptyList()
22. val list = ArrayList<T>(size)
23. for (index in indices) {
24. list.add(get(index))
25. }
26. return list
27. }
这个函数从签名上看,不是那么简单直接。从函数的定义看,这里的indices是当做原来集合的下标来使用的。
代码示例:
1. >>> list
2. [2, 4, 6, 8, 9, 11, 12, 16]
3. >>> list.slice(listOf(2,4,6))
4. [6, 9, 12]
我们可以看出,这里是取出下标为2,4,6的元素。而不是直观理解上的,去掉元素2,4,6。#### filterTo(destination: C, predicate: (T) -> Boolean) 过滤出满足条件的元素并赋值给destination
函数定义:
1. public inline fun <T, C : MutableCollection<in T>> Iterable<T>.filterTo(destination: C, predicate: (T) -> Boolean): C {
2. for (element in this) if (predicate(element)) destination.add(element)
3. return destination
4. }
把满足过滤条件的元素组成的子集合赋值给入参destination。
代码示例:
1. >>> val list = listOf(1,2,3,4,5,6,7)
2. >>> val dest = mutableListOf<Int>()
3. >>> list.filterTo(dest,{it>3})
4. [4, 5, 6, 7]
5. >>> dest
6. [4, 5, 6, 7]
7. ```#### `filter(predicate: (T) -> Boolean)`过滤出满足条件的元素组成的子集合
9. 函数定义:
11. ```kotlin
12. public inline fun <T> Iterable<T>.filter(predicate: (T) -> Boolean): List<T> {
13. return filterTo(ArrayList<T>(), predicate)
14. }
相对于filterTo函数,filter函数更加简单易用。从源码我们可以看出,filter函数直接调用的filterTo(ArrayList<T>(), predicate), 其中入参destination被直接默认赋值为ArrayList<T>()。
代码示例:
1. >>> val list = listOf(1,2,3,4,5,6,7)
2. >>> list.filter({it>3})
3. [4, 5, 6, 7]
另外,还有下面常用的过滤函数:
filterNot(predicate: (T) -> Boolean), 用来过滤所有不满足条件的元素 ;
filterNotNull() 过滤掉null元素。
