From 111d9d0dbc12c9044ff755c8418c175a5393e026 Mon Sep 17 00:00:00 2001 From: Him188 Date: Fri, 13 Dec 2019 10:22:38 +0800 Subject: [PATCH] Add docs --- .../utils/LockFreeLinkedList.kt | 67 ++++++++++++++++--- 1 file changed, 57 insertions(+), 10 deletions(-) diff --git a/mirai-core/src/commonMain/kotlin/net.mamoe.mirai/utils/LockFreeLinkedList.kt b/mirai-core/src/commonMain/kotlin/net.mamoe.mirai/utils/LockFreeLinkedList.kt index fa26146ba..47fa29268 100644 --- a/mirai-core/src/commonMain/kotlin/net.mamoe.mirai/utils/LockFreeLinkedList.kt +++ b/mirai-core/src/commonMain/kotlin/net.mamoe.mirai/utils/LockFreeLinkedList.kt @@ -4,6 +4,7 @@ package net.mamoe.mirai.utils import kotlinx.atomicfu.AtomicRef import kotlinx.atomicfu.atomic +import net.mamoe.mirai.utils.Node.Companion.equals @MiraiExperimentalAPI @@ -15,7 +16,10 @@ inline fun lockFreeLinkedListOf(vararg elements: E): LockFreeLinkedList = inline fun lockFreeLinkedListOf(): LockFreeLinkedList = LockFreeLinkedList() /** - * 无锁链表实现. 元素值不能为 null + * Implementation of lock-free LinkedList. + * + * Modifying can be performed concurrently. + * Iterating concurrency is guaranteed. // TODO: 2019/12/13 ADD MORE */ @MiraiExperimentalAPI class LockFreeLinkedList : MutableList, RandomAccess { @@ -37,7 +41,7 @@ class LockFreeLinkedList : MutableList, RandomAccess { } internal fun getLinkStucture(): String = buildString { - head.childIterate>({ + head.childIterateReturnsLastSatisfying>({ append(it.toString()) append("->") it.nextNode @@ -253,9 +257,10 @@ class LockFreeLinkedList : MutableList, RandomAccess { private inline fun E.asNode(nextNode: Node): Node = Node(nextNode).apply { nodeValueRef.value = this@asNode } /** - * 使用 [iterator] 进行自我迭代, 直到 [mustBeTrue] 返回 false 时停止迭代. 返回最后一个满足条件的元素 + * Self-iterate using the [iterator], until [mustBeTrue] returns `false`. + * Returns the element at the last time when the [mustBeTrue] returns `true` */ -private inline fun > N.childIterate(iterator: (N) -> N, mustBeTrue: (N) -> Boolean): N { +private inline fun > N.childIterateReturnsLastSatisfying(iterator: (N) -> N, mustBeTrue: (N) -> Boolean): N { if (!mustBeTrue(this)) return this var value: N = this @@ -272,7 +277,8 @@ private inline fun > N.childIterate(iterator: (N) -> N, mustBeTrue: } /** - * 使用 [iterator] 进行自我迭代, 直到 [mustBeTrue] 返回 false 时停止迭代. 返回第一个不满足条件的元素 + * Self-iterate using the [iterator], until [mustBeTrue] returns `false`. + * Returns the element at the first time when the [mustBeTrue] returns `false` */ private inline fun E.childIterateReturnFirstUnsitisfying(iterator: (E) -> E, mustBeTrue: (E) -> Boolean): E { if (!mustBeTrue(this)) return this @@ -291,7 +297,8 @@ private inline fun E.childIterateReturnFirstUnsitisfying(iterator: (E) -> E, } /** - * 使用 [iterator] 进行自我迭代, 直到 [mustBeTrue] 返回 false 时停止迭代. 返回满足条件的元素数量 + * Self-iterate using the [iterator], until [mustBeTrue] returns `false`. + * Returns the count of elements being iterated. */ private inline fun E.countChildIterate(iterator: (E) -> E, mustBeTrue: (E) -> Boolean): Int { var count = 0 @@ -330,6 +337,9 @@ private open class Node( val nodeValueRef: AtomicRef = atomic(null) + /** + * Short cut for accessing [nodeValueRef] + */ inline var nodeValue: E? get() = nodeValueRef.value set(value) { @@ -338,6 +348,10 @@ private open class Node( @Suppress("LeakingThis") val nextNodeRef: AtomicRef> = atomic(nextNode ?: this) + + /** + * Short cut for accessing [nextNodeRef] + */ inline var nextNode: Node get() = nextNodeRef.value set(value) { @@ -345,28 +359,61 @@ private open class Node( } - inline fun iterateWhile(filter: (Node) -> Boolean): Node = this.childIterate>({ it.nextNode }, filter) - + /** + * Returns the former node of the last node whence [filter] returnes true + */ inline fun iterateBeforeFirst(filter: (Node) -> Boolean): Node = - this.childIterate>({ it.nextNode }, { !filter(it) }) + this.childIterateReturnsLastSatisfying>({ it.nextNode }, { !filter(it) }) + /** + * Returns the last node whence [filter] returnes true. + */ inline fun iterateStopOnFirst(filter: (Node) -> Boolean): Node = iterateBeforeFirst(filter).nextNode + + /** + * Returns the former node of next node whose value is not null. + * [Tail] is returned if no node is found + */ @Suppress("NOTHING_TO_INLINE") inline fun iterateBeforeNotnull(): Node = iterateBeforeFirst { it.nodeValue != null } + /** + * Returns the next node which is not [Tail] or [Head] and with a notnull value. + * [Tail] is returned if no node is found + */ @Suppress("NOTHING_TO_INLINE") inline fun nextValidElement(): Node = this.iterateBeforeFirst { !it.isValidElementNode() } + /** + * Returns the next node whose value is not null. + * [Tail] is returned if no node is found + */ @Suppress("NOTHING_TO_INLINE") inline fun nextNotnull(): Node = this.iterateBeforeFirst { it.nodeValueRef.value == null } - inline fun allMatching(filter: (Node) -> Boolean): Boolean = this.iterateWhile(filter) !is Tail + /** + * Check if all the node which is not [Tail] matches the [condition] + * + * Head, which is this, is also being tested. + * [Tail], is not being tested. + */ + inline fun allMatching(condition: (Node) -> Boolean): Boolean = this.childIterateReturnsLastSatisfying>({ it.nextNode }, condition) !is Tail + /** + * Stop on and returns the former element of the element that is [equals] to the [element] + * + * E.g.: for `head <- 1 <- 2 <- 3 <- tail`, `iterateStopOnNodeValue(2)` returns the node whose value is 1 + */ @Suppress("NOTHING_TO_INLINE") inline fun iterateBeforeNodeValue(element: E): Node = this.iterateBeforeFirst { it.nodeValueRef.value == element } + /** + * Stop on and returns the element that is [equals] to the [element] + * + * E.g.: for `head <- 1 <- 2 <- 3 <- tail`, `iterateStopOnNodeValue(2)` returns the node whose value is 2 + */ @Suppress("NOTHING_TO_INLINE") inline fun iterateStopOnNodeValue(element: E): Node = this.iterateBeforeNodeValue(element).nextNode }