From 745a7ad66ef125d3f0b00de455109f8e62f2fa58 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Sat, 5 Feb 2022 04:27:10 +0700 Subject: [PATCH 01/59] Add complete constant folding in kmath-ast by introducing TypedMst, some minor changes --- README.md | 6 + kmath-ast/README.md | 63 ++++--- kmath-ast/docs/README-TEMPLATE.md | 114 +++++++---- .../space/kscience/kmath/ast/TypedMst.kt | 177 ++++++++++++++++++ .../kscience/kmath/ast/evaluateConstants.kt | 93 +++++++++ .../space/kscience/kmath/ast/TestFolding.kt | 52 +++++ .../space/kscience/kmath/estree/estree.kt | 89 +++------ .../kmath/estree/internal/ESTreeBuilder.kt | 2 +- .../kmath/wasm/internal/WasmBuilder.kt | 67 +++---- .../kotlin/space/kscience/kmath/wasm/wasm.kt | 30 ++- .../kotlin/space/kscience/kmath/asm/asm.kt | 135 +++++++------ .../kmath/asm/internal/GenericAsmBuilder.kt | 8 +- .../kmath/asm/internal/PrimitiveAsmBuilder.kt | 82 +++----- .../kmath/asm/internal/codegenUtils.kt | 8 +- .../FunctionalExpressionAlgebra.kt | 4 +- .../space/kscience/kmath/expressions/MST.kt | 4 +- 16 files changed, 622 insertions(+), 312 deletions(-) create mode 100644 kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt create mode 100644 kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt create mode 100644 kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt diff --git a/README.md b/README.md index 92260716e..99dd6d00f 100644 --- a/README.md +++ b/README.md @@ -247,6 +247,12 @@ One can still use generic algebras though. > **Maturity**: PROTOTYPE
+* ### [kmath-tensorflow](kmath-tensorflow) +> +> +> **Maturity**: PROTOTYPE +
+ * ### [kmath-tensors](kmath-tensors) > > diff --git a/kmath-ast/README.md b/kmath-ast/README.md index 5e3366881..bedf17486 100644 --- a/kmath-ast/README.md +++ b/kmath-ast/README.md @@ -1,6 +1,6 @@ # Module kmath-ast -Performance and visualization extensions to MST API. +Extensions to MST API: transformations, dynamic compilation and visualization. - [expression-language](src/commonMain/kotlin/space/kscience/kmath/ast/parser.kt) : Expression language and its parser - [mst-jvm-codegen](src/jvmMain/kotlin/space/kscience/kmath/asm/asm.kt) : Dynamic MST to JVM bytecode compiler @@ -35,6 +35,26 @@ dependencies { } ``` +## Parsing expressions + +In this module there is a parser from human-readable strings like `"x^3-x+3"` (in the more specific [grammar](reference/ArithmeticsEvaluator.g4)) to MST instances. + +Supported literals: +1. Constants and variables (consist of latin letters, digits and underscores, can't start with digit): `x`, `_Abc2`. +2. Numbers: `123`, `1.02`, `1e10`, `1e-10`, `1.0e+3`—all parsed either as `kotlin.Long` or `kotlin.Double`. + +Supported binary operators (from the highest precedence to the lowest one): +1. `^` +2. `*`, `/` +3. `+`, `-` + +Supported unary operator: +1. `-`, e. g. `-x` + +Arbitrary unary and binary functions are also supported: names consist of latin letters, digits and underscores, can't start with digit. Examples: +1. `sin(x)` +2. `add(x, y)` + ## Dynamic expression code generation ### On JVM @@ -42,48 +62,41 @@ dependencies { `kmath-ast` JVM module supports runtime code generation to eliminate overhead of tree traversal. Code generator builds a special implementation of `Expression` with implemented `invoke` function. -For example, the following builder: +For example, the following code: ```kotlin -import space.kscience.kmath.expressions.Symbol.Companion.x -import space.kscience.kmath.expressions.* -import space.kscience.kmath.operations.* -import space.kscience.kmath.asm.* +import space.kscience.kmath.asm.compileToExpression +import space.kscience.kmath.complex.ComplexField -MstField { x + 2 }.compileToExpression(DoubleField) -``` +"x+2".parseMath().compileToExpression(ComplexField) +``` -... leads to generation of bytecode, which can be decompiled to the following Java class: +… leads to generation of bytecode, which can be decompiled to the following Java class: ```java -package space.kscience.kmath.asm.generated; - import java.util.Map; - import kotlin.jvm.functions.Function2; import space.kscience.kmath.asm.internal.MapIntrinsics; +import space.kscience.kmath.complex.Complex; import space.kscience.kmath.expressions.Expression; import space.kscience.kmath.expressions.Symbol; -public final class AsmCompiledExpression_45045_0 implements Expression { +public final class CompiledExpression_45045_0 implements Expression { private final Object[] constants; - public final Double invoke(Map arguments) { - return (Double) ((Function2) this.constants[0]).invoke((Double) MapIntrinsics.getOrFail(arguments, "x"), 2); - } - - public AsmCompiledExpression_45045_0(Object[] constants) { - this.constants = constants; + public Complex invoke(Map arguments) { + Complex var2 = (Complex)MapIntrinsics.getOrFail(arguments, "x"); + return (Complex)((Function2)this.constants[0]).invoke(var2, (Complex)this.constants[1]); } } - ``` -#### Known issues +Setting JVM system property `space.kscience.kmath.ast.dump.generated.classes` to `1` makes the translator dump class files to program's working directory, so they can be reviewed manually. -- The same classes may be generated and loaded twice, so it is recommended to cache compiled expressions to avoid class - loading overhead. -- This API is not supported by non-dynamic JVM implementations (like TeaVM and GraalVM) because of using class loaders. +#### Limitations + +- The same classes may be generated and loaded twice, so it is recommended to cache compiled expressions to avoid class loading overhead. +- This API is not supported by non-dynamic JVM implementations like TeaVM or GraalVM Native Image because they may not support class loaders. ### On JS @@ -129,7 +142,7 @@ An example of emitted Wasm IR in the form of WAT: ) ``` -#### Known issues +#### Limitations - ESTree expression compilation uses `eval` which can be unavailable in several environments. - WebAssembly isn't supported by old versions of browsers (see https://webassembly.org/roadmap/). diff --git a/kmath-ast/docs/README-TEMPLATE.md b/kmath-ast/docs/README-TEMPLATE.md index 9494af63a..e9e22f4d4 100644 --- a/kmath-ast/docs/README-TEMPLATE.md +++ b/kmath-ast/docs/README-TEMPLATE.md @@ -1,11 +1,31 @@ # Module kmath-ast -Performance and visualization extensions to MST API. +Extensions to MST API: transformations, dynamic compilation and visualization. ${features} ${artifact} +## Parsing expressions + +In this module there is a parser from human-readable strings like `"x^3-x+3"` (in the more specific [grammar](reference/ArithmeticsEvaluator.g4)) to MST instances. + +Supported literals: +1. Constants and variables (consist of latin letters, digits and underscores, can't start with digit): `x`, `_Abc2`. +2. Numbers: `123`, `1.02`, `1e10`, `1e-10`, `1.0e+3`—all parsed either as `kotlin.Long` or `kotlin.Double`. + +Supported binary operators (from the highest precedence to the lowest one): +1. `^` +2. `*`, `/` +3. `+`, `-` + +Supported unary operator: +1. `-`, e. g. `-x` + +Arbitrary unary and binary functions are also supported: names consist of latin letters, digits and underscores, can't start with digit. Examples: +1. `sin(x)` +2. `add(x, y)` + ## Dynamic expression code generation ### On JVM @@ -13,48 +33,66 @@ ${artifact} `kmath-ast` JVM module supports runtime code generation to eliminate overhead of tree traversal. Code generator builds a special implementation of `Expression` with implemented `invoke` function. -For example, the following builder: +For example, the following code: ```kotlin -import space.kscience.kmath.expressions.Symbol.Companion.x -import space.kscience.kmath.expressions.* -import space.kscience.kmath.operations.* -import space.kscience.kmath.asm.* - -MstField { x + 2 }.compileToExpression(DoubleField) -``` - -... leads to generation of bytecode, which can be decompiled to the following Java class: - -```java -package space.kscience.kmath.asm.generated; - -import java.util.Map; - -import kotlin.jvm.functions.Function2; -import space.kscience.kmath.asm.internal.MapIntrinsics; -import space.kscience.kmath.expressions.Expression; -import space.kscience.kmath.expressions.Symbol; - -public final class AsmCompiledExpression_45045_0 implements Expression { - private final Object[] constants; - - public final Double invoke(Map arguments) { - return (Double) ((Function2) this.constants[0]).invoke((Double) MapIntrinsics.getOrFail(arguments, "x"), 2); - } - - public AsmCompiledExpression_45045_0(Object[] constants) { - this.constants = constants; - } -} +import space.kscience.kmath.asm.compileToExpression +import space.kscience.kmath.operations.DoubleField +"x^3-x+3".parseMath().compileToExpression(DoubleField) ``` -#### Known issues +… leads to generation of bytecode, which can be decompiled to the following Java class: -- The same classes may be generated and loaded twice, so it is recommended to cache compiled expressions to avoid class - loading overhead. -- This API is not supported by non-dynamic JVM implementations (like TeaVM and GraalVM) because of using class loaders. +```java +import java.util.*; +import kotlin.jvm.functions.*; +import space.kscience.kmath.asm.internal.*; +import space.kscience.kmath.complex.*; +import space.kscience.kmath.expressions.*; + +public final class CompiledExpression_45045_0 implements Expression { + private final Object[] constants; + + public Complex invoke(Map arguments) { + Complex var2 = (Complex)MapIntrinsics.getOrFail(arguments, "x"); + return (Complex)((Function2)this.constants[0]).invoke(var2, (Complex)this.constants[1]); + } +} +``` + +For `LongRing`, `IntRing`, and `DoubleField` specialization is supported for better performance: + +```java +import java.util.*; +import space.kscience.kmath.asm.internal.*; +import space.kscience.kmath.expressions.*; + +public final class CompiledExpression_-386104628_0 implements DoubleExpression { + private final SymbolIndexer indexer; + + public SymbolIndexer getIndexer() { + return this.indexer; + } + + public double invoke(double[] arguments) { + double var2 = arguments[0]; + return Math.pow(var2, 3.0D) - var2 + 3.0D; + } + + public final Double invoke(Map arguments) { + double var2 = ((Double)MapIntrinsics.getOrFail(arguments, "x")).doubleValue(); + return Math.pow(var2, 3.0D) - var2 + 3.0D; + } +} +``` + +Setting JVM system property `space.kscience.kmath.ast.dump.generated.classes` to `1` makes the translator dump class files to program's working directory, so they can be reviewed manually. + +#### Limitations + +- The same classes may be generated and loaded twice, so it is recommended to cache compiled expressions to avoid class loading overhead. +- This API is not supported by non-dynamic JVM implementations like TeaVM or GraalVM Native Image because they may not support class loaders. ### On JS @@ -100,7 +138,7 @@ An example of emitted Wasm IR in the form of WAT: ) ``` -#### Known issues +#### Limitations - ESTree expression compilation uses `eval` which can be unavailable in several environments. - WebAssembly isn't supported by old versions of browsers (see https://webassembly.org/roadmap/). diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt new file mode 100644 index 000000000..8a8b8797d --- /dev/null +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt @@ -0,0 +1,177 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.ast + +import space.kscience.kmath.expressions.Expression +import space.kscience.kmath.expressions.Symbol +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.Algebra +import space.kscience.kmath.operations.NumericAlgebra + +/** + * MST form where all values belong to the type [T]. It is optimal for constant folding, dynamic compilation, etc. + * + * @param T the type. + */ +@UnstableKMathAPI +public sealed interface TypedMst { + /** + * A node containing a unary operation. + * + * @param T the type. + * @property operation The identifier of operation. + * @property function The function implementing this operation. + * @property value The argument of this operation. + */ + public class Unary(public val operation: String, public val function: (T) -> T, public val value: TypedMst) : + TypedMst { + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + other as Unary<*> + if (operation != other.operation) return false + if (value != other.value) return false + return true + } + + override fun hashCode(): Int { + var result = operation.hashCode() + result = 31 * result + value.hashCode() + return result + } + + override fun toString(): String = "Unary(operation=$operation, value=$value)" + } + + /** + * A node containing binary operation. + * + * @param T the type. + * @property operation The identifier of operation. + * @property function The binary function implementing this operation. + * @property left The left operand. + * @property right The right operand. + */ + public class Binary( + public val operation: String, + public val function: Function, + public val left: TypedMst, + public val right: TypedMst, + ) : TypedMst { + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + + other as Binary<*> + + if (operation != other.operation) return false + if (left != other.left) return false + if (right != other.right) return false + + return true + } + + override fun hashCode(): Int { + var result = operation.hashCode() + result = 31 * result + left.hashCode() + result = 31 * result + right.hashCode() + return result + } + + override fun toString(): String = "Binary(operation=$operation, left=$left, right=$right)" + } + + /** + * The non-numeric constant value. + * + * @param T the type. + * @property value The held value. + * @property number The number this value corresponds. + */ + public class Constant(public val value: T, public val number: Number?) : TypedMst { + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + other as Constant<*> + if (value != other.value) return false + if (number != other.number) return false + return true + } + + override fun hashCode(): Int { + var result = value?.hashCode() ?: 0 + result = 31 * result + (number?.hashCode() ?: 0) + return result + } + + override fun toString(): String = "Constant(value=$value, number=$number)" + } + + /** + * The node containing a variable + * + * @param T the type. + * @property symbol The symbol of the variable. + */ + public class Variable(public val symbol: Symbol) : TypedMst { + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + other as Variable<*> + if (symbol != other.symbol) return false + return true + } + + override fun hashCode(): Int = symbol.hashCode() + override fun toString(): String = "Variable(symbol=$symbol)" + } +} + +/** + * Interprets the [TypedMst] node with this [Algebra] and [arguments]. + */ +@UnstableKMathAPI +public fun TypedMst.interpret(algebra: Algebra, arguments: Map): T = when (this) { + is TypedMst.Unary -> algebra.unaryOperation(operation, interpret(algebra, arguments)) + + is TypedMst.Binary -> when { + algebra is NumericAlgebra && left is TypedMst.Constant && left.number != null -> + algebra.leftSideNumberOperation(operation, left.number, right.interpret(algebra, arguments)) + + algebra is NumericAlgebra && right is TypedMst.Constant && right.number != null -> + algebra.rightSideNumberOperation(operation, left.interpret(algebra, arguments), right.number) + + else -> algebra.binaryOperation( + operation, + left.interpret(algebra, arguments), + right.interpret(algebra, arguments), + ) + } + + is TypedMst.Constant -> value + is TypedMst.Variable -> arguments.getValue(symbol) +} + +/** + * Interprets the [TypedMst] node with this [Algebra] and optional [arguments]. + */ +@UnstableKMathAPI +public fun TypedMst.interpret(algebra: Algebra, vararg arguments: Pair): T = interpret( + algebra, + when (arguments.size) { + 0 -> emptyMap() + 1 -> mapOf(arguments[0]) + else -> hashMapOf(*arguments) + }, +) + +/** + * Interpret this [TypedMst] node as expression. + */ +@UnstableKMathAPI +public fun TypedMst.toExpression(algebra: Algebra): Expression = Expression { arguments -> + interpret(algebra, arguments) +} diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt new file mode 100644 index 000000000..71fb154c9 --- /dev/null +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt @@ -0,0 +1,93 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.ast + +import space.kscience.kmath.expressions.MST +import space.kscience.kmath.expressions.Symbol +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.Algebra +import space.kscience.kmath.operations.NumericAlgebra +import space.kscience.kmath.operations.bindSymbolOrNull + +/** + * Evaluates constants in given [MST] for given [algebra] at the same time with converting to [TypedMst]. + */ +@UnstableKMathAPI +public fun MST.evaluateConstants(algebra: Algebra): TypedMst = when (this) { + is MST.Numeric -> TypedMst.Constant( + (algebra as? NumericAlgebra)?.number(value) ?: error("Numeric nodes are not supported by $algebra"), + value, + ) + + is MST.Unary -> when (val arg = value.evaluateConstants(algebra)) { + is TypedMst.Constant -> { + val value = algebra.unaryOperation( + operation, + arg.value, + ) + + TypedMst.Constant(value, if (value is Number) value else null) + } + + else -> TypedMst.Unary(operation, algebra.unaryOperationFunction(operation), arg) + } + + is MST.Binary -> { + val left = left.evaluateConstants(algebra) + val right = right.evaluateConstants(algebra) + + when { + left is TypedMst.Constant && right is TypedMst.Constant -> { + val value = when { + algebra is NumericAlgebra && left.number != null -> algebra.leftSideNumberOperation( + operation, + left.number, + right.value, + ) + + algebra is NumericAlgebra && right.number != null -> algebra.rightSideNumberOperation( + operation, + left.value, + right.number, + ) + + else -> algebra.binaryOperation( + operation, + left.value, + right.value, + ) + } + + TypedMst.Constant(value, if (value is Number) value else null) + } + + algebra is NumericAlgebra && left is TypedMst.Constant && left.number != null -> TypedMst.Binary( + operation, + algebra.leftSideNumberOperationFunction(operation), + left, + right, + ) + + algebra is NumericAlgebra && right is TypedMst.Constant && right.number != null -> TypedMst.Binary( + operation, + algebra.rightSideNumberOperationFunction(operation), + left, + right, + ) + + else -> TypedMst.Binary(operation, algebra.binaryOperationFunction(operation), left, right) + } + } + + is Symbol -> { + val boundSymbol = algebra.bindSymbolOrNull(this) + + if (boundSymbol != null) + TypedMst.Constant(boundSymbol, if (boundSymbol is Number) boundSymbol else null) + else + TypedMst.Variable(this) + } +} diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt new file mode 100644 index 000000000..954a0f330 --- /dev/null +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt @@ -0,0 +1,52 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.ast + +import space.kscience.kmath.operations.ByteRing +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.IntRing +import space.kscience.kmath.operations.pi +import kotlin.test.Test +import kotlin.test.assertEquals +import kotlin.test.fail + +internal class TestFolding { + @Test + fun foldUnary() = assertEquals( + -1, + ("-(1)".parseMath().evaluateConstants(IntRing) as? TypedMst.Constant ?: fail()).value, + ) + + @Test + fun foldDeepUnary() = assertEquals( + 1, + ("-(-(1))".parseMath().evaluateConstants(IntRing) as? TypedMst.Constant ?: fail()).value, + ) + + @Test + fun foldBinary() = assertEquals( + 2, + ("1*2".parseMath().evaluateConstants(IntRing) as? TypedMst.Constant ?: fail()).value, + ) + + @Test + fun foldDeepBinary() = assertEquals( + 10, + ("1*2*5".parseMath().evaluateConstants(IntRing) as? TypedMst.Constant ?: fail()).value, + ) + + @Test + fun foldSymbol() = assertEquals( + DoubleField.pi, + ("pi".parseMath().evaluateConstants(DoubleField) as? TypedMst.Constant ?: fail()).value, + ) + + @Test + fun foldNumeric() = assertEquals( + 42.toByte(), + ("42".parseMath().evaluateConstants(ByteRing) as? TypedMst.Constant ?: fail()).value, + ) +} diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt index a6b6e022b..a8b1aa2e1 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt @@ -5,87 +5,48 @@ package space.kscience.kmath.estree +import space.kscience.kmath.ast.TypedMst +import space.kscience.kmath.ast.evaluateConstants import space.kscience.kmath.estree.internal.ESTreeBuilder import space.kscience.kmath.expressions.Expression import space.kscience.kmath.expressions.MST -import space.kscience.kmath.expressions.MST.* import space.kscience.kmath.expressions.Symbol import space.kscience.kmath.expressions.invoke import space.kscience.kmath.internal.estree.BaseExpression +import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Algebra -import space.kscience.kmath.operations.NumericAlgebra -import space.kscience.kmath.operations.bindSymbolOrNull - -@PublishedApi -internal fun MST.compileWith(algebra: Algebra): Expression { - fun ESTreeBuilder.visit(node: MST): BaseExpression = when (node) { - is Symbol -> { - val symbol = algebra.bindSymbolOrNull(node) - - if (symbol != null) - constant(symbol) - else - variable(node.identity) - } - - is Numeric -> constant( - (algebra as? NumericAlgebra)?.number(node.value) ?: error("Numeric nodes are not supported by $this") - ) - - is Unary -> when { - algebra is NumericAlgebra && node.value is Numeric -> constant( - algebra.unaryOperationFunction(node.operation)(algebra.number((node.value as Numeric).value)) - ) - - else -> call(algebra.unaryOperationFunction(node.operation), visit(node.value)) - } - - is Binary -> when { - algebra is NumericAlgebra && node.left is Numeric && node.right is Numeric -> constant( - algebra.binaryOperationFunction(node.operation).invoke( - algebra.number((node.left as Numeric).value), - algebra.number((node.right as Numeric).value) - ) - ) - - algebra is NumericAlgebra && node.left is Numeric -> call( - algebra.leftSideNumberOperationFunction(node.operation), - visit(node.left), - visit(node.right), - ) - - algebra is NumericAlgebra && node.right is Numeric -> call( - algebra.rightSideNumberOperationFunction(node.operation), - visit(node.left), - visit(node.right), - ) - - else -> call( - algebra.binaryOperationFunction(node.operation), - visit(node.left), - visit(node.right), - ) - } - } - - return ESTreeBuilder { visit(this@compileWith) }.instance -} /** * Create a compiled expression with given [MST] and given [algebra]. */ -public fun MST.compileToExpression(algebra: Algebra): Expression = compileWith(algebra) +@OptIn(UnstableKMathAPI::class) +public fun MST.compileToExpression(algebra: Algebra): Expression { + val typed = evaluateConstants(algebra) + if (typed is TypedMst.Constant) return Expression { typed.value } + fun ESTreeBuilder.visit(node: TypedMst): BaseExpression = when (node) { + is TypedMst.Constant -> constant(node.value) + is TypedMst.Variable -> variable(node.symbol) + is TypedMst.Unary -> call(node.function, visit(node.value)) + + is TypedMst.Binary -> call( + node.function, + visit(node.left), + visit(node.right), + ) + } + + return ESTreeBuilder { visit(typed) }.instance +} /** * Compile given MST to expression and evaluate it against [arguments] */ -public inline fun MST.compile(algebra: Algebra, arguments: Map): T = - compileToExpression(algebra).invoke(arguments) - +public fun MST.compile(algebra: Algebra, arguments: Map): T = + compileToExpression(algebra)(arguments) /** * Compile given MST to expression and evaluate it against [arguments] */ -public inline fun MST.compile(algebra: Algebra, vararg arguments: Pair): T = - compileToExpression(algebra).invoke(*arguments) +public fun MST.compile(algebra: Algebra, vararg arguments: Pair): T = + compileToExpression(algebra)(*arguments) diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt index 4907d8225..10a6c4a16 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt @@ -61,7 +61,7 @@ internal class ESTreeBuilder(val bodyCallback: ESTreeBuilder.() -> BaseExp } } - fun variable(name: String): BaseExpression = call(getOrFail, Identifier("arguments"), SimpleLiteral(name)) + fun variable(name: Symbol): BaseExpression = call(getOrFail, Identifier("arguments"), SimpleLiteral(name.identity)) fun call(function: Function, vararg args: BaseExpression): BaseExpression = SimpleCallExpression( optional = false, diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt index 96090a633..aacb62f36 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt @@ -5,8 +5,8 @@ package space.kscience.kmath.wasm.internal +import space.kscience.kmath.ast.TypedMst import space.kscience.kmath.expressions.* -import space.kscience.kmath.expressions.MST.* import space.kscience.kmath.internal.binaryen.* import space.kscience.kmath.internal.webassembly.Instance import space.kscience.kmath.misc.UnstableKMathAPI @@ -16,11 +16,12 @@ import space.kscience.kmath.internal.webassembly.Module as WasmModule private val spreader = eval("(obj, args) => obj(...args)") +@OptIn(UnstableKMathAPI::class) @Suppress("UnsafeCastFromDynamic") internal sealed class WasmBuilder>( protected val binaryenType: Type, protected val algebra: Algebra, - protected val target: MST, + protected val target: TypedMst, ) { protected val keys: MutableList = mutableListOf() protected lateinit var ctx: BinaryenModule @@ -51,59 +52,41 @@ internal sealed class WasmBuilder>( Instance(c, js("{}")).exports.executable } - protected open fun visitSymbol(node: Symbol): ExpressionRef { - algebra.bindSymbolOrNull(node)?.let { return visitNumeric(Numeric(it)) } + protected abstract fun visitNumber(number: Number): ExpressionRef - var idx = keys.indexOf(node) + protected open fun visitVariable(node: TypedMst.Variable): ExpressionRef { + var idx = keys.indexOf(node.symbol) if (idx == -1) { - keys += node + keys += node.symbol idx = keys.lastIndex } return ctx.local.get(idx, binaryenType) } - protected abstract fun visitNumeric(node: Numeric): ExpressionRef - - protected open fun visitUnary(node: Unary): ExpressionRef = + protected open fun visitUnary(node: TypedMst.Unary): ExpressionRef = error("Unary operation ${node.operation} not defined in $this") - protected open fun visitBinary(mst: Binary): ExpressionRef = + protected open fun visitBinary(mst: TypedMst.Binary): ExpressionRef = error("Binary operation ${mst.operation} not defined in $this") protected open fun createModule(): BinaryenModule = js("new \$module\$binaryen.Module()") - protected fun visit(node: MST): ExpressionRef = when (node) { - is Symbol -> visitSymbol(node) - is Numeric -> visitNumeric(node) + protected fun visit(node: TypedMst): ExpressionRef = when (node) { + is TypedMst.Constant -> visitNumber( + node.number ?: error("Object constants are not supported by pritimive ASM builder"), + ) - is Unary -> when { - algebra is NumericAlgebra && node.value is Numeric -> visitNumeric( - Numeric(algebra.unaryOperationFunction(node.operation)(algebra.number((node.value as Numeric).value))) - ) - - else -> visitUnary(node) - } - - is Binary -> when { - algebra is NumericAlgebra && node.left is Numeric && node.right is Numeric -> visitNumeric( - Numeric( - algebra.binaryOperationFunction(node.operation) - .invoke( - algebra.number((node.left as Numeric).value), - algebra.number((node.right as Numeric).value) - ) - ) - ) - - else -> visitBinary(node) - } + is TypedMst.Variable -> visitVariable(node) + is TypedMst.Unary -> visitUnary(node) + is TypedMst.Binary -> visitBinary(node) } } @UnstableKMathAPI -internal class DoubleWasmBuilder(target: MST) : WasmBuilder(f64, DoubleField, target) { +internal class DoubleWasmBuilder(target: TypedMst) : + WasmBuilder(f64, DoubleField, target) { override val instance by lazy { object : DoubleExpression { override val indexer = SimpleSymbolIndexer(keys) @@ -114,9 +97,9 @@ internal class DoubleWasmBuilder(target: MST) : WasmBuilder): ExpressionRef = when (node.operation) { GroupOps.MINUS_OPERATION -> ctx.f64.neg(visit(node.value)) GroupOps.PLUS_OPERATION -> visit(node.value) PowerOperations.SQRT_OPERATION -> ctx.f64.sqrt(visit(node.value)) @@ -137,7 +120,7 @@ internal class DoubleWasmBuilder(target: MST) : WasmBuilder super.visitUnary(node) } - override fun visitBinary(mst: Binary): ExpressionRef = when (mst.operation) { + override fun visitBinary(mst: TypedMst.Binary): ExpressionRef = when (mst.operation) { GroupOps.PLUS_OPERATION -> ctx.f64.add(visit(mst.left), visit(mst.right)) GroupOps.MINUS_OPERATION -> ctx.f64.sub(visit(mst.left), visit(mst.right)) RingOps.TIMES_OPERATION -> ctx.f64.mul(visit(mst.left), visit(mst.right)) @@ -148,7 +131,7 @@ internal class DoubleWasmBuilder(target: MST) : WasmBuilder(i32, IntRing, target) { +internal class IntWasmBuilder(target: TypedMst) : WasmBuilder(i32, IntRing, target) { override val instance by lazy { object : IntExpression { override val indexer = SimpleSymbolIndexer(keys) @@ -157,15 +140,15 @@ internal class IntWasmBuilder(target: MST) : WasmBuilder(i32 } } - override fun visitNumeric(node: Numeric) = ctx.i32.const(node.value.toInt()) + override fun visitNumber(number: Number) = ctx.i32.const(number.toInt()) - override fun visitUnary(node: Unary): ExpressionRef = when (node.operation) { + override fun visitUnary(node: TypedMst.Unary): ExpressionRef = when (node.operation) { GroupOps.MINUS_OPERATION -> ctx.i32.sub(ctx.i32.const(0), visit(node.value)) GroupOps.PLUS_OPERATION -> visit(node.value) else -> super.visitUnary(node) } - override fun visitBinary(mst: Binary): ExpressionRef = when (mst.operation) { + override fun visitBinary(mst: TypedMst.Binary): ExpressionRef = when (mst.operation) { GroupOps.PLUS_OPERATION -> ctx.i32.add(visit(mst.left), visit(mst.right)) GroupOps.MINUS_OPERATION -> ctx.i32.sub(visit(mst.left), visit(mst.right)) RingOps.TIMES_OPERATION -> ctx.i32.mul(visit(mst.left), visit(mst.right)) diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/wasm.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/wasm.kt index 12e6b41af..f9540f9db 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/wasm.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/wasm.kt @@ -7,7 +7,8 @@ package space.kscience.kmath.wasm -import space.kscience.kmath.estree.compileWith +import space.kscience.kmath.ast.TypedMst +import space.kscience.kmath.ast.evaluateConstants import space.kscience.kmath.expressions.* import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField @@ -21,8 +22,16 @@ import space.kscience.kmath.wasm.internal.IntWasmBuilder * @author Iaroslav Postovalov */ @UnstableKMathAPI -public fun MST.compileToExpression(algebra: IntRing): IntExpression = IntWasmBuilder(this).instance +public fun MST.compileToExpression(algebra: IntRing): IntExpression { + val typed = evaluateConstants(algebra) + return if (typed is TypedMst.Constant) object : IntExpression { + override val indexer = SimpleSymbolIndexer(emptyList()) + + override fun invoke(arguments: IntArray): Int = typed.value + } else + IntWasmBuilder(typed).instance +} /** * Compile given MST to expression and evaluate it against [arguments]. @@ -31,7 +40,7 @@ public fun MST.compileToExpression(algebra: IntRing): IntExpression = IntWasmBui */ @UnstableKMathAPI public fun MST.compile(algebra: IntRing, arguments: Map): Int = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** @@ -49,7 +58,16 @@ public fun MST.compile(algebra: IntRing, vararg arguments: Pair): I * @author Iaroslav Postovalov */ @UnstableKMathAPI -public fun MST.compileToExpression(algebra: DoubleField): Expression = DoubleWasmBuilder(this).instance +public fun MST.compileToExpression(algebra: DoubleField): Expression { + val typed = evaluateConstants(algebra) + + return if (typed is TypedMst.Constant) object : DoubleExpression { + override val indexer = SimpleSymbolIndexer(emptyList()) + + override fun invoke(arguments: DoubleArray): Double = typed.value + } else + DoubleWasmBuilder(typed).instance +} /** @@ -59,7 +77,7 @@ public fun MST.compileToExpression(algebra: DoubleField): Expression = D */ @UnstableKMathAPI public fun MST.compile(algebra: DoubleField, arguments: Map): Double = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** @@ -69,4 +87,4 @@ public fun MST.compile(algebra: DoubleField, arguments: Map): Do */ @UnstableKMathAPI public fun MST.compile(algebra: DoubleField, vararg arguments: Pair): Double = - compileToExpression(algebra).invoke(*arguments) + compileToExpression(algebra)(*arguments) diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/asm.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/asm.kt index 8e426622d..73b9c97a7 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/asm.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/asm.kt @@ -8,10 +8,14 @@ package space.kscience.kmath.asm import space.kscience.kmath.asm.internal.* +import space.kscience.kmath.ast.TypedMst +import space.kscience.kmath.ast.evaluateConstants import space.kscience.kmath.expressions.* -import space.kscience.kmath.expressions.MST.* import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.* +import space.kscience.kmath.operations.Algebra +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.IntRing +import space.kscience.kmath.operations.LongRing /** * Compiles given MST to an Expression using AST compiler. @@ -21,102 +25,64 @@ import space.kscience.kmath.operations.* * @return the compiled expression. * @author Alexander Nozik */ +@OptIn(UnstableKMathAPI::class) @PublishedApi internal fun MST.compileWith(type: Class, algebra: Algebra): Expression { - fun GenericAsmBuilder.variablesVisitor(node: MST): Unit = when (node) { - is Symbol -> prepareVariable(node.identity) - is Unary -> variablesVisitor(node.value) + val typed = evaluateConstants(algebra) + if (typed is TypedMst.Constant) return Expression { typed.value } - is Binary -> { + fun GenericAsmBuilder.variablesVisitor(node: TypedMst): Unit = when (node) { + is TypedMst.Unary -> variablesVisitor(node.value) + + is TypedMst.Binary -> { variablesVisitor(node.left) variablesVisitor(node.right) } - else -> Unit + is TypedMst.Variable -> prepareVariable(node.symbol) + is TypedMst.Constant -> Unit } - fun GenericAsmBuilder.expressionVisitor(node: MST): Unit = when (node) { - is Symbol -> { - val symbol = algebra.bindSymbolOrNull(node) + fun GenericAsmBuilder.expressionVisitor(node: TypedMst): Unit = when (node) { + is TypedMst.Constant -> if (node.number != null) + loadNumberConstant(node.number) + else + loadObjectConstant(node.value) - if (symbol != null) - loadObjectConstant(symbol as Any) - else - loadVariable(node.identity) - } + is TypedMst.Variable -> loadVariable(node.symbol) + is TypedMst.Unary -> buildCall(node.function) { expressionVisitor(node.value) } - is Numeric -> if (algebra is NumericAlgebra) { - if (Number::class.java.isAssignableFrom(type)) - loadNumberConstant(algebra.number(node.value) as Number) - else - loadObjectConstant(algebra.number(node.value)) - } else - error("Numeric nodes are not supported by $this") - - is Unary -> when { - algebra is NumericAlgebra && node.value is Numeric -> loadObjectConstant( - algebra.unaryOperationFunction(node.operation)(algebra.number((node.value as Numeric).value)), - ) - - else -> buildCall(algebra.unaryOperationFunction(node.operation)) { expressionVisitor(node.value) } - } - - is Binary -> when { - algebra is NumericAlgebra && node.left is Numeric && node.right is Numeric -> loadObjectConstant( - algebra.binaryOperationFunction(node.operation).invoke( - algebra.number((node.left as Numeric).value), - algebra.number((node.right as Numeric).value), - ) - ) - - algebra is NumericAlgebra && node.left is Numeric -> buildCall( - algebra.leftSideNumberOperationFunction(node.operation), - ) { - expressionVisitor(node.left) - expressionVisitor(node.right) - } - - algebra is NumericAlgebra && node.right is Numeric -> buildCall( - algebra.rightSideNumberOperationFunction(node.operation), - ) { - expressionVisitor(node.left) - expressionVisitor(node.right) - } - - else -> buildCall(algebra.binaryOperationFunction(node.operation)) { - expressionVisitor(node.left) - expressionVisitor(node.right) - } + is TypedMst.Binary -> buildCall(node.function) { + expressionVisitor(node.left) + expressionVisitor(node.right) } } return GenericAsmBuilder( type, - buildName(this), - { variablesVisitor(this@compileWith) }, - { expressionVisitor(this@compileWith) }, + buildName("${typed.hashCode()}_${type.simpleName}"), + { variablesVisitor(typed) }, + { expressionVisitor(typed) }, ).instance } - /** * Create a compiled expression with given [MST] and given [algebra]. */ public inline fun MST.compileToExpression(algebra: Algebra): Expression = compileWith(T::class.java, algebra) - /** * Compile given MST to expression and evaluate it against [arguments] */ public inline fun MST.compile(algebra: Algebra, arguments: Map): T = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** * Compile given MST to expression and evaluate it against [arguments] */ public inline fun MST.compile(algebra: Algebra, vararg arguments: Pair): T = - compileToExpression(algebra).invoke(*arguments) + compileToExpression(algebra)(*arguments) /** @@ -125,7 +91,16 @@ public inline fun MST.compile(algebra: Algebra, vararg argu * @author Iaroslav Postovalov */ @UnstableKMathAPI -public fun MST.compileToExpression(algebra: IntRing): IntExpression = IntAsmBuilder(this).instance +public fun MST.compileToExpression(algebra: IntRing): IntExpression { + val typed = evaluateConstants(algebra) + + return if (typed is TypedMst.Constant) object : IntExpression { + override val indexer = SimpleSymbolIndexer(emptyList()) + + override fun invoke(arguments: IntArray): Int = typed.value + } else + IntAsmBuilder(typed).instance +} /** * Compile given MST to expression and evaluate it against [arguments]. @@ -134,7 +109,7 @@ public fun MST.compileToExpression(algebra: IntRing): IntExpression = IntAsmBuil */ @UnstableKMathAPI public fun MST.compile(algebra: IntRing, arguments: Map): Int = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** * Compile given MST to expression and evaluate it against [arguments]. @@ -152,8 +127,16 @@ public fun MST.compile(algebra: IntRing, vararg arguments: Pair): I * @author Iaroslav Postovalov */ @UnstableKMathAPI -public fun MST.compileToExpression(algebra: LongRing): LongExpression = LongAsmBuilder(this).instance +public fun MST.compileToExpression(algebra: LongRing): LongExpression { + val typed = evaluateConstants(algebra) + return if (typed is TypedMst.Constant) object : LongExpression { + override val indexer = SimpleSymbolIndexer(emptyList()) + + override fun invoke(arguments: LongArray): Long = typed.value + } else + LongAsmBuilder(typed).instance +} /** * Compile given MST to expression and evaluate it against [arguments]. @@ -162,7 +145,7 @@ public fun MST.compileToExpression(algebra: LongRing): LongExpression = LongAsmB */ @UnstableKMathAPI public fun MST.compile(algebra: LongRing, arguments: Map): Long = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** @@ -181,7 +164,17 @@ public fun MST.compile(algebra: LongRing, vararg arguments: Pair): * @author Iaroslav Postovalov */ @UnstableKMathAPI -public fun MST.compileToExpression(algebra: DoubleField): DoubleExpression = DoubleAsmBuilder(this).instance +public fun MST.compileToExpression(algebra: DoubleField): DoubleExpression { + val typed = evaluateConstants(algebra) + + return if (typed is TypedMst.Constant) object : DoubleExpression { + override val indexer = SimpleSymbolIndexer(emptyList()) + + override fun invoke(arguments: DoubleArray): Double = typed.value + } else + DoubleAsmBuilder(typed).instance +} + /** * Compile given MST to expression and evaluate it against [arguments]. @@ -190,7 +183,7 @@ public fun MST.compileToExpression(algebra: DoubleField): DoubleExpression = Dou */ @UnstableKMathAPI public fun MST.compile(algebra: DoubleField, arguments: Map): Double = - compileToExpression(algebra).invoke(arguments) + compileToExpression(algebra)(arguments) /** * Compile given MST to expression and evaluate it against [arguments]. @@ -199,4 +192,4 @@ public fun MST.compile(algebra: DoubleField, arguments: Map): Do */ @UnstableKMathAPI public fun MST.compile(algebra: DoubleField, vararg arguments: Pair): Double = - compileToExpression(algebra).invoke(*arguments) + compileToExpression(algebra)(*arguments) diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/GenericAsmBuilder.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/GenericAsmBuilder.kt index 5eb739956..6cf3d8721 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/GenericAsmBuilder.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/GenericAsmBuilder.kt @@ -56,7 +56,7 @@ internal class GenericAsmBuilder( /** * Local variables indices are indices of symbols in this list. */ - private val argumentsLocals = mutableListOf() + private val argumentsLocals = mutableListOf() /** * Subclasses, loads and instantiates [Expression] for given parameters. @@ -253,10 +253,10 @@ internal class GenericAsmBuilder( * Stores value variable [name] into a local. Should be called within [variablesPrepareCallback] before using * [loadVariable]. */ - fun prepareVariable(name: String): Unit = invokeMethodVisitor.run { + fun prepareVariable(name: Symbol): Unit = invokeMethodVisitor.run { if (name in argumentsLocals) return@run load(1, MAP_TYPE) - aconst(name) + aconst(name.identity) invokestatic( MAP_INTRINSICS_TYPE.internalName, @@ -280,7 +280,7 @@ internal class GenericAsmBuilder( * Loads a variable [name] from arguments [Map] parameter of [Expression.invoke]. The variable should be stored * with [prepareVariable] first. */ - fun loadVariable(name: String): Unit = invokeMethodVisitor.load(2 + argumentsLocals.indexOf(name), tType) + fun loadVariable(name: Symbol): Unit = invokeMethodVisitor.load(2 + argumentsLocals.indexOf(name), tType) inline fun buildCall(function: Function, parameters: GenericAsmBuilder.() -> Unit) { contract { callsInPlace(parameters, InvocationKind.EXACTLY_ONCE) } diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/PrimitiveAsmBuilder.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/PrimitiveAsmBuilder.kt index bf1f42395..01bad83e5 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/PrimitiveAsmBuilder.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/PrimitiveAsmBuilder.kt @@ -11,6 +11,7 @@ import org.objectweb.asm.Opcodes.* import org.objectweb.asm.Type import org.objectweb.asm.Type.* import org.objectweb.asm.commons.InstructionAdapter +import space.kscience.kmath.ast.TypedMst import space.kscience.kmath.expressions.* import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* @@ -25,9 +26,9 @@ internal sealed class PrimitiveAsmBuilder>( classOfT: Class<*>, protected val classOfTPrimitive: Class<*>, expressionParent: Class, - protected val target: MST, + protected val target: TypedMst, ) : AsmBuilder() { - private val className: String = buildName(target) + private val className: String = buildName("${target.hashCode()}_${classOfT.simpleName}") /** * ASM type for [tType]. @@ -329,63 +330,39 @@ internal sealed class PrimitiveAsmBuilder>( } private fun visitVariables( - node: MST, + node: TypedMst, arrayMode: Boolean, alreadyLoaded: MutableList = mutableListOf() ): Unit = when (node) { - is Symbol -> when (node) { - !in alreadyLoaded -> { - alreadyLoaded += node - prepareVariable(node, arrayMode) - } - else -> { - } - } + is TypedMst.Variable -> if (node.symbol !in alreadyLoaded) { + alreadyLoaded += node.symbol + prepareVariable(node.symbol, arrayMode) + } else Unit - is MST.Unary -> visitVariables(node.value, arrayMode, alreadyLoaded) + is TypedMst.Unary -> visitVariables(node.value, arrayMode, alreadyLoaded) - is MST.Binary -> { + is TypedMst.Binary -> { visitVariables(node.left, arrayMode, alreadyLoaded) visitVariables(node.right, arrayMode, alreadyLoaded) } - else -> Unit + is TypedMst.Constant -> Unit } - private fun visitExpression(node: MST): Unit = when (node) { - is Symbol -> { - val symbol = algebra.bindSymbolOrNull(node) + private fun visitExpression(node: TypedMst): Unit = when (node) { + is TypedMst.Variable -> loadVariable(node.symbol) - if (symbol != null) - loadNumberConstant(symbol) - else - loadVariable(node) - } + is TypedMst.Constant -> loadNumberConstant( + node.number ?: error("Object constants are not supported by pritimive ASM builder"), + ) - is MST.Numeric -> loadNumberConstant(algebra.number(node.value)) - - is MST.Unary -> if (node.value is MST.Numeric) - loadNumberConstant( - algebra.unaryOperationFunction(node.operation)(algebra.number((node.value as MST.Numeric).value)), - ) - else - visitUnary(node) - - is MST.Binary -> when { - node.left is MST.Numeric && node.right is MST.Numeric -> loadNumberConstant( - algebra.binaryOperationFunction(node.operation)( - algebra.number((node.left as MST.Numeric).value), - algebra.number((node.right as MST.Numeric).value), - ), - ) - - else -> visitBinary(node) - } + is TypedMst.Unary -> visitUnary(node) + is TypedMst.Binary -> visitBinary(node) } - protected open fun visitUnary(node: MST.Unary) = visitExpression(node.value) + protected open fun visitUnary(node: TypedMst.Unary) = visitExpression(node.value) - protected open fun visitBinary(node: MST.Binary) { + protected open fun visitBinary(node: TypedMst.Binary) { visitExpression(node.left) visitExpression(node.right) } @@ -404,14 +381,13 @@ internal sealed class PrimitiveAsmBuilder>( } @UnstableKMathAPI -internal class DoubleAsmBuilder(target: MST) : PrimitiveAsmBuilder( +internal class DoubleAsmBuilder(target: TypedMst) : PrimitiveAsmBuilder( DoubleField, java.lang.Double::class.java, java.lang.Double.TYPE, DoubleExpression::class.java, target, ) { - private fun buildUnaryJavaMathCall(name: String) = invokeMethodVisitor.invokestatic( MATH_TYPE.internalName, name, @@ -434,7 +410,7 @@ internal class DoubleAsmBuilder(target: MST) : PrimitiveAsmBuilder) { super.visitUnary(node) when (node.operation) { @@ -459,7 +435,7 @@ internal class DoubleAsmBuilder(target: MST) : PrimitiveAsmBuilder) { super.visitBinary(node) when (node.operation) { @@ -479,7 +455,7 @@ internal class DoubleAsmBuilder(target: MST) : PrimitiveAsmBuilder) : PrimitiveAsmBuilder( IntRing, Integer::class.java, @@ -487,7 +463,7 @@ internal class IntAsmBuilder(target: MST) : IntExpression::class.java, target ) { - override fun visitUnary(node: MST.Unary) { + override fun visitUnary(node: TypedMst.Unary) { super.visitUnary(node) when (node.operation) { @@ -497,7 +473,7 @@ internal class IntAsmBuilder(target: MST) : } } - override fun visitBinary(node: MST.Binary) { + override fun visitBinary(node: TypedMst.Binary) { super.visitBinary(node) when (node.operation) { @@ -510,14 +486,14 @@ internal class IntAsmBuilder(target: MST) : } @UnstableKMathAPI -internal class LongAsmBuilder(target: MST) : PrimitiveAsmBuilder( +internal class LongAsmBuilder(target: TypedMst) : PrimitiveAsmBuilder( LongRing, java.lang.Long::class.java, java.lang.Long.TYPE, LongExpression::class.java, target, ) { - override fun visitUnary(node: MST.Unary) { + override fun visitUnary(node: TypedMst.Unary) { super.visitUnary(node) when (node.operation) { @@ -527,7 +503,7 @@ internal class LongAsmBuilder(target: MST) : PrimitiveAsmBuilder) { super.visitBinary(node) when (node.operation) { diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/codegenUtils.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/codegenUtils.kt index 06e040e93..9e880f4fc 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/codegenUtils.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/codegenUtils.kt @@ -55,15 +55,15 @@ internal inline fun MethodVisitor.instructionAdapter(block: InstructionAdapter.( internal fun MethodVisitor.label(): Label = Label().also(::visitLabel) /** - * Creates a class name for [Expression] subclassed to implement [mst] provided. + * Creates a class name for [Expression] based with appending [marker] to reduce collisions. * * These methods help to avoid collisions of class name to prevent loading several classes with the same name. If there * is a colliding class, change [collision] parameter or leave it `0` to check existing classes recursively. * * @author Iaroslav Postovalov */ -internal tailrec fun buildName(mst: MST, collision: Int = 0): String { - val name = "space.kscience.kmath.asm.generated.CompiledExpression_${mst.hashCode()}_$collision" +internal tailrec fun buildName(marker: String, collision: Int = 0): String { + val name = "space.kscience.kmath.asm.generated.CompiledExpression_${marker}_$collision" try { Class.forName(name) @@ -71,7 +71,7 @@ internal tailrec fun buildName(mst: MST, collision: Int = 0): String { return name } - return buildName(mst, collision + 1) + return buildName(marker, collision + 1) } @Suppress("FunctionName") diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt index 5f194f2ea..880cf8421 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt @@ -34,12 +34,12 @@ public abstract class FunctionalExpressionAlgebra>( override fun binaryOperationFunction(operation: String): (left: Expression, right: Expression) -> Expression = { left, right -> Expression { arguments -> - algebra.binaryOperationFunction(operation)(left.invoke(arguments), right.invoke(arguments)) + algebra.binaryOperationFunction(operation)(left(arguments), right(arguments)) } } override fun unaryOperationFunction(operation: String): (arg: Expression) -> Expression = { arg -> - Expression { arguments -> algebra.unaryOperationFunction(operation)(arg.invoke(arguments)) } + Expression { arguments -> algebra.unaryOperation(operation, arg(arguments)) } } } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MST.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MST.kt index 24e96e845..18226119b 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MST.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MST.kt @@ -24,7 +24,7 @@ public sealed interface MST { public data class Numeric(val value: Number) : MST /** - * A node containing an unary operation. + * A node containing a unary operation. * * @property operation the identifier of operation. * @property value the argument of this operation. @@ -34,7 +34,7 @@ public sealed interface MST { /** * A node containing binary operation. * - * @property operation the identifier operation. + * @property operation the identifier of operation. * @property left the left operand. * @property right the right operand. */ -- 2.34.1 From 408443989c5858d555926b2cd6ab3e9edbb057ff Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 13 Feb 2022 17:48:04 +0300 Subject: [PATCH 02/59] Up version --- build.gradle.kts | 2 +- .../kmath/expressions/FunctionalExpressionAlgebra.kt | 2 -- .../space/kscience/kmath/expressions/SimpleAutoDiff.kt | 7 ++----- .../kscience/kmath/tensorflow/TensorFlowAlgebra.kt | 10 ++++++++++ .../space/kscience/kmath/tensorflow/tfOperations.kt | 2 +- 5 files changed, 14 insertions(+), 9 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index 1b2d9d7c0..a07bcd2c5 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -10,7 +10,7 @@ allprojects { } group = "space.kscience" - version = "0.3.0-dev-17" + version = "0.3.0-dev-18" } subprojects { diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt index 880cf8421..68cc8e791 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/FunctionalExpressionAlgebra.kt @@ -164,8 +164,6 @@ public open class FunctionalExpressionExtendedField> override fun binaryOperationFunction(operation: String): (left: Expression, right: Expression) -> Expression = super.binaryOperationFunction(operation) - - override fun bindSymbol(value: String): Expression = super.bindSymbol(value) } public inline fun > A.expressionInGroup( diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SimpleAutoDiff.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SimpleAutoDiff.kt index 96fc73249..ac8c44446 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SimpleAutoDiff.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SimpleAutoDiff.kt @@ -272,7 +272,7 @@ public fun > SimpleAutoDiffField.sqrt(x: Aut public fun > SimpleAutoDiffField.pow( x: AutoDiffValue, y: Double, -): AutoDiffValue = derive(const { x.value.pow(y)}) { z -> +): AutoDiffValue = derive(const { x.value.pow(y) }) { z -> x.d += z.d * y * x.value.pow(y - 1) } @@ -343,10 +343,7 @@ public fun > SimpleAutoDiffField.atanh(x: Au public class SimpleAutoDiffExtendedField>( context: F, bindings: Map, -) : ExtendedField>, ScaleOperations>, - SimpleAutoDiffField(context, bindings) { - - override fun bindSymbol(value: String): AutoDiffValue = super.bindSymbol(value) +) : ExtendedField>, ScaleOperations>, SimpleAutoDiffField(context, bindings) { override fun number(value: Number): AutoDiffValue = const { number(value) } diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt index e2541a73e..e9e75543d 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt @@ -241,6 +241,16 @@ public abstract class TensorFlowAlgebra> internal c ops.math.argMax(asTensorFlow().output, ops.constant(dim), TInt32::class.java).output() ).actualTensor +// private val symbolCache = HashMap>() +// +// override fun bindSymbolOrNull(value: String): TensorFlowOutput? { +// return symbolCache.getOrPut(value){ops.var} +// } +// +// public fun StructureND.grad( +// +// )= operate { ops.gradients() } + @OptIn(UnstableKMathAPI::class) override fun export(arg: StructureND): StructureND = if (arg is TensorFlowOutput) arg.actualTensor else arg diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/tfOperations.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/tfOperations.kt index 257d4d6ea..f67c333ce 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/tfOperations.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/tfOperations.kt @@ -20,4 +20,4 @@ public fun TensorFlowAlgebra.sin( public fun TensorFlowAlgebra.cos( arg: StructureND, -): TensorFlowOutput where A : TrigonometricOperations, A : Ring = arg.operate { ops.math.cos(it) } +): TensorFlowOutput where A : TrigonometricOperations, A : Ring = arg.operate { ops.math.cos(it) } \ No newline at end of file -- 2.34.1 From a78e361b178eca4a9b89a25dc5067e3e0732dc33 Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 13 Feb 2022 16:01:05 +0300 Subject: [PATCH 03/59] Implement much faster dot product algorithm for tensors --- .../kscience/kmath/benchmarks/DotBenchmark.kt | 10 ++++++++++ .../kmath/tensors/core/DoubleTensorAlgebra.kt | 2 +- .../kmath/tensors/core/internal/linUtils.kt | 18 +++++++++++++----- .../tensors/core/TestDoubleTensorAlgebra.kt | 9 +++++++++ 4 files changed, 33 insertions(+), 6 deletions(-) diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt index 63165baaa..53d7ee9b6 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt @@ -15,7 +15,9 @@ import space.kscience.kmath.linear.invoke import space.kscience.kmath.linear.linearSpace import space.kscience.kmath.multik.multikAlgebra import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra import kotlin.random.Random @State(Scope.Benchmark) @@ -32,6 +34,9 @@ internal class DotBenchmark { random.nextDouble() } + val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) + val tensor2 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12225) + val cmMatrix1 = CMLinearSpace { matrix1.toCM() } val cmMatrix2 = CMLinearSpace { matrix2.toCM() } @@ -78,4 +83,9 @@ internal class DotBenchmark { fun doubleDot(blackhole: Blackhole) = with(DoubleField.linearSpace) { blackhole.consume(matrix1 dot matrix2) } + + @Benchmark + fun doubleTensorDot(blackhole: Blackhole) = DoubleTensorAlgebra.invoke { + blackhole.consume(tensor1 dot tensor2) + } } diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index 50252ad31..a75e5a8e3 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -421,7 +421,7 @@ public open class DoubleTensorAlgebra : for ((res, ab) in resTensor.matrixSequence().zip(newThis.matrixSequence().zip(newOther.matrixSequence()))) { val (a, b) = ab - dotTo(a.as2D(), b.as2D(), res.as2D(), l, m1, n) + dotTo(a, b, res, l, m1, n) } return if (penultimateDim) { diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/linUtils.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/linUtils.kt index 2fb5b949f..aba6167ce 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/linUtils.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/linUtils.kt @@ -54,18 +54,26 @@ internal val BufferedTensor.matrices: VirtualBuffer> internal fun BufferedTensor.matrixSequence(): Sequence> = matrices.asSequence() internal fun dotTo( - a: MutableStructure2D, - b: MutableStructure2D, - res: MutableStructure2D, + a: BufferedTensor, + b: BufferedTensor, + res: BufferedTensor, l: Int, m: Int, n: Int, ) { + val aStart = a.bufferStart + val bStart = b.bufferStart + val resStart = res.bufferStart + + val aBuffer = a.mutableBuffer + val bBuffer = b.mutableBuffer + val resBuffer = res.mutableBuffer + for (i in 0 until l) { for (j in 0 until n) { var curr = 0.0 for (k in 0 until m) { - curr += a[i, k] * b[k, j] + curr += aBuffer[aStart + i * m + k] * bBuffer[bStart + k * n + j] } - res[i, j] = curr + resBuffer[resStart + i * n + j] = curr } } } diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensorAlgebra.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensorAlgebra.kt index 03357f1e1..205ae2fee 100644 --- a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensorAlgebra.kt @@ -107,6 +107,8 @@ internal class TestDoubleTensorAlgebra { val tensor11 = fromArray(intArrayOf(3, 2), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) val tensor2 = fromArray(intArrayOf(3), doubleArrayOf(10.0, 20.0, 30.0)) val tensor3 = fromArray(intArrayOf(1, 1, 3), doubleArrayOf(-1.0, -2.0, -3.0)) + val tensor4 = fromArray(intArrayOf(2, 3, 3), (1..18).map { it.toDouble() }.toDoubleArray()) + val tensor5 = fromArray(intArrayOf(2, 3, 3), (1..18).map { 1 + it.toDouble() }.toDoubleArray()) val res12 = tensor1.dot(tensor2) assertTrue(res12.mutableBuffer.array() contentEquals doubleArrayOf(140.0, 320.0)) @@ -123,6 +125,13 @@ internal class TestDoubleTensorAlgebra { val res11 = tensor1.dot(tensor11) assertTrue(res11.mutableBuffer.array() contentEquals doubleArrayOf(22.0, 28.0, 49.0, 64.0)) assertTrue(res11.shape contentEquals intArrayOf(2, 2)) + + val res45 = tensor4.dot(tensor5) + assertTrue(res45.mutableBuffer.array() contentEquals doubleArrayOf( + 36.0, 42.0, 48.0, 81.0, 96.0, 111.0, 126.0, 150.0, 174.0, + 468.0, 501.0, 534.0, 594.0, 636.0, 678.0, 720.0, 771.0, 822.0 + )) + assertTrue(res45.shape contentEquals intArrayOf(2, 3, 3)) } @Test -- 2.34.1 From ac3adfa644911b6def168c257cf8bee3a6018514 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Thu, 17 Feb 2022 22:46:17 +0300 Subject: [PATCH 04/59] Fix tf dot --- benchmarks/build.gradle.kts | 2 ++ .../kscience/kmath/benchmarks/DotBenchmark.kt | 22 ++++++++++++++----- build.gradle.kts | 2 +- .../real/{RealVector.kt => DoubleVector.kt} | 0 .../kmath/tensorflow/TensorFlowAlgebra.kt | 5 +++-- .../kmath/tensorflow/DoubleTensorFlowOps.kt | 16 ++++++++++++++ .../kmath/tensors/core/DoubleTensorAlgebra.kt | 1 + 7 files changed, 40 insertions(+), 8 deletions(-) rename kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/{RealVector.kt => DoubleVector.kt} (100%) diff --git a/benchmarks/build.gradle.kts b/benchmarks/build.gradle.kts index 90ec5dfbe..e46f4a9b4 100644 --- a/benchmarks/build.gradle.kts +++ b/benchmarks/build.gradle.kts @@ -52,6 +52,8 @@ kotlin { implementation(project(":kmath-viktor")) implementation(project(":kmath-jafama")) implementation(project(":kmath-multik")) + implementation(projects.kmath.kmathTensorflow) + implementation("org.tensorflow:tensorflow-core-platform:0.4.0") implementation("org.nd4j:nd4j-native:1.0.0-M1") // uncomment if your system supports AVX2 // val os = System.getProperty("os.name") diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt index 53d7ee9b6..4a5cd4aa2 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt @@ -17,7 +17,9 @@ import space.kscience.kmath.multik.multikAlgebra import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.tensorflow.produceWithTF import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.tensorAlgebra import kotlin.random.Random @State(Scope.Benchmark) @@ -44,6 +46,16 @@ internal class DotBenchmark { val ejmlMatrix2 = EjmlLinearSpaceDDRM { matrix2.toEjml() } } + + @Benchmark + fun tfDot(blackhole: Blackhole){ + blackhole.consume( + DoubleField.produceWithTF { + tensor1 dot tensor2 + } + ) + } + @Benchmark fun cmDotWithConversion(blackhole: Blackhole) = CMLinearSpace { blackhole.consume(matrix1 dot matrix2) @@ -64,13 +76,13 @@ internal class DotBenchmark { blackhole.consume(matrix1 dot matrix2) } -// @Benchmark -// fun tensorDot(blackhole: Blackhole) = with(Double.tensorAlgebra) { -// blackhole.consume(matrix1 dot matrix2) -// } + @Benchmark + fun tensorDot(blackhole: Blackhole) = with(DoubleField.tensorAlgebra) { + blackhole.consume(matrix1 dot matrix2) + } @Benchmark - fun multikDot(blackhole: Blackhole) = with(Double.multikAlgebra) { + fun multikDot(blackhole: Blackhole) = with(DoubleField.multikAlgebra) { blackhole.consume(matrix1 dot matrix2) } diff --git a/build.gradle.kts b/build.gradle.kts index a07bcd2c5..3b48c7328 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -10,7 +10,7 @@ allprojects { } group = "space.kscience" - version = "0.3.0-dev-18" + version = "0.3.0-dev-19" } subprojects { diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealVector.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt similarity index 100% rename from kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealVector.kt rename to kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt index e9e75543d..b40739ee0 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt @@ -199,8 +199,9 @@ public abstract class TensorFlowAlgebra> internal c override fun StructureND.dot(other: StructureND): TensorFlowOutput = operate(other) { l, r -> ops.linalg.matMul( - if (l.asTensor().shape().numDimensions() == 1) ops.expandDims(l, ops.constant(0)) else l, - if (r.asTensor().shape().numDimensions() == 1) ops.expandDims(r, ops.constant(-1)) else r) + if (l.shape().numDimensions() == 1) ops.expandDims(l, ops.constant(0)) else l, + if (r.shape().numDimensions() == 1) ops.expandDims(r, ops.constant(-1)) else r + ) } override fun diagonalEmbedding( diff --git a/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt b/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt index 805ad7c66..3d118d980 100644 --- a/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt +++ b/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt @@ -4,6 +4,9 @@ import org.junit.jupiter.api.Test import space.kscience.kmath.nd.get import space.kscience.kmath.nd.structureND import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.sum +import kotlin.random.Random import kotlin.test.assertEquals class DoubleTensorFlowOps { @@ -18,6 +21,19 @@ class DoubleTensorFlowOps { assertEquals(3.0, res[0, 0]) } + @Test + fun dot(){ + val random = Random(12224) + val dim = 1000 + + val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) + val tensor2 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12225) + + DoubleField.produceWithTF { + tensor1 dot tensor2 + }.sum() + } + @Test fun extensionOps(){ val res = DoubleField.produceWithTF { diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index a75e5a8e3..ebe7a10b6 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -997,5 +997,6 @@ public open class DoubleTensorAlgebra : } public val Double.Companion.tensorAlgebra: DoubleTensorAlgebra.Companion get() = DoubleTensorAlgebra +public val DoubleField.tensorAlgebra: DoubleTensorAlgebra.Companion get() = DoubleTensorAlgebra -- 2.34.1 From 7a72a0b979e04ba928c31e01058ff561cebcc69f Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 13 Feb 2022 13:16:35 +0300 Subject: [PATCH 05/59] Implement Jacobi algorithm to find eigenvalues --- .../kmath/tensors/core/DoubleTensorAlgebra.kt | 98 ++++++++++++++++++- 1 file changed, 97 insertions(+), 1 deletion(-) diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index ebe7a10b6..418cf16b9 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -895,7 +895,7 @@ public open class DoubleTensorAlgebra : * and when the cosine approaches 1 in the SVD algorithm. * @return a pair `eigenvalues to eigenvectors`. */ - public fun StructureND.symEig(epsilon: Double): Pair { + public fun StructureND.symEigSvd(epsilon: Double): Pair { checkSymmetric(tensor, epsilon) fun MutableStructure2D.cleanSym(n: Int) { @@ -922,6 +922,102 @@ public open class DoubleTensorAlgebra : return eig to v } + // TODO + // 1. Cyclic method + // 2. Sort eigenvalues + public fun StructureND.symEig(epsilon: Double): Pair { + checkSymmetric(tensor, epsilon) + + val ii = tensor.minusIndex(-2) + val jj = tensor.minusIndex(-1) + val n = tensor.numElements + + val size = this.dimension + val commonShape = this.shape.sliceArray(0 until size - 2) + intArrayOf(1, 1) + + var d = this.copy() + var s = diagonalEmbedding(ones(this.shape.sliceArray(0 until size - 1))) + + do { + // 1. Find max element by abs value that is not on diagonal + val buffer = MutableBuffer.boxing(commonShape.reduce(Int::times)) { Triple(0.0, 0, 0) } + val maxOffDiagonalElements = BufferedTensor(commonShape, buffer, 0) + for (offset in 0 until n) { + val multiIndex = d.linearStructure.index(offset) + if (multiIndex[ii] != multiIndex[jj]) { + val value = d.mutableBuffer.array()[offset] + + val commonIndex = multiIndex.sliceArray(0 until size - 2) + intArrayOf(0, 0) + if (abs(value) > maxOffDiagonalElements[commonIndex].first) { + maxOffDiagonalElements[commonIndex] = Triple(abs(value), multiIndex[ii], multiIndex[jj]) + } + } + } + + // 2. Evaluate "rotation" angle + val angles = zeros(commonShape) + for (offset in 0 until maxOffDiagonalElements.numElements) { + val (_, i, j) = maxOffDiagonalElements.mutableBuffer[offset] + val multiIndex = maxOffDiagonalElements.linearStructure.index(offset) + + val dIJ = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = i; it[jj] = j })] + val dII = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = i; it[jj] = i })] + val dJJ = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = j; it[jj] = j })] + + angles.mutableBuffer.array()[offset] = if (dII == dJJ) { + if (dIJ > 0) PI / 4 else -PI / 4 + } else { + 0.5 * atan(2 * dIJ / (dJJ - dII)) + } + } + + // 3. Build rotation tensor `s1` + val s1 = diagonalEmbedding(ones(this.shape.sliceArray(0 until size - 1))) + for (offset in 0 until n) { + val multiIndex = d.linearStructure.index(offset) + + val commonIndex = multiIndex.sliceArray(0 until size - 2) + intArrayOf(0, 0) + val (_, i, j) = maxOffDiagonalElements[commonIndex] + val angleValue = angles[commonIndex] + s1.mutableBuffer.array()[offset] = when { + multiIndex[ii] == i && multiIndex[jj] == i || multiIndex[ii] == j && multiIndex[jj] == j -> cos(angleValue) + multiIndex[ii] == i && multiIndex[jj] == j -> sin(angleValue) + multiIndex[ii] == j && multiIndex[jj] == i -> -sin(angleValue) + else -> s1.mutableBuffer.array()[offset] + } + } + + // 4. Evaluate new tensor + d = (s1.transpose() dot d) dot s1 + s = s dot s1 + if (d.isDiagonal(epsilon)) break + } while(true) + + val eigenvalues = zeros(d.shape.sliceArray(0 until size - 1)) + for (offset in 0 until n) { + val multiIndex = d.linearStructure.index(offset) + if (multiIndex[ii] == multiIndex[jj]) { + eigenvalues[multiIndex.sliceArray(0 until size - 1)] = d.mutableBuffer.array()[offset] + } + } + + return eigenvalues to s + } + + public fun StructureND.isDiagonal(epsilon: Double = 1e-9): Boolean { + val ii = tensor.minusIndex(-2) + val jj = tensor.minusIndex(-1) + + for (offset in 0 until tensor.numElements) { + val multiIndex = tensor.linearStructure.index(offset) + if (multiIndex[ii] != multiIndex[jj] && abs(tensor.mutableBuffer.array()[offset]) > epsilon) { + return false + } + } + + return true + } + /** * Computes the determinant of a square matrix input, or of each square matrix in a batched input * using LU factorization algorithm. -- 2.34.1 From 7aff774bc166d537c40a7958418ac9a40403d74e Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 13 Feb 2022 21:49:06 +0300 Subject: [PATCH 06/59] Improve Jacobi algorithm readability by extracting some logic into helper fun --- .../kmath/tensors/core/DoubleTensorAlgebra.kt | 128 +++++++++--------- 1 file changed, 66 insertions(+), 62 deletions(-) diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index 418cf16b9..7fa6e885d 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -10,6 +10,7 @@ package space.kscience.kmath.tensors.core import space.kscience.kmath.misc.PerformancePitfall import space.kscience.kmath.nd.MutableStructure2D +import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.as1D import space.kscience.kmath.nd.as2D @@ -885,7 +886,7 @@ public open class DoubleTensorAlgebra : return Triple(uTensor.transpose(), sTensor, vTensor.transpose()) } - override fun StructureND.symEig(): Pair = symEig(epsilon = 1e-15) + override fun StructureND.symEig(): Pair = symEigJacobi(epsilon = 1e-10) /** * Returns eigenvalues and eigenvectors of a real symmetric matrix input or a batch of real symmetric matrices, @@ -922,96 +923,99 @@ public open class DoubleTensorAlgebra : return eig to v } - // TODO - // 1. Cyclic method - // 2. Sort eigenvalues - public fun StructureND.symEig(epsilon: Double): Pair { + public fun StructureND.symEigJacobi(epsilon: Double): Pair { checkSymmetric(tensor, epsilon) - val ii = tensor.minusIndex(-2) - val jj = tensor.minusIndex(-1) - val n = tensor.numElements - val size = this.dimension - val commonShape = this.shape.sliceArray(0 until size - 2) + intArrayOf(1, 1) + val s = zeros(this.shape) + val eigenvalues = zeros(this.shape.sliceArray(0 until size - 1)) - var d = this.copy() - var s = diagonalEmbedding(ones(this.shape.sliceArray(0 until size - 1))) + var eigenvalueStart = 0 + var eigenvectorStart = 0 + for (matrix in tensor.matrixSequence()) { + matrix.as2D().jacobiHelper(eigenvalues, s, eigenvalueStart, eigenvectorStart, epsilon) + eigenvalueStart += this.shape.last() + eigenvectorStart += this.shape.last() * this.shape.last() + } + // TODO sort eigenvalues + return eigenvalues to s + } + + private fun MutableStructure2D.jacobiHelper( + eigenvalues: DoubleTensor, + eigenvectors: DoubleTensor, + eigenvalueStart: Int, + eigenvectorStart: Int, + epsilon: Double + ) { + var d = this + var s = eye(this.shape[0]) + + // TODO implement cyclic method do { // 1. Find max element by abs value that is not on diagonal - val buffer = MutableBuffer.boxing(commonShape.reduce(Int::times)) { Triple(0.0, 0, 0) } - val maxOffDiagonalElements = BufferedTensor(commonShape, buffer, 0) - for (offset in 0 until n) { - val multiIndex = d.linearStructure.index(offset) - if (multiIndex[ii] != multiIndex[jj]) { - val value = d.mutableBuffer.array()[offset] - - val commonIndex = multiIndex.sliceArray(0 until size - 2) + intArrayOf(0, 0) - if (abs(value) > maxOffDiagonalElements[commonIndex].first) { - maxOffDiagonalElements[commonIndex] = Triple(abs(value), multiIndex[ii], multiIndex[jj]) + var maxOffDiagonalElement = 0.0 + var maxElementIndex = Pair(0, 0) + for (i in 0 until this.rowNum) { + for (j in 0 until this.colNum) { + if (i == j) continue + if (abs(d[i, j]) > maxOffDiagonalElement) { + maxOffDiagonalElement = abs(d[i, j]) + maxElementIndex = i to j } } } // 2. Evaluate "rotation" angle - val angles = zeros(commonShape) - for (offset in 0 until maxOffDiagonalElements.numElements) { - val (_, i, j) = maxOffDiagonalElements.mutableBuffer[offset] - val multiIndex = maxOffDiagonalElements.linearStructure.index(offset) + val dIJ = d[maxElementIndex.first, maxElementIndex.second] + val dII = d[maxElementIndex.first, maxElementIndex.first] + val dJJ = d[maxElementIndex.second, maxElementIndex.second] - val dIJ = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = i; it[jj] = j })] - val dII = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = i; it[jj] = i })] - val dJJ = d.mutableBuffer[d.linearStructure.offset(multiIndex.also { it[ii] = j; it[jj] = j })] - - angles.mutableBuffer.array()[offset] = if (dII == dJJ) { - if (dIJ > 0) PI / 4 else -PI / 4 - } else { - 0.5 * atan(2 * dIJ / (dJJ - dII)) - } + val angle = if (dII == dJJ) { + if (dIJ > 0) PI / 4 else -PI / 4 + } else { + 0.5 * atan(2 * dIJ / (dJJ - dII)) } // 3. Build rotation tensor `s1` - val s1 = diagonalEmbedding(ones(this.shape.sliceArray(0 until size - 1))) - for (offset in 0 until n) { - val multiIndex = d.linearStructure.index(offset) - - val commonIndex = multiIndex.sliceArray(0 until size - 2) + intArrayOf(0, 0) - val (_, i, j) = maxOffDiagonalElements[commonIndex] - val angleValue = angles[commonIndex] - s1.mutableBuffer.array()[offset] = when { - multiIndex[ii] == i && multiIndex[jj] == i || multiIndex[ii] == j && multiIndex[jj] == j -> cos(angleValue) - multiIndex[ii] == i && multiIndex[jj] == j -> sin(angleValue) - multiIndex[ii] == j && multiIndex[jj] == i -> -sin(angleValue) - else -> s1.mutableBuffer.array()[offset] + val s1 = eye(this.rowNum) + for (i in 0 until this.rowNum) { + for (j in 0 until this.colNum) { + s1.mutableBuffer.array()[i * this.rowNum + j] = when { + maxElementIndex.first == i && maxElementIndex.first == j -> cos(angle) + maxElementIndex.second == i && maxElementIndex.second == j -> cos(angle) + maxElementIndex.first == i && maxElementIndex.second == j -> sin(angle) + maxElementIndex.first == j && maxElementIndex.second == i -> -sin(angle) + else -> s1.mutableBuffer.array()[i * this.rowNum + j] + } } } // 4. Evaluate new tensor - d = (s1.transpose() dot d) dot s1 + d = ((s1.transpose() dot d) dot s1).as2D() s = s dot s1 if (d.isDiagonal(epsilon)) break } while(true) - val eigenvalues = zeros(d.shape.sliceArray(0 until size - 1)) - for (offset in 0 until n) { - val multiIndex = d.linearStructure.index(offset) - if (multiIndex[ii] == multiIndex[jj]) { - eigenvalues[multiIndex.sliceArray(0 until size - 1)] = d.mutableBuffer.array()[offset] + // 5. Copy result + for (i in 0 until this.rowNum) { + for (j in 0 until this.colNum) { + eigenvectors.mutableBuffer.array()[eigenvectorStart + i * this.rowNum + j] = s.mutableBuffer.array()[i * this.rowNum + j] } } - return eigenvalues to s + for (i in 0 until this.rowNum) { + eigenvalues.mutableBuffer.array()[eigenvalueStart + i] = d[i, i] + } } - public fun StructureND.isDiagonal(epsilon: Double = 1e-9): Boolean { - val ii = tensor.minusIndex(-2) - val jj = tensor.minusIndex(-1) - - for (offset in 0 until tensor.numElements) { - val multiIndex = tensor.linearStructure.index(offset) - if (multiIndex[ii] != multiIndex[jj] && abs(tensor.mutableBuffer.array()[offset]) > epsilon) { - return false + public fun Structure2D.isDiagonal(epsilon: Double = 1e-9): Boolean { + for (i in 0 until this.rowNum) { + for (j in 0 until this.colNum) { + if (i != j && abs(this[i, j]) > epsilon) { + return false + } } } -- 2.34.1 From b13765ec1928e0f2b2eb6165a8a5a0e1a057b08f Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 20 Feb 2022 02:21:52 +0300 Subject: [PATCH 07/59] Implement much faster Jacobi algorithm --- benchmarks/build.gradle.kts | 5 + .../benchmarks/TensorAlgebraBenchmark.kt | 37 ++++ .../kmath/tensors/core/DoubleTensorAlgebra.kt | 182 ++++++++++-------- 3 files changed, 149 insertions(+), 75 deletions(-) create mode 100644 benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt diff --git a/benchmarks/build.gradle.kts b/benchmarks/build.gradle.kts index e46f4a9b4..f8d39b9c5 100644 --- a/benchmarks/build.gradle.kts +++ b/benchmarks/build.gradle.kts @@ -124,6 +124,11 @@ benchmark { include("JafamaBenchmark") } + configurations.register("tensorAlgebra") { + commonConfiguration() + include("TensorAlgebraBenchmark") + } + configurations.register("viktor") { commonConfiguration() include("ViktorBenchmark") diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt new file mode 100644 index 000000000..38e064e53 --- /dev/null +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt @@ -0,0 +1,37 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.benchmarks + +import kotlinx.benchmark.Benchmark +import kotlinx.benchmark.Blackhole +import kotlinx.benchmark.Scope +import kotlinx.benchmark.State +import space.kscience.kmath.linear.linearSpace +import space.kscience.kmath.linear.matrix +import space.kscience.kmath.linear.symmetric +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.tensors.core.tensorAlgebra +import kotlin.random.Random + +@State(Scope.Benchmark) +internal class TensorAlgebraBenchmark { + companion object { + private val random = Random(12224) + private const val dim = 30 + + private val matrix = DoubleField.linearSpace.matrix(dim, dim).symmetric { _, _ -> random.nextDouble() } + } + + @Benchmark + fun tensorSymEigSvd(blackhole: Blackhole) = with(Double.tensorAlgebra) { + blackhole.consume(matrix.symEigSvd(1e-10)) + } + + @Benchmark + fun tensorSymEigJacobi(blackhole: Blackhole) = with(Double.tensorAlgebra) { + blackhole.consume(matrix.symEigJacobi(50, 1e-10)) + } +} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index 7fa6e885d..675ff4191 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -9,11 +9,7 @@ package space.kscience.kmath.tensors.core import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.MutableStructure2D -import space.kscience.kmath.nd.Structure2D -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.nd.as1D -import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.structures.indices @@ -886,7 +882,7 @@ public open class DoubleTensorAlgebra : return Triple(uTensor.transpose(), sTensor, vTensor.transpose()) } - override fun StructureND.symEig(): Pair = symEigJacobi(epsilon = 1e-10) + override fun StructureND.symEig(): Pair = symEigJacobi(maxIteration = 50, epsilon = 1e-15) /** * Returns eigenvalues and eigenvectors of a real symmetric matrix input or a batch of real symmetric matrices, @@ -923,103 +919,139 @@ public open class DoubleTensorAlgebra : return eig to v } - public fun StructureND.symEigJacobi(epsilon: Double): Pair { + public fun StructureND.symEigJacobi(maxIteration: Int, epsilon: Double): Pair { checkSymmetric(tensor, epsilon) val size = this.dimension - val s = zeros(this.shape) + val eigenvectors = zeros(this.shape) val eigenvalues = zeros(this.shape.sliceArray(0 until size - 1)) var eigenvalueStart = 0 var eigenvectorStart = 0 for (matrix in tensor.matrixSequence()) { - matrix.as2D().jacobiHelper(eigenvalues, s, eigenvalueStart, eigenvectorStart, epsilon) + val matrix2D = matrix.as2D() + val (d, v) = matrix2D.jacobiHelper(maxIteration, epsilon) + + for (i in 0 until matrix2D.rowNum) { + for (j in 0 until matrix2D.colNum) { + eigenvectors.mutableBuffer.array()[eigenvectorStart + i * matrix2D.rowNum + j] = v[i, j] + } + } + + for (i in 0 until matrix2D.rowNum) { + eigenvalues.mutableBuffer.array()[eigenvalueStart + i] = d[i] + } + eigenvalueStart += this.shape.last() eigenvectorStart += this.shape.last() * this.shape.last() } - // TODO sort eigenvalues - return eigenvalues to s + return eigenvalues to eigenvectors } private fun MutableStructure2D.jacobiHelper( - eigenvalues: DoubleTensor, - eigenvectors: DoubleTensor, - eigenvalueStart: Int, - eigenvectorStart: Int, + maxIteration: Int, epsilon: Double - ) { - var d = this - var s = eye(this.shape[0]) + ): Pair, Structure2D> { + val A_ = this.copy().as2D() + val V = eye(this.shape[0]).as2D() + val D = DoubleTensor(intArrayOf(this.shape[0]), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() + val B = DoubleTensor(intArrayOf(this.shape[0]), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() + val Z = zeros(intArrayOf(this.shape[0])).as1D() - // TODO implement cyclic method - do { - // 1. Find max element by abs value that is not on diagonal + fun maxOffDiagonal(matrix: MutableStructure2D): Double { var maxOffDiagonalElement = 0.0 - var maxElementIndex = Pair(0, 0) - for (i in 0 until this.rowNum) { - for (j in 0 until this.colNum) { - if (i == j) continue - if (abs(d[i, j]) > maxOffDiagonalElement) { - maxOffDiagonalElement = abs(d[i, j]) - maxElementIndex = i to j + for (i in 0 until matrix.rowNum - 1) { + for (j in i + 1 until matrix.colNum) { + maxOffDiagonalElement = max(maxOffDiagonalElement, abs(matrix[i, j])) + } + } + return maxOffDiagonalElement + } + + fun rotate(a: MutableStructure2D, s: Double, tau: Double, i: Int, j: Int, k: Int, l: Int) { + val g = a[i, j] + val h = a[k, l] + a[i, j] = g - s * (h + g * tau) + a[k, l] = h + s * (g - h * tau) + } + + fun jacobiIteration( + a: MutableStructure2D, + v: MutableStructure2D, + d: MutableStructure1D, + z: MutableStructure1D, + ) { + for (ip in 0 until a.rowNum - 1) { + for (iq in ip + 1 until a.colNum) { + val g = 100.0 * abs(a[ip, iq]) + + if (g <= epsilon * abs(d[ip]) && g <= epsilon * abs(d[iq])) { + a[ip, iq] = 0.0 + continue + } + + var h = d[iq] - d[ip] + val t = when { + g <= epsilon * abs(h) -> (a[ip, iq]) / h + else -> { + val theta = 0.5 * h / (a[ip, iq]) + val denominator = abs(theta) + sqrt(1.0 + theta * theta) + if (theta < 0.0) -1.0 / denominator else 1.0 / denominator + } + } + + val c = 1.0 / sqrt(1 + t * t) + val s = t * c + val tau = s / (1.0 + c) + h = t * a[ip, iq] + z[ip] -= h + z[iq] += h + d[ip] -= h + d[iq] += h + a[ip, iq] = 0.0 + + for (j in 0 until ip) { + rotate(a, s, tau, j, ip, j, iq) + } + for (j in (ip + 1) until iq) { + rotate(a, s, tau, ip, j, j, iq) + } + for (j in (iq + 1) until a.rowNum) { + rotate(a, s, tau, ip, j, iq, j) + } + for (j in 0 until a.rowNum) { + rotate(v, s, tau, j, ip, j, iq) } } } + } - // 2. Evaluate "rotation" angle - val dIJ = d[maxElementIndex.first, maxElementIndex.second] - val dII = d[maxElementIndex.first, maxElementIndex.first] - val dJJ = d[maxElementIndex.second, maxElementIndex.second] - - val angle = if (dII == dJJ) { - if (dIJ > 0) PI / 4 else -PI / 4 - } else { - 0.5 * atan(2 * dIJ / (dJJ - dII)) - } - - // 3. Build rotation tensor `s1` - val s1 = eye(this.rowNum) - for (i in 0 until this.rowNum) { - for (j in 0 until this.colNum) { - s1.mutableBuffer.array()[i * this.rowNum + j] = when { - maxElementIndex.first == i && maxElementIndex.first == j -> cos(angle) - maxElementIndex.second == i && maxElementIndex.second == j -> cos(angle) - maxElementIndex.first == i && maxElementIndex.second == j -> sin(angle) - maxElementIndex.first == j && maxElementIndex.second == i -> -sin(angle) - else -> s1.mutableBuffer.array()[i * this.rowNum + j] - } - } - } - - // 4. Evaluate new tensor - d = ((s1.transpose() dot d) dot s1).as2D() - s = s dot s1 - if (d.isDiagonal(epsilon)) break - } while(true) - - // 5. Copy result - for (i in 0 until this.rowNum) { - for (j in 0 until this.colNum) { - eigenvectors.mutableBuffer.array()[eigenvectorStart + i * this.rowNum + j] = s.mutableBuffer.array()[i * this.rowNum + j] + fun updateDiagonal( + d: MutableStructure1D, + z: MutableStructure1D, + b: MutableStructure1D, + ) { + for (ip in 0 until d.size) { + b[ip] += z[ip] + d[ip] = b[ip] + z[ip] = 0.0 } } - for (i in 0 until this.rowNum) { - eigenvalues.mutableBuffer.array()[eigenvalueStart + i] = d[i, i] - } - } - - public fun Structure2D.isDiagonal(epsilon: Double = 1e-9): Boolean { - for (i in 0 until this.rowNum) { - for (j in 0 until this.colNum) { - if (i != j && abs(this[i, j]) > epsilon) { - return false - } + var sm = maxOffDiagonal(A_) + for (iteration in 0 until maxIteration) { + if (sm < epsilon) { + break } + + jacobiIteration(A_, V, D, Z) + updateDiagonal(D, Z, B) + sm = maxOffDiagonal(A_) } - return true + // TODO sort eigenvalues + return D to V } /** -- 2.34.1 From dda6602ed4c2b8b9d7eea017b2786697e6b02ec8 Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 20 Feb 2022 02:44:27 +0300 Subject: [PATCH 08/59] Replace complex access to tensor with faster access to buffer in Jacobi algorithm --- .../kmath/tensors/core/DoubleTensorAlgebra.kt | 42 ++++++++++++------- 1 file changed, 26 insertions(+), 16 deletions(-) diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt index 675ff4191..e9dc34748 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensorAlgebra.kt @@ -953,23 +953,33 @@ public open class DoubleTensorAlgebra : maxIteration: Int, epsilon: Double ): Pair, Structure2D> { - val A_ = this.copy().as2D() - val V = eye(this.shape[0]).as2D() - val D = DoubleTensor(intArrayOf(this.shape[0]), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() - val B = DoubleTensor(intArrayOf(this.shape[0]), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() - val Z = zeros(intArrayOf(this.shape[0])).as1D() + val n = this.shape[0] + val A_ = this.copy() + val V = eye(n) + val D = DoubleTensor(intArrayOf(n), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() + val B = DoubleTensor(intArrayOf(n), (0 until this.rowNum).map { this[it, it] }.toDoubleArray()).as1D() + val Z = zeros(intArrayOf(n)).as1D() - fun maxOffDiagonal(matrix: MutableStructure2D): Double { + // assume that buffered tensor is square matrix + operator fun BufferedTensor.get(i: Int, j: Int): Double { + return this.mutableBuffer.array()[bufferStart + i * this.shape[0] + j] + } + + operator fun BufferedTensor.set(i: Int, j: Int, value: Double) { + this.mutableBuffer.array()[bufferStart + i * this.shape[0] + j] = value + } + + fun maxOffDiagonal(matrix: BufferedTensor): Double { var maxOffDiagonalElement = 0.0 - for (i in 0 until matrix.rowNum - 1) { - for (j in i + 1 until matrix.colNum) { + for (i in 0 until n - 1) { + for (j in i + 1 until n) { maxOffDiagonalElement = max(maxOffDiagonalElement, abs(matrix[i, j])) } } return maxOffDiagonalElement } - fun rotate(a: MutableStructure2D, s: Double, tau: Double, i: Int, j: Int, k: Int, l: Int) { + fun rotate(a: BufferedTensor, s: Double, tau: Double, i: Int, j: Int, k: Int, l: Int) { val g = a[i, j] val h = a[k, l] a[i, j] = g - s * (h + g * tau) @@ -977,13 +987,13 @@ public open class DoubleTensorAlgebra : } fun jacobiIteration( - a: MutableStructure2D, - v: MutableStructure2D, + a: BufferedTensor, + v: BufferedTensor, d: MutableStructure1D, z: MutableStructure1D, ) { - for (ip in 0 until a.rowNum - 1) { - for (iq in ip + 1 until a.colNum) { + for (ip in 0 until n - 1) { + for (iq in ip + 1 until n) { val g = 100.0 * abs(a[ip, iq]) if (g <= epsilon * abs(d[ip]) && g <= epsilon * abs(d[iq])) { @@ -1017,10 +1027,10 @@ public open class DoubleTensorAlgebra : for (j in (ip + 1) until iq) { rotate(a, s, tau, ip, j, j, iq) } - for (j in (iq + 1) until a.rowNum) { + for (j in (iq + 1) until n) { rotate(a, s, tau, ip, j, iq, j) } - for (j in 0 until a.rowNum) { + for (j in 0 until n) { rotate(v, s, tau, j, ip, j, iq) } } @@ -1051,7 +1061,7 @@ public open class DoubleTensorAlgebra : } // TODO sort eigenvalues - return D to V + return D to V.as2D() } /** -- 2.34.1 From a621dd7c5b97fa3753ec3fe7f55b238b914fd544 Mon Sep 17 00:00:00 2001 From: Ivan Kylchik Date: Sun, 20 Feb 2022 02:55:37 +0300 Subject: [PATCH 09/59] Drop duplicate test from `DorBenchmark` --- .../kscience/kmath/benchmarks/DotBenchmark.kt | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt index 4a5cd4aa2..16fd544a8 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt @@ -15,10 +15,8 @@ import space.kscience.kmath.linear.invoke import space.kscience.kmath.linear.linearSpace import space.kscience.kmath.multik.multikAlgebra import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer import space.kscience.kmath.tensorflow.produceWithTF -import space.kscience.kmath.tensors.core.DoubleTensorAlgebra import space.kscience.kmath.tensors.core.tensorAlgebra import kotlin.random.Random @@ -36,9 +34,6 @@ internal class DotBenchmark { random.nextDouble() } - val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) - val tensor2 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12225) - val cmMatrix1 = CMLinearSpace { matrix1.toCM() } val cmMatrix2 = CMLinearSpace { matrix2.toCM() } @@ -48,10 +43,10 @@ internal class DotBenchmark { @Benchmark - fun tfDot(blackhole: Blackhole){ + fun tfDot(blackhole: Blackhole) { blackhole.consume( DoubleField.produceWithTF { - tensor1 dot tensor2 + matrix1 dot matrix1 } ) } @@ -95,9 +90,4 @@ internal class DotBenchmark { fun doubleDot(blackhole: Blackhole) = with(DoubleField.linearSpace) { blackhole.consume(matrix1 dot matrix2) } - - @Benchmark - fun doubleTensorDot(blackhole: Blackhole) = DoubleTensorAlgebra.invoke { - blackhole.consume(tensor1 dot tensor2) - } } -- 2.34.1 From 4575ab2b797ff5dfea99ea72e0470b977eb9ee48 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 7 Mar 2022 10:39:59 +0300 Subject: [PATCH 10/59] Update interpolation API to agree with other conventions. --- .../kscience/kmath/benchmarks/DotBenchmark.kt | 7 +++++ .../kmath/functions/interpolateSquare.kt | 4 +-- .../kmath/integration/SplineIntegrator.kt | 3 ++ .../kmath/interpolation/Interpolator.kt | 31 +++++++++++++++++++ .../kmath/interpolation/LinearInterpolator.kt | 4 +++ .../kmath/interpolation/SplineInterpolator.kt | 16 ++++++---- .../interpolation/LinearInterpolatorTest.kt | 6 ++-- .../interpolation/SplineInterpolatorTest.kt | 7 ++--- .../kscience/kmath/multik/MultikNDTest.kt | 25 +++++++++++++++ .../kmath/tensorflow/DoubleTensorFlowOps.kt | 2 -- 10 files changed, 87 insertions(+), 18 deletions(-) diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt index 16fd544a8..7d5ae310b 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt @@ -15,8 +15,10 @@ import space.kscience.kmath.linear.invoke import space.kscience.kmath.linear.linearSpace import space.kscience.kmath.multik.multikAlgebra import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer import space.kscience.kmath.tensorflow.produceWithTF +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra import space.kscience.kmath.tensors.core.tensorAlgebra import kotlin.random.Random @@ -90,4 +92,9 @@ internal class DotBenchmark { fun doubleDot(blackhole: Blackhole) = with(DoubleField.linearSpace) { blackhole.consume(matrix1 dot matrix2) } + + @Benchmark + fun doubleTensorDot(blackhole: Blackhole) = DoubleTensorAlgebra.invoke { + blackhole.consume(matrix1 dot matrix2) + } } diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt index 091242829..feefedece 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt @@ -5,8 +5,8 @@ package space.kscience.kmath.functions -import space.kscience.kmath.interpolation.SplineInterpolator import space.kscience.kmath.interpolation.interpolatePolynomials +import space.kscience.kmath.interpolation.splineInterpolator import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.real.map import space.kscience.kmath.real.step @@ -28,7 +28,7 @@ fun main() { val xs = 0.0..100.0 step 0.5 val ys = xs.map(function) - val polynomial: PiecewisePolynomial = SplineInterpolator.double.interpolatePolynomials(xs, ys) + val polynomial: PiecewisePolynomial = DoubleField.splineInterpolator.interpolatePolynomials(xs, ys) val polyFunction = polynomial.asFunction(DoubleField, 0.0) diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SplineIntegrator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SplineIntegrator.kt index 15d548641..eb88d9ae0 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SplineIntegrator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SplineIntegrator.kt @@ -28,6 +28,8 @@ public fun > PiecewisePolynomial.integrate(algebra: Field> PiecewisePolynomial.integrate( @@ -98,6 +100,7 @@ public object DoubleSplineIntegrator : UnivariateIntegrator { } } +@Suppress("unused") @UnstableKMathAPI public inline val DoubleField.splineIntegrator: UnivariateIntegrator get() = DoubleSplineIntegrator \ No newline at end of file diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/Interpolator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/Interpolator.kt index b13adefa5..2266092a3 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/Interpolator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/Interpolator.kt @@ -9,6 +9,7 @@ package space.kscience.kmath.interpolation import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.functions.PiecewisePolynomial +import space.kscience.kmath.functions.asFunction import space.kscience.kmath.functions.value import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Ring @@ -59,3 +60,33 @@ public fun > PolynomialInterpolator.interpolatePolynomials( val pointSet = XYColumnarData.of(data.map { it.first }.asBuffer(), data.map { it.second }.asBuffer()) return interpolatePolynomials(pointSet) } + +public fun > PolynomialInterpolator.interpolate( + x: Buffer, + y: Buffer, +): (T) -> T? = interpolatePolynomials(x, y).asFunction(algebra) + +public fun > PolynomialInterpolator.interpolate( + data: Map, +): (T) -> T? = interpolatePolynomials(data).asFunction(algebra) + +public fun > PolynomialInterpolator.interpolate( + data: List>, +): (T) -> T? = interpolatePolynomials(data).asFunction(algebra) + + +public fun > PolynomialInterpolator.interpolate( + x: Buffer, + y: Buffer, + defaultValue: T, +): (T) -> T = interpolatePolynomials(x, y).asFunction(algebra, defaultValue) + +public fun > PolynomialInterpolator.interpolate( + data: Map, + defaultValue: T, +): (T) -> T = interpolatePolynomials(data).asFunction(algebra, defaultValue) + +public fun > PolynomialInterpolator.interpolate( + data: List>, + defaultValue: T, +): (T) -> T = interpolatePolynomials(data).asFunction(algebra, defaultValue) \ No newline at end of file diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/LinearInterpolator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/LinearInterpolator.kt index edd0e6b0a..34d7bcf41 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/LinearInterpolator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/LinearInterpolator.kt @@ -22,6 +22,7 @@ internal fun > insureSorted(points: XYColumnarData<*, T, *>) { * Reference JVM implementation: https://github.com/apache/commons-math/blob/master/src/main/java/org/apache/commons/math4/analysis/interpolation/LinearInterpolator.java */ public class LinearInterpolator>(override val algebra: Field) : PolynomialInterpolator { + @OptIn(UnstableKMathAPI::class) override fun interpolatePolynomials(points: XYColumnarData): PiecewisePolynomial = algebra { require(points.size > 0) { "Point array should not be empty" } @@ -37,3 +38,6 @@ public class LinearInterpolator>(override val algebra: Field> Field.linearInterpolator: LinearInterpolator + get() = LinearInterpolator(this) diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/SplineInterpolator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/SplineInterpolator.kt index 39c33ee69..afcb33bd4 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/SplineInterpolator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/SplineInterpolator.kt @@ -63,8 +63,8 @@ public class SplineInterpolator>( //Shift coefficients to represent absolute polynomial instead of one with an offset val polynomial = Polynomial( a - b * x0 + c * x02 - d * x03, - b - 2*c*x0 + 3*d*x02, - c - 3*d*x0, + b - 2 * c * x0 + 3 * d * x02, + c - 3 * d * x0, d ) cOld = c @@ -72,8 +72,12 @@ public class SplineInterpolator>( } } } - - public companion object { - public val double: SplineInterpolator = SplineInterpolator(DoubleField, ::DoubleBuffer) - } } + + +public fun > Field.splineInterpolator( + bufferFactory: MutableBufferFactory, +): SplineInterpolator = SplineInterpolator(this, bufferFactory) + +public val DoubleField.splineInterpolator: SplineInterpolator + get() = SplineInterpolator(this, ::DoubleBuffer) \ No newline at end of file diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/LinearInterpolatorTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/LinearInterpolatorTest.kt index bec678bae..1143036d4 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/LinearInterpolatorTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/LinearInterpolatorTest.kt @@ -5,8 +5,6 @@ package space.kscience.kmath.interpolation -import space.kscience.kmath.functions.PiecewisePolynomial -import space.kscience.kmath.functions.asFunction import space.kscience.kmath.operations.DoubleField import kotlin.test.Test import kotlin.test.assertEquals @@ -21,8 +19,8 @@ internal class LinearInterpolatorTest { 3.0 to 4.0 ) - val polynomial: PiecewisePolynomial = LinearInterpolator(DoubleField).interpolatePolynomials(data) - val function = polynomial.asFunction(DoubleField) + //val polynomial: PiecewisePolynomial = DoubleField.linearInterpolator.interpolatePolynomials(data) + val function = DoubleField.linearInterpolator.interpolate(data) assertEquals(null, function(-1.0)) assertEquals(0.5, function(0.5)) assertEquals(2.0, function(1.5)) diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/SplineInterpolatorTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/SplineInterpolatorTest.kt index 3adaab2d1..4c7d816d4 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/SplineInterpolatorTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/interpolation/SplineInterpolatorTest.kt @@ -5,8 +5,6 @@ package space.kscience.kmath.interpolation -import space.kscience.kmath.functions.PiecewisePolynomial -import space.kscience.kmath.functions.asFunction import space.kscience.kmath.operations.DoubleField import kotlin.math.PI import kotlin.math.sin @@ -21,9 +19,10 @@ internal class SplineInterpolatorTest { x to sin(x) } - val polynomial: PiecewisePolynomial = SplineInterpolator.double.interpolatePolynomials(data) + //val polynomial: PiecewisePolynomial = DoubleField.splineInterpolator.interpolatePolynomials(data) + + val function = DoubleField.splineInterpolator.interpolate(data, Double.NaN) - val function = polynomial.asFunction(DoubleField, Double.NaN) assertEquals(Double.NaN, function(-1.0)) assertEquals(sin(0.5), function(0.5), 0.1) assertEquals(sin(1.5), function(1.5), 0.1) diff --git a/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt b/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt index 404541776..72c43d8e6 100644 --- a/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt +++ b/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt @@ -6,13 +6,38 @@ package space.kscience.kmath.multik import org.junit.jupiter.api.Test +import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.one import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.invoke +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.tensorAlgebra +import kotlin.test.assertTrue internal class MultikNDTest { @Test fun basicAlgebra(): Unit = DoubleField.multikAlgebra{ one(2,2) + 1.0 } + + @Test + fun dotResult(){ + val dim = 100 + + val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) + val tensor2 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12225) + + val multikResult = with(DoubleField.multikAlgebra){ + tensor1 dot tensor2 + } + + val defaultResult = with(DoubleField.tensorAlgebra){ + tensor1 dot tensor2 + } + + assertTrue { + StructureND.contentEquals(multikResult, defaultResult) + } + + } } \ No newline at end of file diff --git a/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt b/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt index 3d118d980..308469eed 100644 --- a/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt +++ b/kmath-tensorflow/src/test/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowOps.kt @@ -6,7 +6,6 @@ import space.kscience.kmath.nd.structureND import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.tensors.core.DoubleTensorAlgebra import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.sum -import kotlin.random.Random import kotlin.test.assertEquals class DoubleTensorFlowOps { @@ -23,7 +22,6 @@ class DoubleTensorFlowOps { @Test fun dot(){ - val random = Random(12224) val dim = 1000 val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) -- 2.34.1 From 8518f333e3a1897af304b344062dbbd9328f44c7 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Tue, 8 Mar 2022 01:31:31 +0700 Subject: [PATCH 11/59] Delete yarn.lock --- .gitignore | 1 + kotlin-js-store/yarn.lock | 2059 ------------------------------------- 2 files changed, 1 insertion(+), 2059 deletions(-) delete mode 100644 kotlin-js-store/yarn.lock diff --git a/.gitignore b/.gitignore index 79f3238e1..5ddd846a8 100644 --- a/.gitignore +++ b/.gitignore @@ -19,3 +19,4 @@ out/ !/.idea/copyright/ !/.idea/scopes/ +/kotlin-js-store/yarn.lock diff --git a/kotlin-js-store/yarn.lock b/kotlin-js-store/yarn.lock deleted file mode 100644 index e21abe604..000000000 --- a/kotlin-js-store/yarn.lock +++ /dev/null @@ -1,2059 +0,0 @@ -# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. -# yarn lockfile v1 - - -"@discoveryjs/json-ext@^0.5.0": - version "0.5.6" - resolved "https://registry.yarnpkg.com/@discoveryjs/json-ext/-/json-ext-0.5.6.tgz#d5e0706cf8c6acd8c6032f8d54070af261bbbb2f" - integrity sha512-ws57AidsDvREKrZKYffXddNkyaF14iHNHm8VQnZH6t99E8gczjNN0GpvcGny0imC80yQ0tHz1xVUKk/KFQSUyA== - -"@types/component-emitter@^1.2.10": - version "1.2.11" - resolved "https://registry.yarnpkg.com/@types/component-emitter/-/component-emitter-1.2.11.tgz#50d47d42b347253817a39709fef03ce66a108506" - integrity sha512-SRXjM+tfsSlA9VuG8hGO2nft2p8zjXCK1VcC6N4NXbBbYbSia9kzCChYQajIjzIqOOOuh5Ock6MmV2oux4jDZQ== - -"@types/cookie@^0.4.0": - version "0.4.1" - resolved "https://registry.yarnpkg.com/@types/cookie/-/cookie-0.4.1.tgz#bfd02c1f2224567676c1545199f87c3a861d878d" - integrity sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q== - -"@types/cors@^2.8.8": - version "2.8.12" - resolved "https://registry.yarnpkg.com/@types/cors/-/cors-2.8.12.tgz#6b2c510a7ad7039e98e7b8d3d6598f4359e5c080" - integrity sha512-vt+kDhq/M2ayberEtJcIN/hxXy1Pk+59g2FV/ZQceeaTyCtCucjL2Q7FXlFjtWn4n15KCr1NE2lNNFhp0lEThw== - -"@types/eslint-scope@^3.7.0": - version "3.7.3" - resolved "https://registry.yarnpkg.com/@types/eslint-scope/-/eslint-scope-3.7.3.tgz#125b88504b61e3c8bc6f870882003253005c3224" - integrity sha512-PB3ldyrcnAicT35TWPs5IcwKD8S333HMaa2VVv4+wdvebJkjWuW/xESoB8IwRcog8HYVYamb1g/R31Qv5Bx03g== - dependencies: - "@types/eslint" "*" - "@types/estree" "*" - -"@types/eslint@*": - version "8.4.1" - resolved "https://registry.yarnpkg.com/@types/eslint/-/eslint-8.4.1.tgz#c48251553e8759db9e656de3efc846954ac32304" - integrity sha512-GE44+DNEyxxh2Kc6ro/VkIj+9ma0pO0bwv9+uHSyBrikYOHr8zYcdPvnBOp1aw8s+CjRvuSx7CyWqRrNFQ59mA== - dependencies: - "@types/estree" "*" - "@types/json-schema" "*" - -"@types/estree@*", "@types/estree@^0.0.50": - version "0.0.50" - resolved "https://registry.yarnpkg.com/@types/estree/-/estree-0.0.50.tgz#1e0caa9364d3fccd2931c3ed96fdbeaa5d4cca83" - integrity sha512-C6N5s2ZFtuZRj54k2/zyRhNDjJwwcViAM3Nbm8zjBpbqAdZ00mr0CFxvSKeO8Y/e03WVFLpQMdHYVfUd6SB+Hw== - -"@types/json-schema@*", "@types/json-schema@^7.0.8": - version "7.0.9" - resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.9.tgz#97edc9037ea0c38585320b28964dde3b39e4660d" - integrity sha512-qcUXuemtEu+E5wZSJHNxUXeCZhAfXKQ41D+duX+VYPde7xyEVZci+/oXKJL13tnRs9lR2pr4fod59GT6/X1/yQ== - -"@types/node@*", "@types/node@>=10.0.0": - version "17.0.12" - resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.12.tgz#f7aa331b27f08244888c47b7df126184bc2339c5" - integrity sha512-4YpbAsnJXWYK/fpTVFlMIcUIho2AYCi4wg5aNPrG1ng7fn/1/RZfCIpRCiBX+12RVa34RluilnvCqD+g3KiSiA== - -"@ungap/promise-all-settled@1.1.2": - version "1.1.2" - resolved "https://registry.yarnpkg.com/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz#aa58042711d6e3275dd37dc597e5d31e8c290a44" - integrity sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q== - -"@webassemblyjs/ast@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/ast/-/ast-1.11.1.tgz#2bfd767eae1a6996f432ff7e8d7fc75679c0b6a7" - integrity sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw== - dependencies: - "@webassemblyjs/helper-numbers" "1.11.1" - "@webassemblyjs/helper-wasm-bytecode" "1.11.1" - -"@webassemblyjs/floating-point-hex-parser@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz#f6c61a705f0fd7a6aecaa4e8198f23d9dc179e4f" - integrity sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ== - -"@webassemblyjs/helper-api-error@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz#1a63192d8788e5c012800ba6a7a46c705288fd16" - integrity sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg== - -"@webassemblyjs/helper-buffer@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz#832a900eb444884cde9a7cad467f81500f5e5ab5" - integrity sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA== - -"@webassemblyjs/helper-numbers@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz#64d81da219fbbba1e3bd1bfc74f6e8c4e10a62ae" - integrity sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ== - dependencies: - "@webassemblyjs/floating-point-hex-parser" "1.11.1" - "@webassemblyjs/helper-api-error" "1.11.1" - "@xtuc/long" "4.2.2" - -"@webassemblyjs/helper-wasm-bytecode@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz#f328241e41e7b199d0b20c18e88429c4433295e1" - integrity sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q== - -"@webassemblyjs/helper-wasm-section@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz#21ee065a7b635f319e738f0dd73bfbda281c097a" - integrity sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/helper-buffer" "1.11.1" - "@webassemblyjs/helper-wasm-bytecode" "1.11.1" - "@webassemblyjs/wasm-gen" "1.11.1" - -"@webassemblyjs/ieee754@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz#963929e9bbd05709e7e12243a099180812992614" - integrity sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ== - dependencies: - "@xtuc/ieee754" "^1.2.0" - -"@webassemblyjs/leb128@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/leb128/-/leb128-1.11.1.tgz#ce814b45574e93d76bae1fb2644ab9cdd9527aa5" - integrity sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw== - dependencies: - "@xtuc/long" "4.2.2" - -"@webassemblyjs/utf8@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/utf8/-/utf8-1.11.1.tgz#d1f8b764369e7c6e6bae350e854dec9a59f0a3ff" - integrity sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ== - -"@webassemblyjs/wasm-edit@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz#ad206ebf4bf95a058ce9880a8c092c5dec8193d6" - integrity sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/helper-buffer" "1.11.1" - "@webassemblyjs/helper-wasm-bytecode" "1.11.1" - "@webassemblyjs/helper-wasm-section" "1.11.1" - "@webassemblyjs/wasm-gen" "1.11.1" - "@webassemblyjs/wasm-opt" "1.11.1" - "@webassemblyjs/wasm-parser" "1.11.1" - "@webassemblyjs/wast-printer" "1.11.1" - -"@webassemblyjs/wasm-gen@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz#86c5ea304849759b7d88c47a32f4f039ae3c8f76" - integrity sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/helper-wasm-bytecode" "1.11.1" - "@webassemblyjs/ieee754" "1.11.1" - "@webassemblyjs/leb128" "1.11.1" - "@webassemblyjs/utf8" "1.11.1" - -"@webassemblyjs/wasm-opt@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz#657b4c2202f4cf3b345f8a4c6461c8c2418985f2" - integrity sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/helper-buffer" "1.11.1" - "@webassemblyjs/wasm-gen" "1.11.1" - "@webassemblyjs/wasm-parser" "1.11.1" - -"@webassemblyjs/wasm-parser@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz#86ca734534f417e9bd3c67c7a1c75d8be41fb199" - integrity sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/helper-api-error" "1.11.1" - "@webassemblyjs/helper-wasm-bytecode" "1.11.1" - "@webassemblyjs/ieee754" "1.11.1" - "@webassemblyjs/leb128" "1.11.1" - "@webassemblyjs/utf8" "1.11.1" - -"@webassemblyjs/wast-printer@1.11.1": - version "1.11.1" - resolved "https://registry.yarnpkg.com/@webassemblyjs/wast-printer/-/wast-printer-1.11.1.tgz#d0c73beda8eec5426f10ae8ef55cee5e7084c2f0" - integrity sha512-IQboUWM4eKzWW+N/jij2sRatKMh99QEelo3Eb2q0qXkvPRISAj8Qxtmw5itwqK+TTkBuUIE45AxYPToqPtL5gg== - dependencies: - "@webassemblyjs/ast" "1.11.1" - "@xtuc/long" "4.2.2" - -"@webpack-cli/configtest@^1.1.0": - version "1.1.1" - resolved "https://registry.yarnpkg.com/@webpack-cli/configtest/-/configtest-1.1.1.tgz#9f53b1b7946a6efc2a749095a4f450e2932e8356" - integrity sha512-1FBc1f9G4P/AxMqIgfZgeOTuRnwZMten8E7zap5zgpPInnCrP8D4Q81+4CWIch8i/Nf7nXjP0v6CjjbHOrXhKg== - -"@webpack-cli/info@^1.4.0": - version "1.4.1" - resolved "https://registry.yarnpkg.com/@webpack-cli/info/-/info-1.4.1.tgz#2360ea1710cbbb97ff156a3f0f24556e0fc1ebea" - integrity sha512-PKVGmazEq3oAo46Q63tpMr4HipI3OPfP7LiNOEJg963RMgT0rqheag28NCML0o3GIzA3DmxP1ZIAv9oTX1CUIA== - dependencies: - envinfo "^7.7.3" - -"@webpack-cli/serve@^1.6.0": - version "1.6.1" - resolved "https://registry.yarnpkg.com/@webpack-cli/serve/-/serve-1.6.1.tgz#0de2875ac31b46b6c5bb1ae0a7d7f0ba5678dffe" - integrity sha512-gNGTiTrjEVQ0OcVnzsRSqTxaBSr+dmTfm+qJsCDluky8uhdLWep7Gcr62QsAKHTMxjCS/8nEITsmFAhfIx+QSw== - -"@xtuc/ieee754@^1.2.0": - version "1.2.0" - resolved "https://registry.yarnpkg.com/@xtuc/ieee754/-/ieee754-1.2.0.tgz#eef014a3145ae477a1cbc00cd1e552336dceb790" - integrity sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA== - -"@xtuc/long@4.2.2": - version "4.2.2" - resolved "https://registry.yarnpkg.com/@xtuc/long/-/long-4.2.2.tgz#d291c6a4e97989b5c61d9acf396ae4fe133a718d" - integrity sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ== - -abab@^2.0.5: - version "2.0.5" - resolved "https://registry.yarnpkg.com/abab/-/abab-2.0.5.tgz#c0b678fb32d60fc1219c784d6a826fe385aeb79a" - integrity sha512-9IK9EadsbHo6jLWIpxpR6pL0sazTXV6+SQv25ZB+F7Bj9mJNaOc4nCRabwd5M/JwmUa8idz6Eci6eKfJryPs6Q== - -accepts@~1.3.4: - version "1.3.7" - resolved "https://registry.yarnpkg.com/accepts/-/accepts-1.3.7.tgz#531bc726517a3b2b41f850021c6cc15eaab507cd" - integrity sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA== - dependencies: - mime-types "~2.1.24" - negotiator "0.6.2" - -acorn-import-assertions@^1.7.6: - version "1.8.0" - resolved "https://registry.yarnpkg.com/acorn-import-assertions/-/acorn-import-assertions-1.8.0.tgz#ba2b5939ce62c238db6d93d81c9b111b29b855e9" - integrity sha512-m7VZ3jwz4eK6A4Vtt8Ew1/mNbP24u0FhdyfA7fSvnJR6LMdfOYnmuIrrJAgrYfYJ10F/otaHTtrtrtmHdMNzEw== - -acorn@^8.4.1: - version "8.7.0" - resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.7.0.tgz#90951fde0f8f09df93549481e5fc141445b791cf" - integrity sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ== - -ajv-keywords@^3.5.2: - version "3.5.2" - resolved "https://registry.yarnpkg.com/ajv-keywords/-/ajv-keywords-3.5.2.tgz#31f29da5ab6e00d1c2d329acf7b5929614d5014d" - integrity sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ== - -ajv@^6.12.5: - version "6.12.6" - resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" - integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== - dependencies: - fast-deep-equal "^3.1.1" - fast-json-stable-stringify "^2.0.0" - json-schema-traverse "^0.4.1" - uri-js "^4.2.2" - -ansi-colors@4.1.1: - version "4.1.1" - resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" - integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== - -ansi-regex@^5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" - integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== - -ansi-styles@^4.0.0, ansi-styles@^4.1.0: - version "4.3.0" - resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" - integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== - dependencies: - color-convert "^2.0.1" - -anymatch@~3.1.2: - version "3.1.2" - resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.2.tgz#c0557c096af32f106198f4f4e2a383537e378716" - integrity sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg== - dependencies: - normalize-path "^3.0.0" - picomatch "^2.0.4" - -argparse@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" - integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== - -astring@1.7.5: - version "1.7.5" - resolved "https://registry.yarnpkg.com/astring/-/astring-1.7.5.tgz#a7d47fceaf32b052d33a3d07c511efeec67447ca" - integrity sha512-lobf6RWXb8c4uZ7Mdq0U12efYmpD1UFnyOWVJPTa3ukqZrMopav+2hdNu0hgBF0JIBFK9QgrBDfwYvh3DFJDAA== - -balanced-match@^1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" - integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== - -base64-arraybuffer@0.1.4: - version "0.1.4" - resolved "https://registry.yarnpkg.com/base64-arraybuffer/-/base64-arraybuffer-0.1.4.tgz#9818c79e059b1355f97e0428a017c838e90ba812" - integrity sha1-mBjHngWbE1X5fgQooBfIOOkLqBI= - -base64id@2.0.0, base64id@~2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/base64id/-/base64id-2.0.0.tgz#2770ac6bc47d312af97a8bf9a634342e0cd25cb6" - integrity sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog== - -benchmark@*: - version "2.1.4" - resolved "https://registry.yarnpkg.com/benchmark/-/benchmark-2.1.4.tgz#09f3de31c916425d498cc2ee565a0ebf3c2a5629" - integrity sha1-CfPeMckWQl1JjMLuVloOvzwqVik= - dependencies: - lodash "^4.17.4" - platform "^1.3.3" - -binary-extensions@^2.0.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.2.0.tgz#75f502eeaf9ffde42fc98829645be4ea76bd9e2d" - integrity sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA== - -binaryen@101.0.0: - version "101.0.0" - resolved "https://registry.yarnpkg.com/binaryen/-/binaryen-101.0.0.tgz#42a9e4cc7a22e2c1d75a31d28005a9b518b2c555" - integrity sha512-FRmVxvrR8jtcf0qcukNAPZDM3dZ2sc9GmA/hKxBI7k3fFzREKh1cAs+ruQi+ITTKz7u/AuFMuVnbJwTh0ef/HQ== - -body-parser@^1.19.0: - version "1.19.1" - resolved "https://registry.yarnpkg.com/body-parser/-/body-parser-1.19.1.tgz#1499abbaa9274af3ecc9f6f10396c995943e31d4" - integrity sha512-8ljfQi5eBk8EJfECMrgqNGWPEY5jWP+1IzkzkGdFFEwFQZZyaZ21UqdaHktgiMlH0xLHqIFtE/u2OYE5dOtViA== - dependencies: - bytes "3.1.1" - content-type "~1.0.4" - debug "2.6.9" - depd "~1.1.2" - http-errors "1.8.1" - iconv-lite "0.4.24" - on-finished "~2.3.0" - qs "6.9.6" - raw-body "2.4.2" - type-is "~1.6.18" - -brace-expansion@^1.1.7: - version "1.1.11" - resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" - integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== - dependencies: - balanced-match "^1.0.0" - concat-map "0.0.1" - -braces@^3.0.2, braces@~3.0.2: - version "3.0.2" - resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" - integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== - dependencies: - fill-range "^7.0.1" - -browser-stdout@1.3.1: - version "1.3.1" - resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" - integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== - -browserslist@^4.14.5: - version "4.19.1" - resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.19.1.tgz#4ac0435b35ab655896c31d53018b6dd5e9e4c9a3" - integrity sha512-u2tbbG5PdKRTUoctO3NBD8FQ5HdPh1ZXPHzp1rwaa5jTc+RV9/+RlWiAIKmjRPQF+xbGM9Kklj5bZQFa2s/38A== - dependencies: - caniuse-lite "^1.0.30001286" - electron-to-chromium "^1.4.17" - escalade "^3.1.1" - node-releases "^2.0.1" - picocolors "^1.0.0" - -buffer-from@^1.0.0: - version "1.1.2" - resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5" - integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== - -bytes@3.1.1: - version "3.1.1" - resolved "https://registry.yarnpkg.com/bytes/-/bytes-3.1.1.tgz#3f018291cb4cbad9accb6e6970bca9c8889e879a" - integrity sha512-dWe4nWO/ruEOY7HkUJ5gFt1DCFV9zPRoJr8pV0/ASQermOZjtq8jMjOprC0Kd10GLN+l7xaUPvxzJFWtxGu8Fg== - -camelcase@^6.0.0: - version "6.3.0" - resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" - integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== - -caniuse-lite@^1.0.30001286: - version "1.0.30001301" - resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001301.tgz#ebc9086026534cab0dab99425d9c3b4425e5f450" - integrity sha512-csfD/GpHMqgEL3V3uIgosvh+SVIQvCh43SNu9HRbP1lnxkKm1kjDG4f32PP571JplkLjfS+mg2p1gxR7MYrrIA== - -chalk@^4.1.0: - version "4.1.2" - resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" - integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== - dependencies: - ansi-styles "^4.1.0" - supports-color "^7.1.0" - -chokidar@3.5.2: - version "3.5.2" - resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.2.tgz#dba3976fcadb016f66fd365021d91600d01c1e75" - integrity sha512-ekGhOnNVPgT77r4K/U3GDhu+FQ2S8TnK/s2KbIGXi0SZWuwkZ2QNyfWdZW+TVfn84DpEP7rLeCt2UI6bJ8GwbQ== - dependencies: - anymatch "~3.1.2" - braces "~3.0.2" - glob-parent "~5.1.2" - is-binary-path "~2.1.0" - is-glob "~4.0.1" - normalize-path "~3.0.0" - readdirp "~3.6.0" - optionalDependencies: - fsevents "~2.3.2" - -chokidar@^3.5.1: - version "3.5.3" - resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.3.tgz#1cf37c8707b932bd1af1ae22c0432e2acd1903bd" - integrity sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw== - dependencies: - anymatch "~3.1.2" - braces "~3.0.2" - glob-parent "~5.1.2" - is-binary-path "~2.1.0" - is-glob "~4.0.1" - normalize-path "~3.0.0" - readdirp "~3.6.0" - optionalDependencies: - fsevents "~2.3.2" - -chrome-trace-event@^1.0.2: - version "1.0.3" - resolved "https://registry.yarnpkg.com/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz#1015eced4741e15d06664a957dbbf50d041e26ac" - integrity sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg== - -cliui@^7.0.2: - version "7.0.4" - resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" - integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== - dependencies: - string-width "^4.2.0" - strip-ansi "^6.0.0" - wrap-ansi "^7.0.0" - -clone-deep@^4.0.1: - version "4.0.1" - resolved "https://registry.yarnpkg.com/clone-deep/-/clone-deep-4.0.1.tgz#c19fd9bdbbf85942b4fd979c84dcf7d5f07c2387" - integrity sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ== - dependencies: - is-plain-object "^2.0.4" - kind-of "^6.0.2" - shallow-clone "^3.0.0" - -color-convert@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" - integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== - dependencies: - color-name "~1.1.4" - -color-name@~1.1.4: - version "1.1.4" - resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" - integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== - -colorette@^2.0.14: - version "2.0.16" - resolved "https://registry.yarnpkg.com/colorette/-/colorette-2.0.16.tgz#713b9af84fdb000139f04546bd4a93f62a5085da" - integrity sha512-hUewv7oMjCp+wkBv5Rm0v87eJhq4woh5rSR+42YSQJKecCqgIqNkZ6lAlQms/BwHPJA5NKMRlpxPRv0n8HQW6g== - -colors@^1.4.0: - version "1.4.0" - resolved "https://registry.yarnpkg.com/colors/-/colors-1.4.0.tgz#c50491479d4c1bdaed2c9ced32cf7c7dc2360f78" - integrity sha512-a+UqTh4kgZg/SlGvfbzDHpgRu7AAQOmmqRHJnxhRZICKFUT91brVhNNt58CMWU9PsBbv3PDCZUHbVxuDiH2mtA== - -commander@^2.20.0: - version "2.20.3" - resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" - integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== - -commander@^7.0.0: - version "7.2.0" - resolved "https://registry.yarnpkg.com/commander/-/commander-7.2.0.tgz#a36cb57d0b501ce108e4d20559a150a391d97ab7" - integrity sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw== - -component-emitter@~1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/component-emitter/-/component-emitter-1.3.0.tgz#16e4070fba8ae29b679f2215853ee181ab2eabc0" - integrity sha512-Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg== - -concat-map@0.0.1: - version "0.0.1" - resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" - integrity sha1-2Klr13/Wjfd5OnMDajug1UBdR3s= - -connect@^3.7.0: - version "3.7.0" - resolved "https://registry.yarnpkg.com/connect/-/connect-3.7.0.tgz#5d49348910caa5e07a01800b030d0c35f20484f8" - integrity sha512-ZqRXc+tZukToSNmh5C2iWMSoV3X1YUcPbqEM4DkEG5tNQXrQUZCNVGGv3IuicnkMtPfGf3Xtp8WCXs295iQ1pQ== - dependencies: - debug "2.6.9" - finalhandler "1.1.2" - parseurl "~1.3.3" - utils-merge "1.0.1" - -content-type@~1.0.4: - version "1.0.4" - resolved "https://registry.yarnpkg.com/content-type/-/content-type-1.0.4.tgz#e138cc75e040c727b1966fe5e5f8c9aee256fe3b" - integrity sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA== - -cookie@~0.4.1: - version "0.4.1" - resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.1.tgz#afd713fe26ebd21ba95ceb61f9a8116e50a537d1" - integrity sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA== - -cors@~2.8.5: - version "2.8.5" - resolved "https://registry.yarnpkg.com/cors/-/cors-2.8.5.tgz#eac11da51592dd86b9f06f6e7ac293b3df875d29" - integrity sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g== - dependencies: - object-assign "^4" - vary "^1" - -cross-spawn@^7.0.3: - version "7.0.3" - resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6" - integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== - dependencies: - path-key "^3.1.0" - shebang-command "^2.0.0" - which "^2.0.1" - -css-loader@6.3.0: - version "6.3.0" - resolved "https://registry.yarnpkg.com/css-loader/-/css-loader-6.3.0.tgz#334d3500ff0a0c14cfbd4b0670088dbb5b5c1530" - integrity sha512-9NGvHOR+L6ps13Ilw/b216++Q8q+5RpJcVufCdW9S/9iCzs4KBDNa8qnA/n3FK/sSfWmH35PAIK/cfPi7LOSUg== - dependencies: - icss-utils "^5.1.0" - postcss "^8.2.15" - postcss-modules-extract-imports "^3.0.0" - postcss-modules-local-by-default "^4.0.0" - postcss-modules-scope "^3.0.0" - postcss-modules-values "^4.0.0" - postcss-value-parser "^4.1.0" - semver "^7.3.5" - -cssesc@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/cssesc/-/cssesc-3.0.0.tgz#37741919903b868565e1c09ea747445cd18983ee" - integrity sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg== - -custom-event@~1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/custom-event/-/custom-event-1.0.1.tgz#5d02a46850adf1b4a317946a3928fccb5bfd0425" - integrity sha1-XQKkaFCt8bSjF5RqOSj8y1v9BCU= - -date-format@^4.0.3: - version "4.0.3" - resolved "https://registry.yarnpkg.com/date-format/-/date-format-4.0.3.tgz#f63de5dc08dc02efd8ef32bf2a6918e486f35873" - integrity sha512-7P3FyqDcfeznLZp2b+OMitV9Sz2lUnsT87WaTat9nVwqsBkTzPG3lPLNwW3en6F4pHUiWzr6vb8CLhjdK9bcxQ== - -debug@2.6.9: - version "2.6.9" - resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f" - integrity sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA== - dependencies: - ms "2.0.0" - -debug@4.3.2: - version "4.3.2" - resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.2.tgz#f0a49c18ac8779e31d4a0c6029dfb76873c7428b" - integrity sha512-mOp8wKcvj7XxC78zLgw/ZA+6TSgkoE2C/ienthhRD298T7UNwAg9diBpLRxC0mOezLl4B0xV7M0cCO6P/O0Xhw== - dependencies: - ms "2.1.2" - -debug@^4.1.1, debug@^4.3.3, debug@~4.3.1: - version "4.3.3" - resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.3.tgz#04266e0b70a98d4462e6e288e38259213332b664" - integrity sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q== - dependencies: - ms "2.1.2" - -decamelize@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" - integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== - -depd@~1.1.2: - version "1.1.2" - resolved "https://registry.yarnpkg.com/depd/-/depd-1.1.2.tgz#9bcd52e14c097763e749b274c4346ed2e560b5a9" - integrity sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak= - -di@^0.0.1: - version "0.0.1" - resolved "https://registry.yarnpkg.com/di/-/di-0.0.1.tgz#806649326ceaa7caa3306d75d985ea2748ba913c" - integrity sha1-gGZJMmzqp8qjMG112YXqJ0i6kTw= - -diff@5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" - integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== - -dom-serialize@^2.2.1: - version "2.2.1" - resolved "https://registry.yarnpkg.com/dom-serialize/-/dom-serialize-2.2.1.tgz#562ae8999f44be5ea3076f5419dcd59eb43ac95b" - integrity sha1-ViromZ9Evl6jB29UGdzVnrQ6yVs= - dependencies: - custom-event "~1.0.0" - ent "~2.2.0" - extend "^3.0.0" - void-elements "^2.0.0" - -dukat@0.5.8-rc.4: - version "0.5.8-rc.4" - resolved "https://registry.yarnpkg.com/dukat/-/dukat-0.5.8-rc.4.tgz#90384dcb50b14c26f0e99dae92b2dea44f5fce21" - integrity sha512-ZnMt6DGBjlVgK2uQamXfd7uP/AxH7RqI0BL9GLrrJb2gKdDxvJChWy+M9AQEaL+7/6TmxzJxFOsRiInY9oGWTA== - dependencies: - google-protobuf "3.12.2" - typescript "3.9.5" - -ee-first@1.1.1: - version "1.1.1" - resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d" - integrity sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0= - -electron-to-chromium@^1.4.17: - version "1.4.52" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.52.tgz#ce44c6d6cc449e7688a4356b8c261cfeafa26833" - integrity sha512-JGkh8HEh5PnVrhU4HbpyyO0O791dVY6k7AdqfDeqbcRMeoGxtNHWT77deR2nhvbLe4dKpxjlDEvdEwrvRLGu2Q== - -emoji-regex@^8.0.0: - version "8.0.0" - resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" - integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== - -encodeurl@~1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.2.tgz#ad3ff4c86ec2d029322f5a02c3a9a606c95b3f59" - integrity sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k= - -engine.io-parser@~4.0.0: - version "4.0.3" - resolved "https://registry.yarnpkg.com/engine.io-parser/-/engine.io-parser-4.0.3.tgz#83d3a17acfd4226f19e721bb22a1ee8f7662d2f6" - integrity sha512-xEAAY0msNnESNPc00e19y5heTPX4y/TJ36gr8t1voOaNmTojP9b3oK3BbJLFufW2XFPQaaijpFewm2g2Um3uqA== - dependencies: - base64-arraybuffer "0.1.4" - -engine.io@~4.1.0: - version "4.1.2" - resolved "https://registry.yarnpkg.com/engine.io/-/engine.io-4.1.2.tgz#f96ceb56d4b39cc7ca5bd29a20e9c99c1ad1a765" - integrity sha512-t5z6zjXuVLhXDMiFJPYsPOWEER8B0tIsD3ETgw19S1yg9zryvUfY3Vhtk3Gf4sihw/bQGIqQ//gjvVlu+Ca0bQ== - dependencies: - accepts "~1.3.4" - base64id "2.0.0" - cookie "~0.4.1" - cors "~2.8.5" - debug "~4.3.1" - engine.io-parser "~4.0.0" - ws "~7.4.2" - -enhanced-resolve@^5.8.3: - version "5.8.3" - resolved "https://registry.yarnpkg.com/enhanced-resolve/-/enhanced-resolve-5.8.3.tgz#6d552d465cce0423f5b3d718511ea53826a7b2f0" - integrity sha512-EGAbGvH7j7Xt2nc0E7D99La1OiEs8LnyimkRgwExpUMScN6O+3x9tIWs7PLQZVNx4YD+00skHXPXi1yQHpAmZA== - dependencies: - graceful-fs "^4.2.4" - tapable "^2.2.0" - -ent@~2.2.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/ent/-/ent-2.2.0.tgz#e964219325a21d05f44466a2f686ed6ce5f5dd1d" - integrity sha1-6WQhkyWiHQX0RGai9obtbOX13R0= - -envinfo@^7.7.3: - version "7.8.1" - resolved "https://registry.yarnpkg.com/envinfo/-/envinfo-7.8.1.tgz#06377e3e5f4d379fea7ac592d5ad8927e0c4d475" - integrity sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw== - -es-module-lexer@^0.9.0: - version "0.9.3" - resolved "https://registry.yarnpkg.com/es-module-lexer/-/es-module-lexer-0.9.3.tgz#6f13db00cc38417137daf74366f535c8eb438f19" - integrity sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ== - -escalade@^3.1.1: - version "3.1.1" - resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" - integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== - -escape-html@~1.0.3: - version "1.0.3" - resolved "https://registry.yarnpkg.com/escape-html/-/escape-html-1.0.3.tgz#0258eae4d3d0c0974de1c169188ef0051d1d1988" - integrity sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg= - -escape-string-regexp@4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" - integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== - -eslint-scope@5.1.1: - version "5.1.1" - resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-5.1.1.tgz#e786e59a66cb92b3f6c1fb0d508aab174848f48c" - integrity sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw== - dependencies: - esrecurse "^4.3.0" - estraverse "^4.1.1" - -esrecurse@^4.3.0: - version "4.3.0" - resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" - integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== - dependencies: - estraverse "^5.2.0" - -estraverse@^4.1.1: - version "4.3.0" - resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.3.0.tgz#398ad3f3c5a24948be7725e83d11a7de28cdbd1d" - integrity sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw== - -estraverse@^5.2.0: - version "5.3.0" - resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-5.3.0.tgz#2eea5290702f26ab8fe5370370ff86c965d21123" - integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== - -eventemitter3@^4.0.0: - version "4.0.7" - resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-4.0.7.tgz#2de9b68f6528d5644ef5c59526a1b4a07306169f" - integrity sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw== - -events@^3.2.0: - version "3.3.0" - resolved "https://registry.yarnpkg.com/events/-/events-3.3.0.tgz#31a95ad0a924e2d2c419a813aeb2c4e878ea7400" - integrity sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q== - -execa@^5.0.0: - version "5.1.1" - resolved "https://registry.yarnpkg.com/execa/-/execa-5.1.1.tgz#f80ad9cbf4298f7bd1d4c9555c21e93741c411dd" - integrity sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg== - dependencies: - cross-spawn "^7.0.3" - get-stream "^6.0.0" - human-signals "^2.1.0" - is-stream "^2.0.0" - merge-stream "^2.0.0" - npm-run-path "^4.0.1" - onetime "^5.1.2" - signal-exit "^3.0.3" - strip-final-newline "^2.0.0" - -extend@^3.0.0: - version "3.0.2" - resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.2.tgz#f8b1136b4071fbd8eb140aff858b1019ec2915fa" - integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g== - -fast-deep-equal@^3.1.1: - version "3.1.3" - resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" - integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== - -fast-json-stable-stringify@^2.0.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" - integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== - -fastest-levenshtein@^1.0.12: - version "1.0.12" - resolved "https://registry.yarnpkg.com/fastest-levenshtein/-/fastest-levenshtein-1.0.12.tgz#9990f7d3a88cc5a9ffd1f1745745251700d497e2" - integrity sha512-On2N+BpYJ15xIC974QNVuYGMOlEVt4s0EOI3wwMqOmK1fdDY+FN/zltPV8vosq4ad4c/gJ1KHScUn/6AWIgiow== - -fill-range@^7.0.1: - version "7.0.1" - resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" - integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== - dependencies: - to-regex-range "^5.0.1" - -finalhandler@1.1.2: - version "1.1.2" - resolved "https://registry.yarnpkg.com/finalhandler/-/finalhandler-1.1.2.tgz#b7e7d000ffd11938d0fdb053506f6ebabe9f587d" - integrity sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA== - dependencies: - debug "2.6.9" - encodeurl "~1.0.2" - escape-html "~1.0.3" - on-finished "~2.3.0" - parseurl "~1.3.3" - statuses "~1.5.0" - unpipe "~1.0.0" - -find-up@5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" - integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== - dependencies: - locate-path "^6.0.0" - path-exists "^4.0.0" - -find-up@^4.0.0: - version "4.1.0" - resolved "https://registry.yarnpkg.com/find-up/-/find-up-4.1.0.tgz#97afe7d6cdc0bc5928584b7c8d7b16e8a9aa5d19" - integrity sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw== - dependencies: - locate-path "^5.0.0" - path-exists "^4.0.0" - -flat@^5.0.2: - version "5.0.2" - resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" - integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== - -flatted@^3.2.4: - version "3.2.4" - resolved "https://registry.yarnpkg.com/flatted/-/flatted-3.2.4.tgz#28d9969ea90661b5134259f312ab6aa7929ac5e2" - integrity sha512-8/sOawo8tJ4QOBX8YlQBMxL8+RLZfxMQOif9o0KUKTNTjMYElWPE0r/m5VNFxTRd0NSw8qSy8dajrwX4RYI1Hw== - -follow-redirects@^1.0.0: - version "1.14.7" - resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.14.7.tgz#2004c02eb9436eee9a21446a6477debf17e81685" - integrity sha512-+hbxoLbFMbRKDwohX8GkTataGqO6Jb7jGwpAlwgy2bIz25XtRm7KEzJM76R1WiNT5SwZkX4Y75SwBolkpmE7iQ== - -format-util@1.0.5: - version "1.0.5" - resolved "https://registry.yarnpkg.com/format-util/-/format-util-1.0.5.tgz#1ffb450c8a03e7bccffe40643180918cc297d271" - integrity sha512-varLbTj0e0yVyRpqQhuWV+8hlePAgaoFRhNFj50BNjEIrw1/DphHSObtqwskVCPWNgzwPoQrZAbfa/SBiicNeg== - -fs-extra@^10.0.0: - version "10.0.0" - resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-10.0.0.tgz#9ff61b655dde53fb34a82df84bb214ce802e17c1" - integrity sha512-C5owb14u9eJwizKGdchcDUQeFtlSHHthBk8pbX9Vc1PFZrLombudjDnNns88aYslCyF6IY5SUw3Roz6xShcEIQ== - dependencies: - graceful-fs "^4.2.0" - jsonfile "^6.0.1" - universalify "^2.0.0" - -fs.realpath@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" - integrity sha1-FQStJSMVjKpA20onh8sBQRmU6k8= - -fsevents@~2.3.2: - version "2.3.2" - resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.2.tgz#8a526f78b8fdf4623b709e0b975c52c24c02fd1a" - integrity sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA== - -function-bind@^1.1.1: - version "1.1.1" - resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" - integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A== - -get-caller-file@^2.0.5: - version "2.0.5" - resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" - integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== - -get-stream@^6.0.0: - version "6.0.1" - resolved "https://registry.yarnpkg.com/get-stream/-/get-stream-6.0.1.tgz#a262d8eef67aced57c2852ad6167526a43cbf7b7" - integrity sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg== - -glob-parent@~5.1.2: - version "5.1.2" - resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" - integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== - dependencies: - is-glob "^4.0.1" - -glob-to-regexp@^0.4.1: - version "0.4.1" - resolved "https://registry.yarnpkg.com/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz#c75297087c851b9a578bd217dd59a92f59fe546e" - integrity sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw== - -glob@7.1.7: - version "7.1.7" - resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.7.tgz#3b193e9233f01d42d0b3f78294bbeeb418f94a90" - integrity sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ== - dependencies: - fs.realpath "^1.0.0" - inflight "^1.0.4" - inherits "2" - minimatch "^3.0.4" - once "^1.3.0" - path-is-absolute "^1.0.0" - -glob@^7.1.3, glob@^7.1.7: - version "7.2.0" - resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023" - integrity sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q== - dependencies: - fs.realpath "^1.0.0" - inflight "^1.0.4" - inherits "2" - minimatch "^3.0.4" - once "^1.3.0" - path-is-absolute "^1.0.0" - -google-protobuf@3.12.2: - version "3.12.2" - resolved "https://registry.yarnpkg.com/google-protobuf/-/google-protobuf-3.12.2.tgz#50ce9f9b6281235724eb243d6a83e969a2176e53" - integrity sha512-4CZhpuRr1d6HjlyrxoXoocoGFnRYgKULgMtikMddA9ztRyYR59Aondv2FioyxWVamRo0rF2XpYawkTCBEQOSkA== - -graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.2.0, graceful-fs@^4.2.4, graceful-fs@^4.2.6: - version "4.2.9" - resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.9.tgz#041b05df45755e587a24942279b9d113146e1c96" - integrity sha512-NtNxqUcXgpW2iMrfqSfR73Glt39K+BLwWsPs94yR63v45T0Wbej7eRmL5cWfwEgqXnmjQp3zaJTshdRW/qC2ZQ== - -growl@1.10.5: - version "1.10.5" - resolved "https://registry.yarnpkg.com/growl/-/growl-1.10.5.tgz#f2735dc2283674fa67478b10181059355c369e5e" - integrity sha512-qBr4OuELkhPenW6goKVXiv47US3clb3/IbuWF9KNKEijAy9oeHxU9IgzjvJhHkUzhaj7rOUD7+YGWqUjLp5oSA== - -has-flag@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" - integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== - -has@^1.0.3: - version "1.0.3" - resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" - integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== - dependencies: - function-bind "^1.1.1" - -he@1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" - integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== - -http-errors@1.8.1: - version "1.8.1" - resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-1.8.1.tgz#7c3f28577cbc8a207388455dbd62295ed07bd68c" - integrity sha512-Kpk9Sm7NmI+RHhnj6OIWDI1d6fIoFAtFt9RLaTMRlg/8w49juAStsrBgp0Dp4OdxdVbRIeKhtCUvoi/RuAhO4g== - dependencies: - depd "~1.1.2" - inherits "2.0.4" - setprototypeof "1.2.0" - statuses ">= 1.5.0 < 2" - toidentifier "1.0.1" - -http-proxy@^1.18.1: - version "1.18.1" - resolved "https://registry.yarnpkg.com/http-proxy/-/http-proxy-1.18.1.tgz#401541f0534884bbf95260334e72f88ee3976549" - integrity sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ== - dependencies: - eventemitter3 "^4.0.0" - follow-redirects "^1.0.0" - requires-port "^1.0.0" - -human-signals@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/human-signals/-/human-signals-2.1.0.tgz#dc91fcba42e4d06e4abaed33b3e7a3c02f514ea0" - integrity sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw== - -iconv-lite@0.4.24: - version "0.4.24" - resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" - integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== - dependencies: - safer-buffer ">= 2.1.2 < 3" - -iconv-lite@^0.6.2: - version "0.6.3" - resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.6.3.tgz#a52f80bf38da1952eb5c681790719871a1a72501" - integrity sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw== - dependencies: - safer-buffer ">= 2.1.2 < 3.0.0" - -icss-utils@^5.0.0, icss-utils@^5.1.0: - version "5.1.0" - resolved "https://registry.yarnpkg.com/icss-utils/-/icss-utils-5.1.0.tgz#c6be6858abd013d768e98366ae47e25d5887b1ae" - integrity sha512-soFhflCVWLfRNOPU3iv5Z9VUdT44xFRbzjLsEzSr5AQmgqPMTHdU3PMT1Cf1ssx8fLNJDA1juftYl+PUcv3MqA== - -import-local@^3.0.2: - version "3.1.0" - resolved "https://registry.yarnpkg.com/import-local/-/import-local-3.1.0.tgz#b4479df8a5fd44f6cdce24070675676063c95cb4" - integrity sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg== - dependencies: - pkg-dir "^4.2.0" - resolve-cwd "^3.0.0" - -inflight@^1.0.4: - version "1.0.6" - resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" - integrity sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk= - dependencies: - once "^1.3.0" - wrappy "1" - -inherits@2, inherits@2.0.4: - version "2.0.4" - resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" - integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== - -interpret@^2.2.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/interpret/-/interpret-2.2.0.tgz#1a78a0b5965c40a5416d007ad6f50ad27c417df9" - integrity sha512-Ju0Bz/cEia55xDwUWEa8+olFpCiQoypjnQySseKtmjNrnps3P+xfpUmGr90T7yjlVJmOtybRvPXhKMbHr+fWnw== - -is-binary-path@~2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" - integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== - dependencies: - binary-extensions "^2.0.0" - -is-core-module@^2.8.1: - version "2.8.1" - resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.8.1.tgz#f59fdfca701d5879d0a6b100a40aa1560ce27211" - integrity sha512-SdNCUs284hr40hFTFP6l0IfZ/RSrMXF3qgoRHd3/79unUTvrFO/JoXwkGm+5J/Oe3E/b5GsnG330uUNgRpu1PA== - dependencies: - has "^1.0.3" - -is-extglob@^2.1.1: - version "2.1.1" - resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" - integrity sha1-qIwCU1eR8C7TfHahueqXc8gz+MI= - -is-fullwidth-code-point@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" - integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== - -is-glob@^4.0.1, is-glob@~4.0.1: - version "4.0.3" - resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" - integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== - dependencies: - is-extglob "^2.1.1" - -is-number@^7.0.0: - version "7.0.0" - resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" - integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== - -is-plain-obj@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" - integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== - -is-plain-object@^2.0.4: - version "2.0.4" - resolved "https://registry.yarnpkg.com/is-plain-object/-/is-plain-object-2.0.4.tgz#2c163b3fafb1b606d9d17928f05c2a1c38e07677" - integrity sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og== - dependencies: - isobject "^3.0.1" - -is-stream@^2.0.0: - version "2.0.1" - resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-2.0.1.tgz#fac1e3d53b97ad5a9d0ae9cef2389f5810a5c077" - integrity sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg== - -is-unicode-supported@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz#3f26c76a809593b52bfa2ecb5710ed2779b522a7" - integrity sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw== - -isbinaryfile@^4.0.8: - version "4.0.8" - resolved "https://registry.yarnpkg.com/isbinaryfile/-/isbinaryfile-4.0.8.tgz#5d34b94865bd4946633ecc78a026fc76c5b11fcf" - integrity sha512-53h6XFniq77YdW+spoRrebh0mnmTxRPTlcuIArO57lmMdq4uBKFKaeTjnb92oYWrSn/LVL+LT+Hap2tFQj8V+w== - -isexe@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" - integrity sha1-6PvzdNxVb/iUehDcsFctYz8s+hA= - -isobject@^3.0.1: - version "3.0.1" - resolved "https://registry.yarnpkg.com/isobject/-/isobject-3.0.1.tgz#4e431e92b11a9731636aa1f9c8d1ccbcfdab78df" - integrity sha1-TkMekrEalzFjaqH5yNHMvP2reN8= - -jest-worker@^27.4.1: - version "27.4.6" - resolved "https://registry.yarnpkg.com/jest-worker/-/jest-worker-27.4.6.tgz#5d2d93db419566cb680752ca0792780e71b3273e" - integrity sha512-gHWJF/6Xi5CTG5QCvROr6GcmpIqNYpDJyc8A1h/DyXqH1tD6SnRCM0d3U5msV31D2LB/U+E0M+W4oyvKV44oNw== - dependencies: - "@types/node" "*" - merge-stream "^2.0.0" - supports-color "^8.0.0" - -js-base64@3.6.1: - version "3.6.1" - resolved "https://registry.yarnpkg.com/js-base64/-/js-base64-3.6.1.tgz#555aae398b74694b4037af1f8a5a6209d170efbe" - integrity sha512-Frdq2+tRRGLQUIQOgsIGSCd1VePCS2fsddTG5dTCqR0JHgltXWfsxnY0gIXPoMeRmdom6Oyq+UMOFg5suduOjQ== - -js-yaml@4.1.0: - version "4.1.0" - resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" - integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== - dependencies: - argparse "^2.0.1" - -json-parse-better-errors@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz#bb867cfb3450e69107c131d1c514bab3dc8bcaa9" - integrity sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw== - -json-schema-traverse@^0.4.1: - version "0.4.1" - resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz#69f6a87d9513ab8bb8fe63bdb0979c448e684660" - integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== - -jsonfile@^6.0.1: - version "6.1.0" - resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-6.1.0.tgz#bc55b2634793c679ec6403094eb13698a6ec0aae" - integrity sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ== - dependencies: - universalify "^2.0.0" - optionalDependencies: - graceful-fs "^4.1.6" - -karma-chrome-launcher@3.1.0: - version "3.1.0" - resolved "https://registry.yarnpkg.com/karma-chrome-launcher/-/karma-chrome-launcher-3.1.0.tgz#805a586799a4d05f4e54f72a204979f3f3066738" - integrity sha512-3dPs/n7vgz1rxxtynpzZTvb9y/GIaW8xjAwcIGttLbycqoFtI7yo1NGnQi6oFTherRE+GIhCAHZC4vEqWGhNvg== - dependencies: - which "^1.2.1" - -karma-mocha@2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/karma-mocha/-/karma-mocha-2.0.1.tgz#4b0254a18dfee71bdbe6188d9a6861bf86b0cd7d" - integrity sha512-Tzd5HBjm8his2OA4bouAsATYEpZrp9vC7z5E5j4C5Of5Rrs1jY67RAwXNcVmd/Bnk1wgvQRou0zGVLey44G4tQ== - dependencies: - minimist "^1.2.3" - -karma-sourcemap-loader@0.3.8: - version "0.3.8" - resolved "https://registry.yarnpkg.com/karma-sourcemap-loader/-/karma-sourcemap-loader-0.3.8.tgz#d4bae72fb7a8397328a62b75013d2df937bdcf9c" - integrity sha512-zorxyAakYZuBcHRJE+vbrK2o2JXLFWK8VVjiT/6P+ltLBUGUvqTEkUiQ119MGdOrK7mrmxXHZF1/pfT6GgIZ6g== - dependencies: - graceful-fs "^4.1.2" - -karma-webpack@5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/karma-webpack/-/karma-webpack-5.0.0.tgz#2a2c7b80163fe7ffd1010f83f5507f95ef39f840" - integrity sha512-+54i/cd3/piZuP3dr54+NcFeKOPnys5QeM1IY+0SPASwrtHsliXUiCL50iW+K9WWA7RvamC4macvvQ86l3KtaA== - dependencies: - glob "^7.1.3" - minimatch "^3.0.4" - webpack-merge "^4.1.5" - -karma@6.3.4: - version "6.3.4" - resolved "https://registry.yarnpkg.com/karma/-/karma-6.3.4.tgz#359899d3aab3d6b918ea0f57046fd2a6b68565e6" - integrity sha512-hbhRogUYIulfkBTZT7xoPrCYhRBnBoqbbL4fszWD0ReFGUxU+LYBr3dwKdAluaDQ/ynT9/7C+Lf7pPNW4gSx4Q== - dependencies: - body-parser "^1.19.0" - braces "^3.0.2" - chokidar "^3.5.1" - colors "^1.4.0" - connect "^3.7.0" - di "^0.0.1" - dom-serialize "^2.2.1" - glob "^7.1.7" - graceful-fs "^4.2.6" - http-proxy "^1.18.1" - isbinaryfile "^4.0.8" - lodash "^4.17.21" - log4js "^6.3.0" - mime "^2.5.2" - minimatch "^3.0.4" - qjobs "^1.2.0" - range-parser "^1.2.1" - rimraf "^3.0.2" - socket.io "^3.1.0" - source-map "^0.6.1" - tmp "^0.2.1" - ua-parser-js "^0.7.28" - yargs "^16.1.1" - -kind-of@^6.0.2: - version "6.0.3" - resolved "https://registry.yarnpkg.com/kind-of/-/kind-of-6.0.3.tgz#07c05034a6c349fa06e24fa35aa76db4580ce4dd" - integrity sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw== - -loader-runner@^4.2.0: - version "4.2.0" - resolved "https://registry.yarnpkg.com/loader-runner/-/loader-runner-4.2.0.tgz#d7022380d66d14c5fb1d496b89864ebcfd478384" - integrity sha512-92+huvxMvYlMzMt0iIOukcwYBFpkYJdpl2xsZ7LrlayO7E8SOv+JJUEK17B/dJIHAOLMfh2dZZ/Y18WgmGtYNw== - -locate-path@^5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-5.0.0.tgz#1afba396afd676a6d42504d0a67a3a7eb9f62aa0" - integrity sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g== - dependencies: - p-locate "^4.1.0" - -locate-path@^6.0.0: - version "6.0.0" - resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" - integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== - dependencies: - p-locate "^5.0.0" - -lodash@^4.17.15, lodash@^4.17.21, lodash@^4.17.4: - version "4.17.21" - resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" - integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== - -log-symbols@4.1.0: - version "4.1.0" - resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.1.0.tgz#3fbdbb95b4683ac9fc785111e792e558d4abd503" - integrity sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg== - dependencies: - chalk "^4.1.0" - is-unicode-supported "^0.1.0" - -log4js@^6.3.0: - version "6.4.1" - resolved "https://registry.yarnpkg.com/log4js/-/log4js-6.4.1.tgz#9d3a8bf2c31c1e213fe3fc398a6053f7a2bc53e8" - integrity sha512-iUiYnXqAmNKiIZ1XSAitQ4TmNs8CdZYTAWINARF3LjnsLN8tY5m0vRwd6uuWj/yNY0YHxeZodnbmxKFUOM2rMg== - dependencies: - date-format "^4.0.3" - debug "^4.3.3" - flatted "^3.2.4" - rfdc "^1.3.0" - streamroller "^3.0.2" - -lru-cache@^6.0.0: - version "6.0.0" - resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" - integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== - dependencies: - yallist "^4.0.0" - -media-typer@0.3.0: - version "0.3.0" - resolved "https://registry.yarnpkg.com/media-typer/-/media-typer-0.3.0.tgz#8710d7af0aa626f8fffa1ce00168545263255748" - integrity sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g= - -merge-stream@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/merge-stream/-/merge-stream-2.0.0.tgz#52823629a14dd00c9770fb6ad47dc6310f2c1f60" - integrity sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w== - -mime-db@1.51.0: - version "1.51.0" - resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.51.0.tgz#d9ff62451859b18342d960850dc3cfb77e63fb0c" - integrity sha512-5y8A56jg7XVQx2mbv1lu49NR4dokRnhZYTtL+KGfaa27uq4pSTXkwQkFJl4pkRMyNFz/EtYDSkiiEHx3F7UN6g== - -mime-types@^2.1.27, mime-types@~2.1.24: - version "2.1.34" - resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.34.tgz#5a712f9ec1503511a945803640fafe09d3793c24" - integrity sha512-6cP692WwGIs9XXdOO4++N+7qjqv0rqxxVvJ3VHPh/Sc9mVZcQP+ZGhkKiTvWMQRr2tbHkJP/Yn7Y0npb3ZBs4A== - dependencies: - mime-db "1.51.0" - -mime@^2.5.2: - version "2.6.0" - resolved "https://registry.yarnpkg.com/mime/-/mime-2.6.0.tgz#a2a682a95cd4d0cb1d6257e28f83da7e35800367" - integrity sha512-USPkMeET31rOMiarsBNIHZKLGgvKc/LrjofAnBlOttf5ajRvqiRA8QsenbcooctK6d6Ts6aqZXBA+XbkKthiQg== - -mimic-fn@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/mimic-fn/-/mimic-fn-2.1.0.tgz#7ed2c2ccccaf84d3ffcb7a69b57711fc2083401b" - integrity sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg== - -minimatch@3.0.4, minimatch@^3.0.4: - version "3.0.4" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083" - integrity sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA== - dependencies: - brace-expansion "^1.1.7" - -minimist@^1.2.3: - version "1.2.5" - resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.5.tgz#67d66014b66a6a8aaa0c083c5fd58df4e4e97602" - integrity sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw== - -mocha@9.1.2: - version "9.1.2" - resolved "https://registry.yarnpkg.com/mocha/-/mocha-9.1.2.tgz#93f53175b0f0dc4014bd2d612218fccfcf3534d3" - integrity sha512-ta3LtJ+63RIBP03VBjMGtSqbe6cWXRejF9SyM9Zyli1CKZJZ+vfCTj3oW24V7wAphMJdpOFLoMI3hjJ1LWbs0w== - dependencies: - "@ungap/promise-all-settled" "1.1.2" - ansi-colors "4.1.1" - browser-stdout "1.3.1" - chokidar "3.5.2" - debug "4.3.2" - diff "5.0.0" - escape-string-regexp "4.0.0" - find-up "5.0.0" - glob "7.1.7" - growl "1.10.5" - he "1.2.0" - js-yaml "4.1.0" - log-symbols "4.1.0" - minimatch "3.0.4" - ms "2.1.3" - nanoid "3.1.25" - serialize-javascript "6.0.0" - strip-json-comments "3.1.1" - supports-color "8.1.1" - which "2.0.2" - workerpool "6.1.5" - yargs "16.2.0" - yargs-parser "20.2.4" - yargs-unparser "2.0.0" - -ms@2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8" - integrity sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g= - -ms@2.1.2: - version "2.1.2" - resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" - integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== - -ms@2.1.3: - version "2.1.3" - resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" - integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== - -nanoid@3.1.25: - version "3.1.25" - resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.1.25.tgz#09ca32747c0e543f0e1814b7d3793477f9c8e152" - integrity sha512-rdwtIXaXCLFAQbnfqDRnI6jaRHp9fTcYBjtFKE8eezcZ7LuLjhUaQGNeMXf1HmRoCH32CLz6XwX0TtxEOS/A3Q== - -nanoid@^3.1.30: - version "3.2.0" - resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.2.0.tgz#62667522da6673971cca916a6d3eff3f415ff80c" - integrity sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA== - -negotiator@0.6.2: - version "0.6.2" - resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.2.tgz#feacf7ccf525a77ae9634436a64883ffeca346fb" - integrity sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw== - -neo-async@^2.6.2: - version "2.6.2" - resolved "https://registry.yarnpkg.com/neo-async/-/neo-async-2.6.2.tgz#b4aafb93e3aeb2d8174ca53cf163ab7d7308305f" - integrity sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw== - -node-releases@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/node-releases/-/node-releases-2.0.1.tgz#3d1d395f204f1f2f29a54358b9fb678765ad2fc5" - integrity sha512-CqyzN6z7Q6aMeF/ktcMVTzhAHCEpf8SOarwpzpf8pNBY2k5/oM34UHldUwp8VKI7uxct2HxSRdJjBaZeESzcxA== - -normalize-path@^3.0.0, normalize-path@~3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" - integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== - -npm-run-path@^4.0.1: - version "4.0.1" - resolved "https://registry.yarnpkg.com/npm-run-path/-/npm-run-path-4.0.1.tgz#b7ecd1e5ed53da8e37a55e1c2269e0b97ed748ea" - integrity sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw== - dependencies: - path-key "^3.0.0" - -object-assign@^4: - version "4.1.1" - resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" - integrity sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM= - -on-finished@~2.3.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/on-finished/-/on-finished-2.3.0.tgz#20f1336481b083cd75337992a16971aa2d906947" - integrity sha1-IPEzZIGwg811M3mSoWlxqi2QaUc= - dependencies: - ee-first "1.1.1" - -once@^1.3.0: - version "1.4.0" - resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" - integrity sha1-WDsap3WWHUsROsF9nFC6753Xa9E= - dependencies: - wrappy "1" - -onetime@^5.1.2: - version "5.1.2" - resolved "https://registry.yarnpkg.com/onetime/-/onetime-5.1.2.tgz#d0e96ebb56b07476df1dd9c4806e5237985ca45e" - integrity sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg== - dependencies: - mimic-fn "^2.1.0" - -p-limit@^2.2.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-2.3.0.tgz#3dd33c647a214fdfffd835933eb086da0dc21db1" - integrity sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w== - dependencies: - p-try "^2.0.0" - -p-limit@^3.0.2: - version "3.1.0" - resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" - integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== - dependencies: - yocto-queue "^0.1.0" - -p-locate@^4.1.0: - version "4.1.0" - resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-4.1.0.tgz#a3428bb7088b3a60292f66919278b7c297ad4f07" - integrity sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A== - dependencies: - p-limit "^2.2.0" - -p-locate@^5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" - integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== - dependencies: - p-limit "^3.0.2" - -p-try@^2.0.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/p-try/-/p-try-2.2.0.tgz#cb2868540e313d61de58fafbe35ce9004d5540e6" - integrity sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ== - -parseurl@~1.3.3: - version "1.3.3" - resolved "https://registry.yarnpkg.com/parseurl/-/parseurl-1.3.3.tgz#9da19e7bee8d12dff0513ed5b76957793bc2e8d4" - integrity sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ== - -path-exists@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" - integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== - -path-is-absolute@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" - integrity sha1-F0uSaHNVNP+8es5r9TpanhtcX18= - -path-key@^3.0.0, path-key@^3.1.0: - version "3.1.1" - resolved "https://registry.yarnpkg.com/path-key/-/path-key-3.1.1.tgz#581f6ade658cbba65a0d3380de7753295054f375" - integrity sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q== - -path-parse@^1.0.7: - version "1.0.7" - resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" - integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== - -picocolors@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/picocolors/-/picocolors-1.0.0.tgz#cb5bdc74ff3f51892236eaf79d68bc44564ab81c" - integrity sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ== - -picomatch@^2.0.4, picomatch@^2.2.1: - version "2.3.1" - resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" - integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== - -pkg-dir@^4.2.0: - version "4.2.0" - resolved "https://registry.yarnpkg.com/pkg-dir/-/pkg-dir-4.2.0.tgz#f099133df7ede422e81d1d8448270eeb3e4261f3" - integrity sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ== - dependencies: - find-up "^4.0.0" - -platform@^1.3.3: - version "1.3.6" - resolved "https://registry.yarnpkg.com/platform/-/platform-1.3.6.tgz#48b4ce983164b209c2d45a107adb31f473a6e7a7" - integrity sha512-fnWVljUchTro6RiCFvCXBbNhJc2NijN7oIQxbwsyL0buWJPG85v81ehlHI9fXrJsMNgTofEoWIQeClKpgxFLrg== - -postcss-modules-extract-imports@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/postcss-modules-extract-imports/-/postcss-modules-extract-imports-3.0.0.tgz#cda1f047c0ae80c97dbe28c3e76a43b88025741d" - integrity sha512-bdHleFnP3kZ4NYDhuGlVK+CMrQ/pqUm8bx/oGL93K6gVwiclvX5x0n76fYMKuIGKzlABOy13zsvqjb0f92TEXw== - -postcss-modules-local-by-default@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/postcss-modules-local-by-default/-/postcss-modules-local-by-default-4.0.0.tgz#ebbb54fae1598eecfdf691a02b3ff3b390a5a51c" - integrity sha512-sT7ihtmGSF9yhm6ggikHdV0hlziDTX7oFoXtuVWeDd3hHObNkcHRo9V3yg7vCAY7cONyxJC/XXCmmiHHcvX7bQ== - dependencies: - icss-utils "^5.0.0" - postcss-selector-parser "^6.0.2" - postcss-value-parser "^4.1.0" - -postcss-modules-scope@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/postcss-modules-scope/-/postcss-modules-scope-3.0.0.tgz#9ef3151456d3bbfa120ca44898dfca6f2fa01f06" - integrity sha512-hncihwFA2yPath8oZ15PZqvWGkWf+XUfQgUGamS4LqoP1anQLOsOJw0vr7J7IwLpoY9fatA2qiGUGmuZL0Iqlg== - dependencies: - postcss-selector-parser "^6.0.4" - -postcss-modules-values@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/postcss-modules-values/-/postcss-modules-values-4.0.0.tgz#d7c5e7e68c3bb3c9b27cbf48ca0bb3ffb4602c9c" - integrity sha512-RDxHkAiEGI78gS2ofyvCsu7iycRv7oqw5xMWn9iMoR0N/7mf9D50ecQqUo5BZ9Zh2vH4bCUR/ktCqbB9m8vJjQ== - dependencies: - icss-utils "^5.0.0" - -postcss-selector-parser@^6.0.2, postcss-selector-parser@^6.0.4: - version "6.0.9" - resolved "https://registry.yarnpkg.com/postcss-selector-parser/-/postcss-selector-parser-6.0.9.tgz#ee71c3b9ff63d9cd130838876c13a2ec1a992b2f" - integrity sha512-UO3SgnZOVTwu4kyLR22UQ1xZh086RyNZppb7lLAKBFK8a32ttG5i87Y/P3+2bRSjZNyJ1B7hfFNo273tKe9YxQ== - dependencies: - cssesc "^3.0.0" - util-deprecate "^1.0.2" - -postcss-value-parser@^4.1.0: - version "4.2.0" - resolved "https://registry.yarnpkg.com/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz#723c09920836ba6d3e5af019f92bc0971c02e514" - integrity sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ== - -postcss@^8.2.15: - version "8.4.5" - resolved "https://registry.yarnpkg.com/postcss/-/postcss-8.4.5.tgz#bae665764dfd4c6fcc24dc0fdf7e7aa00cc77f95" - integrity sha512-jBDboWM8qpaqwkMwItqTQTiFikhs/67OYVvblFFTM7MrZjt6yMKd6r2kgXizEbTTljacm4NldIlZnhbjr84QYg== - dependencies: - nanoid "^3.1.30" - picocolors "^1.0.0" - source-map-js "^1.0.1" - -punycode@^2.1.0: - version "2.1.1" - resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.1.1.tgz#b58b010ac40c22c5657616c8d2c2c02c7bf479ec" - integrity sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A== - -qjobs@^1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/qjobs/-/qjobs-1.2.0.tgz#c45e9c61800bd087ef88d7e256423bdd49e5d071" - integrity sha512-8YOJEHtxpySA3fFDyCRxA+UUV+fA+rTWnuWvylOK/NCjhY+b4ocCtmu8TtsWb+mYeU+GCHf/S66KZF/AsteKHg== - -qs@6.9.6: - version "6.9.6" - resolved "https://registry.yarnpkg.com/qs/-/qs-6.9.6.tgz#26ed3c8243a431b2924aca84cc90471f35d5a0ee" - integrity sha512-TIRk4aqYLNoJUbd+g2lEdz5kLWIuTMRagAXxl78Q0RiVjAOugHmeKNGdd3cwo/ktpf9aL9epCfFqWDEKysUlLQ== - -randombytes@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" - integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== - dependencies: - safe-buffer "^5.1.0" - -range-parser@^1.2.1: - version "1.2.1" - resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.2.1.tgz#3cf37023d199e1c24d1a55b84800c2f3e6468031" - integrity sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg== - -raw-body@2.4.2: - version "2.4.2" - resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.4.2.tgz#baf3e9c21eebced59dd6533ac872b71f7b61cb32" - integrity sha512-RPMAFUJP19WIet/99ngh6Iv8fzAbqum4Li7AD6DtGaW2RpMB/11xDoalPiJMTbu6I3hkbMVkATvZrqb9EEqeeQ== - dependencies: - bytes "3.1.1" - http-errors "1.8.1" - iconv-lite "0.4.24" - unpipe "1.0.0" - -readdirp@~3.6.0: - version "3.6.0" - resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.6.0.tgz#74a370bd857116e245b29cc97340cd431a02a6c7" - integrity sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA== - dependencies: - picomatch "^2.2.1" - -rechoir@^0.7.0: - version "0.7.1" - resolved "https://registry.yarnpkg.com/rechoir/-/rechoir-0.7.1.tgz#9478a96a1ca135b5e88fc027f03ee92d6c645686" - integrity sha512-/njmZ8s1wVeR6pjTZ+0nCnv8SpZNRMT2D1RLOJQESlYFDBvwpTA4KWJpZ+sBJ4+vhjILRcK7JIFdGCdxEAAitg== - dependencies: - resolve "^1.9.0" - -require-directory@^2.1.1: - version "2.1.1" - resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" - integrity sha1-jGStX9MNqxyXbiNE/+f3kqam30I= - -requires-port@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/requires-port/-/requires-port-1.0.0.tgz#925d2601d39ac485e091cf0da5c6e694dc3dcaff" - integrity sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8= - -resolve-cwd@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/resolve-cwd/-/resolve-cwd-3.0.0.tgz#0f0075f1bb2544766cf73ba6a6e2adfebcb13f2d" - integrity sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg== - dependencies: - resolve-from "^5.0.0" - -resolve-from@^5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-5.0.0.tgz#c35225843df8f776df21c57557bc087e9dfdfc69" - integrity sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw== - -resolve@^1.9.0: - version "1.22.0" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.0.tgz#5e0b8c67c15df57a89bdbabe603a002f21731198" - integrity sha512-Hhtrw0nLeSrFQ7phPp4OOcVjLPIeMnRlr5mcnVuMe7M/7eBn98A3hmFRLoFo3DLZkivSYwhRUJTyPyWAk56WLw== - dependencies: - is-core-module "^2.8.1" - path-parse "^1.0.7" - supports-preserve-symlinks-flag "^1.0.0" - -rfdc@^1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/rfdc/-/rfdc-1.3.0.tgz#d0b7c441ab2720d05dc4cf26e01c89631d9da08b" - integrity sha512-V2hovdzFbOi77/WajaSMXk2OLm+xNIeQdMMuB7icj7bk6zi2F8GGAxigcnDFpJHbNyNcgyJDiP+8nOrY5cZGrA== - -rimraf@^3.0.0, rimraf@^3.0.2: - version "3.0.2" - resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" - integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== - dependencies: - glob "^7.1.3" - -safe-buffer@^5.1.0: - version "5.2.1" - resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" - integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== - -"safer-buffer@>= 2.1.2 < 3", "safer-buffer@>= 2.1.2 < 3.0.0": - version "2.1.2" - resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" - integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== - -schema-utils@^3.1.0, schema-utils@^3.1.1: - version "3.1.1" - resolved "https://registry.yarnpkg.com/schema-utils/-/schema-utils-3.1.1.tgz#bc74c4b6b6995c1d88f76a8b77bea7219e0c8281" - integrity sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw== - dependencies: - "@types/json-schema" "^7.0.8" - ajv "^6.12.5" - ajv-keywords "^3.5.2" - -semver@^7.3.5: - version "7.3.5" - resolved "https://registry.yarnpkg.com/semver/-/semver-7.3.5.tgz#0b621c879348d8998e4b0e4be94b3f12e6018ef7" - integrity sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ== - dependencies: - lru-cache "^6.0.0" - -serialize-javascript@6.0.0, serialize-javascript@^6.0.0: - version "6.0.0" - resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz#efae5d88f45d7924141da8b5c3a7a7e663fefeb8" - integrity sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag== - dependencies: - randombytes "^2.1.0" - -setprototypeof@1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.2.0.tgz#66c9a24a73f9fc28cbe66b09fed3d33dcaf1b424" - integrity sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw== - -shallow-clone@^3.0.0: - version "3.0.1" - resolved "https://registry.yarnpkg.com/shallow-clone/-/shallow-clone-3.0.1.tgz#8f2981ad92531f55035b01fb230769a40e02efa3" - integrity sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA== - dependencies: - kind-of "^6.0.2" - -shebang-command@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-2.0.0.tgz#ccd0af4f8835fbdc265b82461aaf0c36663f34ea" - integrity sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA== - dependencies: - shebang-regex "^3.0.0" - -shebang-regex@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-3.0.0.tgz#ae16f1644d873ecad843b0307b143362d4c42172" - integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A== - -signal-exit@^3.0.3: - version "3.0.6" - resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.6.tgz#24e630c4b0f03fea446a2bd299e62b4a6ca8d0af" - integrity sha512-sDl4qMFpijcGw22U5w63KmD3cZJfBuFlVNbVMKje2keoKML7X2UzWbc4XrmEbDwg0NXJc3yv4/ox7b+JWb57kQ== - -socket.io-adapter@~2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/socket.io-adapter/-/socket.io-adapter-2.1.0.tgz#edc5dc36602f2985918d631c1399215e97a1b527" - integrity sha512-+vDov/aTsLjViYTwS9fPy5pEtTkrbEKsw2M+oVSoFGw6OD1IpvlV1VPhUzNbofCQ8oyMbdYJqDtGdmHQK6TdPg== - -socket.io-parser@~4.0.3: - version "4.0.4" - resolved "https://registry.yarnpkg.com/socket.io-parser/-/socket.io-parser-4.0.4.tgz#9ea21b0d61508d18196ef04a2c6b9ab630f4c2b0" - integrity sha512-t+b0SS+IxG7Rxzda2EVvyBZbvFPBCjJoyHuE0P//7OAsN23GItzDRdWa6ALxZI/8R5ygK7jAR6t028/z+7295g== - dependencies: - "@types/component-emitter" "^1.2.10" - component-emitter "~1.3.0" - debug "~4.3.1" - -socket.io@^3.1.0: - version "3.1.2" - resolved "https://registry.yarnpkg.com/socket.io/-/socket.io-3.1.2.tgz#06e27caa1c4fc9617547acfbb5da9bc1747da39a" - integrity sha512-JubKZnTQ4Z8G4IZWtaAZSiRP3I/inpy8c/Bsx2jrwGrTbKeVU5xd6qkKMHpChYeM3dWZSO0QACiGK+obhBNwYw== - dependencies: - "@types/cookie" "^0.4.0" - "@types/cors" "^2.8.8" - "@types/node" ">=10.0.0" - accepts "~1.3.4" - base64id "~2.0.0" - debug "~4.3.1" - engine.io "~4.1.0" - socket.io-adapter "~2.1.0" - socket.io-parser "~4.0.3" - -source-map-js@^0.6.2: - version "0.6.2" - resolved "https://registry.yarnpkg.com/source-map-js/-/source-map-js-0.6.2.tgz#0bb5de631b41cfbda6cfba8bd05a80efdfd2385e" - integrity sha512-/3GptzWzu0+0MBQFrDKzw/DvvMTUORvgY6k6jd/VS6iCR4RDTKWH6v6WPwQoUO8667uQEf9Oe38DxAYWY5F/Ug== - -source-map-js@^1.0.1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/source-map-js/-/source-map-js-1.0.2.tgz#adbc361d9c62df380125e7f161f71c826f1e490c" - integrity sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw== - -source-map-loader@3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/source-map-loader/-/source-map-loader-3.0.0.tgz#f2a04ee2808ad01c774dea6b7d2639839f3b3049" - integrity sha512-GKGWqWvYr04M7tn8dryIWvb0s8YM41z82iQv01yBtIylgxax0CwvSy6gc2Y02iuXwEfGWRlMicH0nvms9UZphw== - dependencies: - abab "^2.0.5" - iconv-lite "^0.6.2" - source-map-js "^0.6.2" - -source-map-support@0.5.20: - version "0.5.20" - resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.20.tgz#12166089f8f5e5e8c56926b377633392dd2cb6c9" - integrity sha512-n1lZZ8Ve4ksRqizaBQgxXDgKwttHDhyfQjA6YZZn8+AroHbsIz+JjwxQDxbp+7y5OYCI8t1Yk7etjD9CRd2hIw== - dependencies: - buffer-from "^1.0.0" - source-map "^0.6.0" - -source-map-support@~0.5.20: - version "0.5.21" - resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.21.tgz#04fe7c7f9e1ed2d662233c28cb2b35b9f63f6e4f" - integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== - dependencies: - buffer-from "^1.0.0" - source-map "^0.6.0" - -source-map@^0.6.0, source-map@^0.6.1: - version "0.6.1" - resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" - integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== - -source-map@~0.7.2: - version "0.7.3" - resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.7.3.tgz#5302f8169031735226544092e64981f751750383" - integrity sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ== - -"statuses@>= 1.5.0 < 2", statuses@~1.5.0: - version "1.5.0" - resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.5.0.tgz#161c7dac177659fd9811f43771fa99381478628c" - integrity sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow= - -streamroller@^3.0.2: - version "3.0.2" - resolved "https://registry.yarnpkg.com/streamroller/-/streamroller-3.0.2.tgz#30418d0eee3d6c93ec897f892ed098e3a81e68b7" - integrity sha512-ur6y5S5dopOaRXBuRIZ1u6GC5bcEXHRZKgfBjfCglMhmIf+roVCECjvkEYzNQOXIN2/JPnkMPW/8B3CZoKaEPA== - dependencies: - date-format "^4.0.3" - debug "^4.1.1" - fs-extra "^10.0.0" - -string-width@^4.1.0, string-width@^4.2.0: - version "4.2.3" - resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010" - integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== - dependencies: - emoji-regex "^8.0.0" - is-fullwidth-code-point "^3.0.0" - strip-ansi "^6.0.1" - -strip-ansi@^6.0.0, strip-ansi@^6.0.1: - version "6.0.1" - resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" - integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== - dependencies: - ansi-regex "^5.0.1" - -strip-final-newline@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/strip-final-newline/-/strip-final-newline-2.0.0.tgz#89b852fb2fcbe936f6f4b3187afb0a12c1ab58ad" - integrity sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA== - -strip-json-comments@3.1.1: - version "3.1.1" - resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" - integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== - -style-loader@3.3.0: - version "3.3.0" - resolved "https://registry.yarnpkg.com/style-loader/-/style-loader-3.3.0.tgz#d66ea95fc50b22f8b79b69a9e414760fcf58d8d8" - integrity sha512-szANub7ksJtQioJYtpbWwh1hUl99uK15n5HDlikeCRil/zYMZgSxucHddyF/4A3qJMUiAjPhFowrrQuNMA7jwQ== - -supports-color@8.1.1, supports-color@^8.0.0: - version "8.1.1" - resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" - integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== - dependencies: - has-flag "^4.0.0" - -supports-color@^7.1.0: - version "7.2.0" - resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" - integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== - dependencies: - has-flag "^4.0.0" - -supports-preserve-symlinks-flag@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz#6eda4bd344a3c94aea376d4cc31bc77311039e09" - integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== - -tapable@^2.1.1, tapable@^2.2.0: - version "2.2.1" - resolved "https://registry.yarnpkg.com/tapable/-/tapable-2.2.1.tgz#1967a73ef4060a82f12ab96af86d52fdb76eeca0" - integrity sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ== - -terser-webpack-plugin@^5.1.3: - version "5.3.0" - resolved "https://registry.yarnpkg.com/terser-webpack-plugin/-/terser-webpack-plugin-5.3.0.tgz#21641326486ecf91d8054161c816e464435bae9f" - integrity sha512-LPIisi3Ol4chwAaPP8toUJ3L4qCM1G0wao7L3qNv57Drezxj6+VEyySpPw4B1HSO2Eg/hDY/MNF5XihCAoqnsQ== - dependencies: - jest-worker "^27.4.1" - schema-utils "^3.1.1" - serialize-javascript "^6.0.0" - source-map "^0.6.1" - terser "^5.7.2" - -terser@^5.7.2: - version "5.10.0" - resolved "https://registry.yarnpkg.com/terser/-/terser-5.10.0.tgz#b86390809c0389105eb0a0b62397563096ddafcc" - integrity sha512-AMmF99DMfEDiRJfxfY5jj5wNH/bYO09cniSqhfoyxc8sFoYIgkJy86G04UoZU5VjlpnplVu0K6Tx6E9b5+DlHA== - dependencies: - commander "^2.20.0" - source-map "~0.7.2" - source-map-support "~0.5.20" - -tmp@^0.2.1: - version "0.2.1" - resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.2.1.tgz#8457fc3037dcf4719c251367a1af6500ee1ccf14" - integrity sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ== - dependencies: - rimraf "^3.0.0" - -to-regex-range@^5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" - integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== - dependencies: - is-number "^7.0.0" - -toidentifier@1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/toidentifier/-/toidentifier-1.0.1.tgz#3be34321a88a820ed1bd80dfaa33e479fbb8dd35" - integrity sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA== - -type-is@~1.6.18: - version "1.6.18" - resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.18.tgz#4e552cd05df09467dcbc4ef739de89f2cf37c131" - integrity sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g== - dependencies: - media-typer "0.3.0" - mime-types "~2.1.24" - -typescript@3.9.5: - version "3.9.5" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.9.5.tgz#586f0dba300cde8be52dd1ac4f7e1009c1b13f36" - integrity sha512-hSAifV3k+i6lEoCJ2k6R2Z/rp/H3+8sdmcn5NrS3/3kE7+RyZXm9aqvxWqjEXHAd8b0pShatpcdMTvEdvAJltQ== - -ua-parser-js@^0.7.28: - version "0.7.31" - resolved "https://registry.yarnpkg.com/ua-parser-js/-/ua-parser-js-0.7.31.tgz#649a656b191dffab4f21d5e053e27ca17cbff5c6" - integrity sha512-qLK/Xe9E2uzmYI3qLeOmI0tEOt+TBBQyUIAh4aAgU05FVYzeZrKUdkAZfBNVGRaHVgV0TDkdEngJSw/SyQchkQ== - -universalify@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/universalify/-/universalify-2.0.0.tgz#75a4984efedc4b08975c5aeb73f530d02df25717" - integrity sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ== - -unpipe@1.0.0, unpipe@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" - integrity sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw= - -uri-js@^4.2.2: - version "4.4.1" - resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.4.1.tgz#9b1a52595225859e55f669d928f88c6c57f2a77e" - integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== - dependencies: - punycode "^2.1.0" - -util-deprecate@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" - integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8= - -utils-merge@1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/utils-merge/-/utils-merge-1.0.1.tgz#9f95710f50a267947b2ccc124741c1028427e713" - integrity sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM= - -v8-compile-cache@^2.2.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz#2de19618c66dc247dcfb6f99338035d8245a2cee" - integrity sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA== - -vary@^1: - version "1.1.2" - resolved "https://registry.yarnpkg.com/vary/-/vary-1.1.2.tgz#2299f02c6ded30d4a5961b0b9f74524a18f634fc" - integrity sha1-IpnwLG3tMNSllhsLn3RSShj2NPw= - -void-elements@^2.0.0: - version "2.0.1" - resolved "https://registry.yarnpkg.com/void-elements/-/void-elements-2.0.1.tgz#c066afb582bb1cb4128d60ea92392e94d5e9dbec" - integrity sha1-wGavtYK7HLQSjWDqkjkulNXp2+w= - -watchpack@^2.2.0: - version "2.3.1" - resolved "https://registry.yarnpkg.com/watchpack/-/watchpack-2.3.1.tgz#4200d9447b401156eeca7767ee610f8809bc9d25" - integrity sha512-x0t0JuydIo8qCNctdDrn1OzH/qDzk2+rdCOC3YzumZ42fiMqmQ7T3xQurykYMhYfHaPHTp4ZxAx2NfUo1K6QaA== - dependencies: - glob-to-regexp "^0.4.1" - graceful-fs "^4.1.2" - -webpack-cli@4.9.0: - version "4.9.0" - resolved "https://registry.yarnpkg.com/webpack-cli/-/webpack-cli-4.9.0.tgz#dc43e6e0f80dd52e89cbf73d5294bcd7ad6eb343" - integrity sha512-n/jZZBMzVEl4PYIBs+auy2WI0WTQ74EnJDiyD98O2JZY6IVIHJNitkYp/uTXOviIOMfgzrNvC9foKv/8o8KSZw== - dependencies: - "@discoveryjs/json-ext" "^0.5.0" - "@webpack-cli/configtest" "^1.1.0" - "@webpack-cli/info" "^1.4.0" - "@webpack-cli/serve" "^1.6.0" - colorette "^2.0.14" - commander "^7.0.0" - execa "^5.0.0" - fastest-levenshtein "^1.0.12" - import-local "^3.0.2" - interpret "^2.2.0" - rechoir "^0.7.0" - v8-compile-cache "^2.2.0" - webpack-merge "^5.7.3" - -webpack-merge@^4.1.5: - version "4.2.2" - resolved "https://registry.yarnpkg.com/webpack-merge/-/webpack-merge-4.2.2.tgz#a27c52ea783d1398afd2087f547d7b9d2f43634d" - integrity sha512-TUE1UGoTX2Cd42j3krGYqObZbOD+xF7u28WB7tfUordytSjbWTIjK/8V0amkBfTYN4/pB/GIDlJZZ657BGG19g== - dependencies: - lodash "^4.17.15" - -webpack-merge@^5.7.3: - version "5.8.0" - resolved "https://registry.yarnpkg.com/webpack-merge/-/webpack-merge-5.8.0.tgz#2b39dbf22af87776ad744c390223731d30a68f61" - integrity sha512-/SaI7xY0831XwP6kzuwhKWVKDP9t1QY1h65lAFLbZqMPIuYcD9QAW4u9STIbU9kaJbPBB/geU/gLr1wDjOhQ+Q== - dependencies: - clone-deep "^4.0.1" - wildcard "^2.0.0" - -webpack-sources@^3.2.0: - version "3.2.3" - resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-3.2.3.tgz#2d4daab8451fd4b240cc27055ff6a0c2ccea0cde" - integrity sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w== - -webpack@5.57.1: - version "5.57.1" - resolved "https://registry.yarnpkg.com/webpack/-/webpack-5.57.1.tgz#ead5ace2c17ecef2ae8126f143bfeaa7f55eab44" - integrity sha512-kHszukYjTPVfCOEyrUthA3jqJwduY/P3eO8I0gMNOZGIQWKAwZftxmp5hq6paophvwo9NoUrcZOecs9ulOyyTg== - dependencies: - "@types/eslint-scope" "^3.7.0" - "@types/estree" "^0.0.50" - "@webassemblyjs/ast" "1.11.1" - "@webassemblyjs/wasm-edit" "1.11.1" - "@webassemblyjs/wasm-parser" "1.11.1" - acorn "^8.4.1" - acorn-import-assertions "^1.7.6" - browserslist "^4.14.5" - chrome-trace-event "^1.0.2" - enhanced-resolve "^5.8.3" - es-module-lexer "^0.9.0" - eslint-scope "5.1.1" - events "^3.2.0" - glob-to-regexp "^0.4.1" - graceful-fs "^4.2.4" - json-parse-better-errors "^1.0.2" - loader-runner "^4.2.0" - mime-types "^2.1.27" - neo-async "^2.6.2" - schema-utils "^3.1.0" - tapable "^2.1.1" - terser-webpack-plugin "^5.1.3" - watchpack "^2.2.0" - webpack-sources "^3.2.0" - -which@2.0.2, which@^2.0.1: - version "2.0.2" - resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1" - integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== - dependencies: - isexe "^2.0.0" - -which@^1.2.1: - version "1.3.1" - resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a" - integrity sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ== - dependencies: - isexe "^2.0.0" - -wildcard@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/wildcard/-/wildcard-2.0.0.tgz#a77d20e5200c6faaac979e4b3aadc7b3dd7f8fec" - integrity sha512-JcKqAHLPxcdb9KM49dufGXn2x3ssnfjbcaQdLlfZsL9rH9wgDQjUtDxbo8NE0F6SFvydeu1VhZe7hZuHsB2/pw== - -workerpool@6.1.5: - version "6.1.5" - resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.1.5.tgz#0f7cf076b6215fd7e1da903ff6f22ddd1886b581" - integrity sha512-XdKkCK0Zqc6w3iTxLckiuJ81tiD/o5rBE/m+nXpRCB+/Sq4DqkfXZ/x0jW02DG1tGsfUGXbTJyZDP+eu67haSw== - -wrap-ansi@^7.0.0: - version "7.0.0" - resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" - integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== - dependencies: - ansi-styles "^4.0.0" - string-width "^4.1.0" - strip-ansi "^6.0.0" - -wrappy@1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" - integrity sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8= - -ws@~7.4.2: - version "7.4.6" - resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" - integrity sha512-YmhHDO4MzaDLB+M9ym/mDA5z0naX8j7SIlT8f8z+I0VtzsRbekxEutHSme7NPS2qE8StCYQNUnfWdXta/Yu85A== - -y18n@^5.0.5: - version "5.0.8" - resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" - integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== - -yallist@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" - integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== - -yargs-parser@20.2.4: - version "20.2.4" - resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" - integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== - -yargs-parser@^20.2.2: - version "20.2.9" - resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" - integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== - -yargs-unparser@2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" - integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== - dependencies: - camelcase "^6.0.0" - decamelize "^4.0.0" - flat "^5.0.2" - is-plain-obj "^2.1.0" - -yargs@16.2.0, yargs@^16.1.1: - version "16.2.0" - resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" - integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== - dependencies: - cliui "^7.0.2" - escalade "^3.1.1" - get-caller-file "^2.0.5" - require-directory "^2.1.1" - string-width "^4.2.0" - y18n "^5.0.5" - yargs-parser "^20.2.2" - -yocto-queue@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" - integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== -- 2.34.1 From 0b2e8ff25ee572c5561d5d5aaa392a7e66332fa1 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 8 Mar 2022 23:15:48 +0300 Subject: [PATCH 12/59] Build fixes --- build.gradle.kts | 5 +++-- buildSrc/build.gradle.kts | 3 ++- buildSrc/gradle.properties | 8 +------- buildSrc/settings.gradle.kts | 5 +++-- gradle.properties | 3 +-- settings.gradle.kts | 16 ---------------- 6 files changed, 10 insertions(+), 30 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index 3b48c7328..3372d505d 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -1,16 +1,17 @@ plugins { id("ru.mipt.npm.gradle.project") - id("org.jetbrains.kotlinx.kover") version "0.5.0-RC" + id("org.jetbrains.kotlinx.kover") version "0.5.0" } allprojects { repositories { + maven("https://repo.kotlin.link") maven("https://oss.sonatype.org/content/repositories/snapshots") mavenCentral() } group = "space.kscience" - version = "0.3.0-dev-19" + version = "0.3.0-dev-20" } subprojects { diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts index ceb220bd5..b69ebe6cd 100644 --- a/buildSrc/build.gradle.kts +++ b/buildSrc/build.gradle.kts @@ -7,6 +7,7 @@ plugins { java.targetCompatibility = JavaVersion.VERSION_11 repositories { + mavenLocal() maven("https://repo.kotlin.link") mavenCentral() gradlePluginPortal() @@ -14,7 +15,7 @@ repositories { val toolsVersion: String by extra val kotlinVersion = npmlibs.versions.kotlin.asProvider().get() -val benchmarksVersion = "0.4.2" +val benchmarksVersion = npmlibs.versions.kotlinx.benchmark.get() dependencies { api("ru.mipt.npm:gradle-tools:$toolsVersion") diff --git a/buildSrc/gradle.properties b/buildSrc/gradle.properties index 6678f24a8..05486d4f6 100644 --- a/buildSrc/gradle.properties +++ b/buildSrc/gradle.properties @@ -4,11 +4,5 @@ # kotlin.code.style=official -kotlin.mpp.stability.nowarn=true -kotlin.jupyter.add.scanner=false - -org.gradle.configureondemand=true -org.gradle.parallel=true - -toolsVersion=0.10.9-kotlin-1.6.10 +toolsVersion=0.11.1-kotlin-1.6.10 diff --git a/buildSrc/settings.gradle.kts b/buildSrc/settings.gradle.kts index 87ff205f6..9c5550602 100644 --- a/buildSrc/settings.gradle.kts +++ b/buildSrc/settings.gradle.kts @@ -3,7 +3,6 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ - enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") enableFeaturePreview("VERSION_CATALOGS") @@ -12,8 +11,10 @@ dependencyResolutionManagement { val toolsVersion: String by extra repositories { + mavenLocal() maven("https://repo.kotlin.link") mavenCentral() + gradlePluginPortal() } versionCatalogs { @@ -21,4 +22,4 @@ dependencyResolutionManagement { from("ru.mipt.npm:version-catalog:$toolsVersion") } } -} +} \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index 7dd9e6d61..7d9628621 100644 --- a/gradle.properties +++ b/gradle.properties @@ -5,11 +5,10 @@ kotlin.code.style=official kotlin.mpp.stability.nowarn=true +kotlin.native.ignoreDisabledTargets=true kotlin.jupyter.add.scanner=false org.gradle.configureondemand=true org.gradle.parallel=true org.gradle.jvmargs=-XX:MaxMetaspaceSize=1G - -toolsVersion=0.11.1-kotlin-1.6.10 diff --git a/settings.gradle.kts b/settings.gradle.kts index 3001d000c..a8b473fee 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -3,22 +3,6 @@ rootProject.name = "kmath" enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") enableFeaturePreview("VERSION_CATALOGS") -dependencyResolutionManagement { - - val toolsVersion: String by extra - - repositories { - maven("https://repo.kotlin.link") - mavenCentral() - } - - versionCatalogs { - create("npmlibs") { - from("ru.mipt.npm:version-catalog:$toolsVersion") - } - } -} - include( ":kmath-memory", ":kmath-complex", -- 2.34.1 From 39640498fc93f4ca5adc4c439c641d5aeb4510cb Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sat, 19 Mar 2022 09:20:32 +0300 Subject: [PATCH 13/59] Another histogram refactor --- build.gradle.kts | 2 +- buildSrc/gradle.properties | 2 +- .../kmath/domains/HyperSquareDomain.kt | 11 ++++- .../kmath/histogram/DoubleHistogramSpace.kt | 46 +++++++++++-------- .../kmath/histogram/IndexedHistogramSpace.kt | 20 ++++---- .../kmath/histogram/UnivariateHistogram.kt | 20 -------- .../kmath/histogram/TreeHistogramSpace.kt | 22 ++++++++- .../kmath/histogram/TreeHistogramTest.kt | 2 +- 8 files changed, 71 insertions(+), 54 deletions(-) rename kmath-histograms/src/{jvmMain => commonMain}/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt (71%) diff --git a/build.gradle.kts b/build.gradle.kts index 3372d505d..ee77f32df 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -11,7 +11,7 @@ allprojects { } group = "space.kscience" - version = "0.3.0-dev-20" + version = "0.3.0-dev-21" } subprojects { diff --git a/buildSrc/gradle.properties b/buildSrc/gradle.properties index 05486d4f6..713f9bcd9 100644 --- a/buildSrc/gradle.properties +++ b/buildSrc/gradle.properties @@ -5,4 +5,4 @@ kotlin.code.style=official -toolsVersion=0.11.1-kotlin-1.6.10 +toolsVersion=0.11.2-kotlin-1.6.10 diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt index bd5514623..2fac442e7 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt @@ -7,6 +7,7 @@ package space.kscience.kmath.domains import space.kscience.kmath.linear.Point import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.indices /** @@ -16,9 +17,17 @@ import space.kscience.kmath.structures.indices * @author Alexander Nozik */ @UnstableKMathAPI -public class HyperSquareDomain(private val lower: Buffer, private val upper: Buffer) : DoubleDomain { +public class HyperSquareDomain(public val lower: Buffer, public val upper: Buffer) : DoubleDomain { + init { + require(lower.size == upper.size) { + "Domain borders size mismatch. Lower borders size is ${lower.size}, but upper borders size is ${upper.size}" + } + } + override val dimension: Int get() = lower.size + public val center: DoubleBuffer get() = DoubleBuffer(dimension) { (lower[it] + upper[it]) / 2.0 } + override operator fun contains(point: Point): Boolean = point.indices.all { i -> point[i] in lower[i]..upper[i] } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt index 61d0b9f33..27f04d60b 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt @@ -5,7 +5,6 @@ package space.kscience.kmath.histogram -import space.kscience.kmath.domains.Domain import space.kscience.kmath.domains.HyperSquareDomain import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.* @@ -13,6 +12,9 @@ import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.structures.* import kotlin.math.floor +/** + * Multivariate histogram space for hyper-square real-field bins. + */ public class DoubleHistogramSpace( private val lower: Buffer, private val upper: Buffer, @@ -47,7 +49,7 @@ public class DoubleHistogramSpace( } @OptIn(UnstableKMathAPI::class) - override fun getDomain(index: IntArray): Domain { + override fun getDomain(index: IntArray): HyperSquareDomain { val lowerBoundary = index.mapIndexed { axis, i -> when (i) { 0 -> Double.NEGATIVE_INFINITY @@ -67,8 +69,13 @@ public class DoubleHistogramSpace( return HyperSquareDomain(lowerBoundary, upperBoundary) } + @OptIn(UnstableKMathAPI::class) + public val Bin.domain: HyperSquareDomain + get() = (this as? DomainBin)?.domain as? HyperSquareDomain + ?: error("Im a teapot. This is not my bin") - override fun produceBin(index: IntArray, value: Double): Bin { + @OptIn(UnstableKMathAPI::class) + override fun produceBin(index: IntArray, value: Double): DomainBin { val domain = getDomain(index) return DomainBin(domain, value) } @@ -96,7 +103,9 @@ public class DoubleHistogramSpace( *) *``` */ - public fun fromRanges(vararg ranges: ClosedFloatingPointRange): DoubleHistogramSpace = DoubleHistogramSpace( + public fun fromRanges( + vararg ranges: ClosedFloatingPointRange, + ): DoubleHistogramSpace = DoubleHistogramSpace( ranges.map(ClosedFloatingPointRange::start).asBuffer(), ranges.map(ClosedFloatingPointRange::endInclusive).asBuffer() ) @@ -110,21 +119,22 @@ public class DoubleHistogramSpace( *) *``` */ - public fun fromRanges(vararg ranges: Pair, Int>): DoubleHistogramSpace = - DoubleHistogramSpace( - ListBuffer( - ranges - .map(Pair, Int>::first) - .map(ClosedFloatingPointRange::start) - ), + public fun fromRanges( + vararg ranges: Pair, Int>, + ): DoubleHistogramSpace = DoubleHistogramSpace( + ListBuffer( + ranges + .map(Pair, Int>::first) + .map(ClosedFloatingPointRange::start) + ), - ListBuffer( - ranges - .map(Pair, Int>::first) - .map(ClosedFloatingPointRange::endInclusive) - ), + ListBuffer( + ranges + .map(Pair, Int>::first) + .map(ClosedFloatingPointRange::endInclusive) + ), - ranges.map(Pair, Int>::second).toIntArray() - ) + ranges.map(Pair, Int>::second).toIntArray() + ) } } \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt index 9275c1c5e..bfacebb43 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt @@ -7,7 +7,6 @@ package space.kscience.kmath.histogram import space.kscience.kmath.domains.Domain import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.DefaultStrides import space.kscience.kmath.nd.FieldND import space.kscience.kmath.nd.Shape @@ -24,22 +23,21 @@ public data class DomainBin>( override val value: Number, ) : Bin, Domain by domain -@OptIn(UnstableKMathAPI::class) public class IndexedHistogram, V : Any>( - public val context: IndexedHistogramSpace, + public val histogramSpace: IndexedHistogramSpace, public val values: StructureND, ) : Histogram> { override fun get(point: Point): Bin? { - val index = context.getIndex(point) ?: return null - return context.produceBin(index, values[index]) + val index = histogramSpace.getIndex(point) ?: return null + return histogramSpace.produceBin(index, values[index]) } - override val dimension: Int get() = context.shape.size + override val dimension: Int get() = histogramSpace.shape.size override val bins: Iterable> - get() = DefaultStrides(context.shape).asSequence().map { - context.produceBin(it, values[it]) + get() = DefaultStrides(histogramSpace.shape).asSequence().map { + histogramSpace.produceBin(it, values[it]) }.asIterable() } @@ -67,13 +65,13 @@ public interface IndexedHistogramSpace, V : Any> public fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram override fun add(left: IndexedHistogram, right: IndexedHistogram): IndexedHistogram { - require(left.context == this) { "Can't operate on a histogram produced by external space" } - require(right.context == this) { "Can't operate on a histogram produced by external space" } + require(left.histogramSpace == this) { "Can't operate on a histogram produced by external space" } + require(right.histogramSpace == this) { "Can't operate on a histogram produced by external space" } return IndexedHistogram(this, histogramValueSpace { left.values + right.values }) } override fun scale(a: IndexedHistogram, value: Double): IndexedHistogram { - require(a.context == this) { "Can't operate on a histogram produced by external space" } + require(a.histogramSpace == this) { "Can't operate on a histogram produced by external space" } return IndexedHistogram(this, histogramValueSpace { a.values * value }) } diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt similarity index 71% rename from kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt rename to kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt index ac0576a8e..69ea83ae3 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt @@ -37,26 +37,6 @@ public class UnivariateBin( public interface UnivariateHistogram : Histogram { public operator fun get(value: Double): UnivariateBin? override operator fun get(point: Buffer): UnivariateBin? = get(point[0]) - - public companion object { - /** - * Build and fill a [UnivariateHistogram]. Returns a read-only histogram. - */ - public inline fun uniform( - binSize: Double, - start: Double = 0.0, - builder: UnivariateHistogramBuilder.() -> Unit, - ): UnivariateHistogram = TreeHistogramSpace.uniform(binSize, start).fill(builder) - - /** - * Build and fill a histogram with custom borders. Returns a read-only histogram. - */ - public inline fun custom( - borders: DoubleArray, - builder: UnivariateHistogramBuilder.() -> Unit, - ): UnivariateHistogram = TreeHistogramSpace.custom(borders).fill(builder) - - } } @UnstableKMathAPI diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt index 0853615e6..1ab49003c 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt @@ -49,7 +49,9 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> UnivariateDomain fun createBin(value: Double): BinCounter { val binDefinition = binFactory(value) val newBin = BinCounter(binDefinition) - synchronized(this) { bins[binDefinition.center] = newBin } + synchronized(this) { + bins[binDefinition.center] = newBin + } return newBin } @@ -131,6 +133,24 @@ public class TreeHistogramSpace( override val zero: UnivariateHistogram by lazy { fill { } } public companion object { + /** + * Build and fill a [UnivariateHistogram]. Returns a read-only histogram. + */ + public inline fun uniform( + binSize: Double, + start: Double = 0.0, + builder: UnivariateHistogramBuilder.() -> Unit, + ): UnivariateHistogram = uniform(binSize, start).fill(builder) + + /** + * Build and fill a histogram with custom borders. Returns a read-only histogram. + */ + public inline fun custom( + borders: DoubleArray, + builder: UnivariateHistogramBuilder.() -> Unit, + ): UnivariateHistogram = custom(borders).fill(builder) + + /** * Build and fill a [UnivariateHistogram]. Returns a read-only histogram. */ diff --git a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt index 28a1b03cb..f1a8f953b 100644 --- a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt +++ b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt @@ -13,7 +13,7 @@ class TreeHistogramTest { @Test fun normalFill() { - val histogram = UnivariateHistogram.uniform(0.1) { + val histogram = TreeHistogramSpace.uniform(0.1) { repeat(100_000) { putValue(Random.nextDouble()) } -- 2.34.1 From 29369cd6d7ef4a0b127df5551953e0b7239ffdec Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 22 Mar 2022 22:17:20 +0300 Subject: [PATCH 14/59] [WIP] Another histogram refactor --- .../{UnivariateDomain.kt => Domain1D.kt} | 15 +++- .../kmath/histogram/DoubleHistogramSpace.kt | 22 +++--- .../kscience/kmath/histogram/Histogram.kt | 33 +++++---- .../kscience/kmath/histogram/Histogram1D.kt | 56 +++++++++++++++ .../kmath/histogram/IndexedHistogramSpace.kt | 27 +++---- .../histogram/UniformDoubleHistogram1D.kt | 9 +++ .../kmath/histogram/UnivariateHistogram.kt | 59 --------------- .../kmath/histogram/TreeHistogramSpace.kt | 71 +++++++++---------- 8 files changed, 159 insertions(+), 133 deletions(-) rename kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/{UnivariateDomain.kt => Domain1D.kt} (57%) create mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt create mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt delete mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnivariateDomain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt similarity index 57% rename from kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnivariateDomain.kt rename to kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt index 9020ef8cb..f50f16c11 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnivariateDomain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt @@ -9,16 +9,21 @@ import space.kscience.kmath.linear.Point import space.kscience.kmath.misc.UnstableKMathAPI @UnstableKMathAPI -public class UnivariateDomain(public val range: ClosedFloatingPointRange) : DoubleDomain { +public abstract class Domain1D>(public val range: ClosedRange) : Domain { override val dimension: Int get() = 1 - public operator fun contains(d: Double): Boolean = range.contains(d) + public operator fun contains(value: T): Boolean = range.contains(value) - override operator fun contains(point: Point): Boolean { + override operator fun contains(point: Point): Boolean { require(point.size == 0) return contains(point[0]) } +} +@UnstableKMathAPI +public class DoubleDomain1D( + @Suppress("CanBeParameter") public val doubleRange: ClosedFloatingPointRange, +) : Domain1D(doubleRange), DoubleDomain { override fun getLowerBound(num: Int): Double { require(num == 0) return range.start @@ -31,3 +36,7 @@ public class UnivariateDomain(public val range: ClosedFloatingPointRange override fun volume(): Double = range.endInclusive - range.start } + +@UnstableKMathAPI +public val DoubleDomain1D.center: Double + get() = (range.endInclusive + range.start) / 2 diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt index 27f04d60b..c0df8c2cc 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt @@ -6,6 +6,7 @@ package space.kscience.kmath.histogram import space.kscience.kmath.domains.HyperSquareDomain +import space.kscience.kmath.linear.Point import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleField @@ -31,7 +32,7 @@ public class DoubleHistogramSpace( public val dimension: Int get() = lower.size override val shape: IntArray = IntArray(binNums.size) { binNums[it] + 2 } - override val histogramValueSpace: DoubleFieldND = DoubleField.ndAlgebra(*shape) + override val histogramValueAlgebra: DoubleFieldND = DoubleField.ndAlgebra(*shape) private val binSize = DoubleBuffer(dimension) { (upper[it] - lower[it]) / binNums[it] } @@ -70,21 +71,20 @@ public class DoubleHistogramSpace( } @OptIn(UnstableKMathAPI::class) - public val Bin.domain: HyperSquareDomain - get() = (this as? DomainBin)?.domain as? HyperSquareDomain - ?: error("Im a teapot. This is not my bin") - - @OptIn(UnstableKMathAPI::class) - override fun produceBin(index: IntArray, value: Double): DomainBin { + override fun produceBin(index: IntArray, value: Double): DomainBin { val domain = getDomain(index) return DomainBin(domain, value) } - override fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram { + override fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram { val ndCounter = StructureND.auto(shape) { Counter.double() } - val hBuilder = HistogramBuilder { point, value -> - val index = getIndex(point) - ndCounter[index].add(value.toDouble()) + val hBuilder = object : HistogramBuilder { + override val defaultValue: Double get() = 1.0 + + override fun putValue(point: Point, value: Double) { + val index = getIndex(point) + ndCounter[index].add(value) + } } hBuilder.apply(builder) val values: BufferND = ndCounter.mapToBuffer { it.value } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt index 4e803fc63..64c031c7a 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt @@ -13,14 +13,14 @@ import space.kscience.kmath.structures.asBuffer /** * The binned data element. Could be a histogram bin with a number of counts or an artificial construct. */ -public interface Bin : Domain { +public interface Bin : Domain { /** * The value of this bin. */ - public val value: Number + public val value: V } -public interface Histogram> { +public interface Histogram> { /** * Find existing bin, corresponding to given coordinates */ @@ -32,29 +32,38 @@ public interface Histogram> { public val dimension: Int public val bins: Iterable + + public companion object { + //A discoverability root + } } -public fun interface HistogramBuilder { +public interface HistogramBuilder { /** - * Increment appropriate bin + * The default value increment for a bin */ - public fun putValue(point: Point, value: Number) + public val defaultValue: V + + /** + * Increment appropriate bin with given value + */ + public fun putValue(point: Point, value: V = defaultValue) } -public fun > HistogramBuilder.put(point: Point): Unit = putValue(point, 1.0) +public fun HistogramBuilder.put(point: Point): Unit = putValue(point) -public fun HistogramBuilder.put(vararg point: T): Unit = put(point.asBuffer()) +public fun HistogramBuilder.put(vararg point: T): Unit = put(point.asBuffer()) -public fun HistogramBuilder.put(vararg point: Number): Unit = +public fun HistogramBuilder.put(vararg point: Number): Unit = put(DoubleBuffer(point.map { it.toDouble() }.toDoubleArray())) -public fun HistogramBuilder.put(vararg point: Double): Unit = put(DoubleBuffer(point)) -public fun HistogramBuilder.fill(sequence: Iterable>): Unit = sequence.forEach { put(it) } +public fun HistogramBuilder.put(vararg point: Double): Unit = put(DoubleBuffer(point)) +public fun HistogramBuilder.fill(sequence: Iterable>): Unit = sequence.forEach { put(it) } /** * Pass a sequence builder into histogram */ -public fun HistogramBuilder.fill(block: suspend SequenceScope>.() -> Unit): Unit = +public fun HistogramBuilder.fill(block: suspend SequenceScope>.() -> Unit): Unit = fill(sequence(block).asIterable()) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt new file mode 100644 index 000000000..e9c62b141 --- /dev/null +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt @@ -0,0 +1,56 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.histogram + +import space.kscience.kmath.domains.Domain1D +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.asSequence +import space.kscience.kmath.structures.Buffer + + +/** + * A univariate bin based on a range + * + * @property value The value of histogram including weighting + * @property standardDeviation Standard deviation of the bin value. Zero or negative if not applicable + */ +@UnstableKMathAPI +public class Bin1D, out V>( + public val domain: Domain1D, + override val value: V, +) : Bin, ClosedRange by domain.range { + + override val dimension: Int get() = 1 + + override fun contains(point: Buffer): Boolean = point.size == 1 && contains(point[0]) +} + +@OptIn(UnstableKMathAPI::class) +public interface Histogram1D, V> : Histogram> { + override val dimension: Int get() = 1 + public operator fun get(value: T): Bin1D? + override operator fun get(point: Buffer): Bin1D? = get(point[0]) +} + +@UnstableKMathAPI +public interface Histogram1DBuilder : HistogramBuilder { + /** + * Thread safe put operation + */ + public fun putValue(at: T, value: V = defaultValue) +} + +@UnstableKMathAPI +public fun Histogram1DBuilder.fill(items: Iterable): Unit = + items.forEach(this::putValue) + +@UnstableKMathAPI +public fun Histogram1DBuilder.fill(array: DoubleArray): Unit = + array.forEach(this::putValue) + +@UnstableKMathAPI +public fun Histogram1DBuilder.fill(buffer: Buffer): Unit = + buffer.asSequence().forEach(this::putValue) \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt index bfacebb43..a2623b1a1 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt @@ -18,24 +18,28 @@ import space.kscience.kmath.operations.invoke /** * A simple histogram bin based on domain */ -public data class DomainBin>( +public data class DomainBin, out V>( public val domain: Domain, - override val value: Number, -) : Bin, Domain by domain + override val value: V, +) : Bin, Domain by domain +/** + * @param T the type of the argument space + * @param V the type of bin value + */ public class IndexedHistogram, V : Any>( public val histogramSpace: IndexedHistogramSpace, public val values: StructureND, -) : Histogram> { +) : Histogram> { - override fun get(point: Point): Bin? { + override fun get(point: Point): DomainBin? { val index = histogramSpace.getIndex(point) ?: return null return histogramSpace.produceBin(index, values[index]) } override val dimension: Int get() = histogramSpace.shape.size - override val bins: Iterable> + override val bins: Iterable> get() = DefaultStrides(histogramSpace.shape).asSequence().map { histogramSpace.produceBin(it, values[it]) }.asIterable() @@ -46,9 +50,8 @@ public class IndexedHistogram, V : Any>( */ public interface IndexedHistogramSpace, V : Any> : Group>, ScaleOperations> { - //public val valueSpace: Space public val shape: Shape - public val histogramValueSpace: FieldND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), + public val histogramValueAlgebra: FieldND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), /** * Resolve index of the bin including given [point] @@ -60,19 +63,19 @@ public interface IndexedHistogramSpace, V : Any> */ public fun getDomain(index: IntArray): Domain? - public fun produceBin(index: IntArray, value: V): Bin + public fun produceBin(index: IntArray, value: V): DomainBin - public fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram + public fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram override fun add(left: IndexedHistogram, right: IndexedHistogram): IndexedHistogram { require(left.histogramSpace == this) { "Can't operate on a histogram produced by external space" } require(right.histogramSpace == this) { "Can't operate on a histogram produced by external space" } - return IndexedHistogram(this, histogramValueSpace { left.values + right.values }) + return IndexedHistogram(this, histogramValueAlgebra { left.values + right.values }) } override fun scale(a: IndexedHistogram, value: Double): IndexedHistogram { require(a.histogramSpace == this) { "Can't operate on a histogram produced by external space" } - return IndexedHistogram(this, histogramValueSpace { a.values * value }) + return IndexedHistogram(this, histogramValueAlgebra { a.values * value }) } override val zero: IndexedHistogram get() = produce { } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt new file mode 100644 index 000000000..856cd8592 --- /dev/null +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt @@ -0,0 +1,9 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.histogram + +//class UniformDoubleHistogram1D: DoubleHistogram1D { +//} \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt deleted file mode 100644 index 69ea83ae3..000000000 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UnivariateHistogram.kt +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -package space.kscience.kmath.histogram - -import space.kscience.kmath.domains.UnivariateDomain -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.asSequence -import space.kscience.kmath.structures.Buffer - - -@UnstableKMathAPI -public val UnivariateDomain.center: Double - get() = (range.endInclusive + range.start) / 2 - -/** - * A univariate bin based on a range - * - * @property value The value of histogram including weighting - * @property standardDeviation Standard deviation of the bin value. Zero or negative if not applicable - */ -@UnstableKMathAPI -public class UnivariateBin( - public val domain: UnivariateDomain, - override val value: Double, - public val standardDeviation: Double, -) : Bin, ClosedFloatingPointRange by domain.range { - - override val dimension: Int get() = 1 - - override fun contains(point: Buffer): Boolean = point.size == 1 && contains(point[0]) -} - -@OptIn(UnstableKMathAPI::class) -public interface UnivariateHistogram : Histogram { - public operator fun get(value: Double): UnivariateBin? - override operator fun get(point: Buffer): UnivariateBin? = get(point[0]) -} - -@UnstableKMathAPI -public interface UnivariateHistogramBuilder : HistogramBuilder { - /** - * Thread safe put operation - */ - public fun putValue(at: Double, value: Double = 1.0) - - override fun putValue(point: Buffer, value: Number) -} - -@UnstableKMathAPI -public fun UnivariateHistogramBuilder.fill(items: Iterable): Unit = items.forEach(this::putValue) - -@UnstableKMathAPI -public fun UnivariateHistogramBuilder.fill(array: DoubleArray): Unit = array.forEach(this::putValue) - -@UnstableKMathAPI -public fun UnivariateHistogramBuilder.fill(buffer: Buffer): Unit = buffer.asSequence().forEach(this::putValue) \ No newline at end of file diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt index 1ab49003c..9d07d5014 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt @@ -5,7 +5,7 @@ package space.kscience.kmath.histogram -import space.kscience.kmath.domains.UnivariateDomain +import space.kscience.kmath.domains.DoubleDomain1D import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Group import space.kscience.kmath.operations.ScaleOperations @@ -15,7 +15,7 @@ import kotlin.math.abs import kotlin.math.floor import kotlin.math.sqrt -private fun > TreeMap.getBin(value: Double): B? { +private fun > TreeMap.getBin(value: Double): B? { // check ceiling entry and return it if it is what needed val ceil = ceilingEntry(value)?.value if (ceil != null && value in ceil) return ceil @@ -28,19 +28,18 @@ private fun > TreeMap.getBin(val @UnstableKMathAPI public class TreeHistogram( - private val binMap: TreeMap, -) : UnivariateHistogram { - override fun get(value: Double): UnivariateBin? = binMap.getBin(value) - override val dimension: Int get() = 1 - override val bins: Collection get() = binMap.values + private val binMap: TreeMap>, +) : Histogram1D { + override fun get(value: Double): Bin1D? = binMap.getBin(value) + override val bins: Collection> get() = binMap.values } @OptIn(UnstableKMathAPI::class) @PublishedApi -internal class TreeHistogramBuilder(val binFactory: (Double) -> UnivariateDomain) : UnivariateHistogramBuilder { +internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) : Histogram1DBuilder { - internal class BinCounter(val domain: UnivariateDomain, val counter: Counter = Counter.double()) : - ClosedFloatingPointRange by domain.range + internal class BinCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.double()) : + ClosedRange by domain.range private val bins: TreeMap = TreeMap() @@ -64,15 +63,15 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> UnivariateDomain } } - override fun putValue(point: Buffer, value: Number) { + override fun putValue(point: Buffer, value: Double) { require(point.size == 1) { "Only points with single value could be used in univariate histogram" } putValue(point[0], value.toDouble()) } fun build(): TreeHistogram { - val map = bins.mapValuesTo(TreeMap()) { (_, binCounter) -> + val map = bins.mapValuesTo(TreeMap>()) { (_, binCounter) -> val count = binCounter.counter.value - UnivariateBin(binCounter.domain, count, sqrt(count)) + Bin1D(binCounter.domain, count, sqrt(count)) } return TreeHistogram(map) } @@ -83,23 +82,23 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> UnivariateDomain */ @UnstableKMathAPI public class TreeHistogramSpace( - @PublishedApi internal val binFactory: (Double) -> UnivariateDomain, -) : Group, ScaleOperations { + @PublishedApi internal val binFactory: (Double) -> DoubleDomain1D, +) : Group>, ScaleOperations> { - public inline fun fill(block: UnivariateHistogramBuilder.() -> Unit): UnivariateHistogram = + public inline fun fill(block: Histogram1DBuilder.() -> Unit): Histogram1D = TreeHistogramBuilder(binFactory).apply(block).build() override fun add( - left: UnivariateHistogram, - right: UnivariateHistogram, - ): UnivariateHistogram { + left: Histogram1D, + right: Histogram1D, + ): Histogram1D { // require(a.context == this) { "Histogram $a does not belong to this context" } // require(b.context == this) { "Histogram $b does not belong to this context" } - val bins = TreeMap().apply { + val bins = TreeMap>().apply { (left.bins.map { it.domain } union right.bins.map { it.domain }).forEach { def -> put( def.center, - UnivariateBin( + Bin1D( def, value = (left[def.center]?.value ?: 0.0) + (right[def.center]?.value ?: 0.0), standardDeviation = (left[def.center]?.standardDeviation @@ -111,12 +110,12 @@ public class TreeHistogramSpace( return TreeHistogram(bins) } - override fun scale(a: UnivariateHistogram, value: Double): UnivariateHistogram { - val bins = TreeMap().apply { + override fun scale(a: Histogram1D, value: Double): Histogram1D { + val bins = TreeMap>().apply { a.bins.forEach { bin -> put( bin.domain.center, - UnivariateBin( + Bin1D( bin.domain, value = bin.value * value, standardDeviation = abs(bin.standardDeviation * value) @@ -128,38 +127,38 @@ public class TreeHistogramSpace( return TreeHistogram(bins) } - override fun UnivariateHistogram.unaryMinus(): UnivariateHistogram = this * (-1) + override fun Histogram1D.unaryMinus(): Histogram1D = this * (-1) - override val zero: UnivariateHistogram by lazy { fill { } } + override val zero: Histogram1D by lazy { fill { } } public companion object { /** - * Build and fill a [UnivariateHistogram]. Returns a read-only histogram. + * Build and fill a [DoubleHistogram1D]. Returns a read-only histogram. */ public inline fun uniform( binSize: Double, start: Double = 0.0, - builder: UnivariateHistogramBuilder.() -> Unit, - ): UnivariateHistogram = uniform(binSize, start).fill(builder) + builder: Histogram1DBuilder.() -> Unit, + ): Histogram1D = uniform(binSize, start).fill(builder) /** * Build and fill a histogram with custom borders. Returns a read-only histogram. */ public inline fun custom( borders: DoubleArray, - builder: UnivariateHistogramBuilder.() -> Unit, - ): UnivariateHistogram = custom(borders).fill(builder) + builder: Histogram1DBuilder.() -> Unit, + ): Histogram1D = custom(borders).fill(builder) /** - * Build and fill a [UnivariateHistogram]. Returns a read-only histogram. + * Build and fill a [DoubleHistogram1D]. Returns a read-only histogram. */ public fun uniform( binSize: Double, start: Double = 0.0, ): TreeHistogramSpace = TreeHistogramSpace { value -> val center = start + binSize * floor((value - start) / binSize + 0.5) - UnivariateDomain((center - binSize / 2)..(center + binSize / 2)) + DoubleDomain1D((center - binSize / 2)..(center + binSize / 2)) } /** @@ -170,11 +169,11 @@ public class TreeHistogramSpace( return TreeHistogramSpace { value -> when { - value < sorted.first() -> UnivariateDomain( + value < sorted.first() -> DoubleDomain1D( Double.NEGATIVE_INFINITY..sorted.first() ) - value > sorted.last() -> UnivariateDomain( + value > sorted.last() -> DoubleDomain1D( sorted.last()..Double.POSITIVE_INFINITY ) @@ -182,7 +181,7 @@ public class TreeHistogramSpace( val index = sorted.indices.first { value > sorted[it] } val left = sorted[index] val right = sorted[index + 1] - UnivariateDomain(left..right) + DoubleDomain1D(left..right) } } } -- 2.34.1 From 3a3a5bd77f02b8a1fc43c399c53a5086a7891d5c Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Wed, 23 Mar 2022 14:07:24 +0300 Subject: [PATCH 15/59] Histogram API refactor --- gradle/wrapper/gradle-wrapper.properties | 2 +- .../space/kscience/kmath/domains/Domain1D.kt | 2 +- .../kscience/kmath/histogram/Histogram.kt | 2 +- .../kscience/kmath/histogram/Histogram1D.kt | 4 +- .../kmath/histogram/IndexedHistogramSpace.kt | 2 +- .../histogram/MultivariateHistogramTest.kt | 6 +- .../kmath/histogram/TreeHistogramSpace.kt | 70 +++++++++++-------- 7 files changed, 49 insertions(+), 39 deletions(-) diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 2e6e5897b..00e33edef 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,5 +1,5 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-7.4.1-bin.zip zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt index f50f16c11..ccd1c3edb 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt @@ -38,5 +38,5 @@ public class DoubleDomain1D( } @UnstableKMathAPI -public val DoubleDomain1D.center: Double +public val Domain1D.center: Double get() = (range.endInclusive + range.start) / 2 diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt index 64c031c7a..f9550df17 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt @@ -17,7 +17,7 @@ public interface Bin : Domain { /** * The value of this bin. */ - public val value: V + public val binValue: V } public interface Histogram> { diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt index e9c62b141..4f193f943 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt @@ -14,13 +14,13 @@ import space.kscience.kmath.structures.Buffer /** * A univariate bin based on a range * - * @property value The value of histogram including weighting + * @property binValue The value of histogram including weighting * @property standardDeviation Standard deviation of the bin value. Zero or negative if not applicable */ @UnstableKMathAPI public class Bin1D, out V>( public val domain: Domain1D, - override val value: V, + override val binValue: V, ) : Bin, ClosedRange by domain.range { override val dimension: Int get() = 1 diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt index a2623b1a1..3e4b07984 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt @@ -20,7 +20,7 @@ import space.kscience.kmath.operations.invoke */ public data class DomainBin, out V>( public val domain: Domain, - override val value: V, + override val binValue: V, ) : Bin, Domain by domain /** diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt index 923cc98de..31a29676c 100644 --- a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt @@ -21,7 +21,7 @@ internal class MultivariateHistogramTest { val histogram = hSpace.produce { put(0.55, 0.55) } - val bin = histogram.bins.find { it.value.toInt() > 0 } ?: fail() + val bin = histogram.bins.find { it.binValue.toInt() > 0 } ?: fail() assertTrue { bin.contains(DoubleVector(0.55, 0.55)) } assertTrue { bin.contains(DoubleVector(0.6, 0.5)) } assertFalse { bin.contains(DoubleVector(-0.55, 0.55)) } @@ -44,7 +44,7 @@ internal class MultivariateHistogramTest { put(nextDouble(), nextDouble(), nextDouble()) } } - assertEquals(n, histogram.bins.sumOf { it.value.toInt() }) + assertEquals(n, histogram.bins.sumOf { it.binValue.toInt() }) } @Test @@ -77,7 +77,7 @@ internal class MultivariateHistogramTest { assertTrue { res.bins.count() >= histogram1.bins.count() } - assertEquals(0.0, res.bins.sumOf { it.value.toDouble() }) + assertEquals(0.0, res.bins.sumOf { it.binValue.toDouble() }) } } } \ No newline at end of file diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt index 9d07d5014..38e533db0 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt @@ -6,6 +6,7 @@ package space.kscience.kmath.histogram import space.kscience.kmath.domains.DoubleDomain1D +import space.kscience.kmath.domains.center import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Group import space.kscience.kmath.operations.ScaleOperations @@ -26,18 +27,24 @@ private fun > TreeMap.getBin(value: Double): return null } +public data class ValueAndError(val value: Double, val error: Double) + +public typealias WeightedBin1D = Bin1D + @UnstableKMathAPI public class TreeHistogram( - private val binMap: TreeMap>, -) : Histogram1D { - override fun get(value: Double): Bin1D? = binMap.getBin(value) - override val bins: Collection> get() = binMap.values + private val binMap: TreeMap, +) : Histogram1D { + override fun get(value: Double): WeightedBin1D? = binMap.getBin(value) + override val bins: Collection get() = binMap.values } @OptIn(UnstableKMathAPI::class) @PublishedApi internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) : Histogram1DBuilder { + override val defaultValue: Double get() = 1.0 + internal class BinCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.double()) : ClosedRange by domain.range @@ -46,7 +53,7 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) fun get(value: Double): BinCounter? = bins.getBin(value) fun createBin(value: Double): BinCounter { - val binDefinition = binFactory(value) + val binDefinition: DoubleDomain1D = binFactory(value) val newBin = BinCounter(binDefinition) synchronized(this) { bins[binDefinition.center] = newBin @@ -69,9 +76,9 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) } fun build(): TreeHistogram { - val map = bins.mapValuesTo(TreeMap>()) { (_, binCounter) -> - val count = binCounter.counter.value - Bin1D(binCounter.domain, count, sqrt(count)) + val map = bins.mapValuesTo(TreeMap()) { (_, binCounter) -> + val count: Double = binCounter.counter.value + WeightedBin1D(binCounter.domain, ValueAndError(count, sqrt(count))) } return TreeHistogram(map) } @@ -83,26 +90,27 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) @UnstableKMathAPI public class TreeHistogramSpace( @PublishedApi internal val binFactory: (Double) -> DoubleDomain1D, -) : Group>, ScaleOperations> { +) : Group, ScaleOperations { - public inline fun fill(block: Histogram1DBuilder.() -> Unit): Histogram1D = + public inline fun fill(block: Histogram1DBuilder.() -> Unit): TreeHistogram = TreeHistogramBuilder(binFactory).apply(block).build() override fun add( - left: Histogram1D, - right: Histogram1D, - ): Histogram1D { + left: TreeHistogram, + right: TreeHistogram, + ): TreeHistogram { // require(a.context == this) { "Histogram $a does not belong to this context" } // require(b.context == this) { "Histogram $b does not belong to this context" } - val bins = TreeMap>().apply { + val bins = TreeMap().apply { (left.bins.map { it.domain } union right.bins.map { it.domain }).forEach { def -> put( def.center, - Bin1D( + WeightedBin1D( def, - value = (left[def.center]?.value ?: 0.0) + (right[def.center]?.value ?: 0.0), - standardDeviation = (left[def.center]?.standardDeviation - ?: 0.0) + (right[def.center]?.standardDeviation ?: 0.0) + ValueAndError( + (left[def.center]?.binValue?.value ?: 0.0) + (right[def.center]?.binValue?.value ?: 0.0), + (left[def.center]?.binValue?.error ?: 0.0) + (right[def.center]?.binValue?.error ?: 0.0) + ) ) ) } @@ -110,15 +118,17 @@ public class TreeHistogramSpace( return TreeHistogram(bins) } - override fun scale(a: Histogram1D, value: Double): Histogram1D { - val bins = TreeMap>().apply { + override fun scale(a: TreeHistogram, value: Double): TreeHistogram { + val bins = TreeMap().apply { a.bins.forEach { bin -> put( bin.domain.center, - Bin1D( + WeightedBin1D( bin.domain, - value = bin.value * value, - standardDeviation = abs(bin.standardDeviation * value) + ValueAndError( + bin.binValue.value * value, + abs(bin.binValue.error * value) + ) ) ) } @@ -127,27 +137,27 @@ public class TreeHistogramSpace( return TreeHistogram(bins) } - override fun Histogram1D.unaryMinus(): Histogram1D = this * (-1) + override fun TreeHistogram.unaryMinus(): TreeHistogram = this * (-1) - override val zero: Histogram1D by lazy { fill { } } + override val zero: TreeHistogram by lazy { fill { } } public companion object { /** - * Build and fill a [DoubleHistogram1D]. Returns a read-only histogram. + * Build and fill a [TreeHistogram]. Returns a read-only histogram. */ public inline fun uniform( binSize: Double, start: Double = 0.0, - builder: Histogram1DBuilder.() -> Unit, - ): Histogram1D = uniform(binSize, start).fill(builder) + builder: Histogram1DBuilder.() -> Unit, + ): TreeHistogram = uniform(binSize, start).fill(builder) /** * Build and fill a histogram with custom borders. Returns a read-only histogram. */ public inline fun custom( borders: DoubleArray, - builder: Histogram1DBuilder.() -> Unit, - ): Histogram1D = custom(borders).fill(builder) + builder: Histogram1DBuilder.() -> Unit, + ): TreeHistogram = custom(borders).fill(builder) /** -- 2.34.1 From ce82d2d07633240f8df932fb9b8ac185e0e8c9d6 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Wed, 23 Mar 2022 15:51:08 +0300 Subject: [PATCH 16/59] Histogram API refactor --- .../{UniformDoubleHistogram1D.kt => UniformHistogram1D.kt} | 5 ++++- .../space/kscience/kmath/histogram/TreeHistogramSpace.kt | 5 ++--- 2 files changed, 6 insertions(+), 4 deletions(-) rename kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/{UniformDoubleHistogram1D.kt => UniformHistogram1D.kt} (58%) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt similarity index 58% rename from kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt rename to kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index 856cd8592..ed8b2e29d 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformDoubleHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -5,5 +5,8 @@ package space.kscience.kmath.histogram -//class UniformDoubleHistogram1D: DoubleHistogram1D { +//class UniformHistogram1D( +// public val borders: Buffer, +// public val values: Buffer, +//) : Histogram1D { //} \ No newline at end of file diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt index 38e533db0..e85bb0a3c 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt @@ -3,6 +3,8 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:OptIn(UnstableKMathAPI::class) + package space.kscience.kmath.histogram import space.kscience.kmath.domains.DoubleDomain1D @@ -31,7 +33,6 @@ public data class ValueAndError(val value: Double, val error: Double) public typealias WeightedBin1D = Bin1D -@UnstableKMathAPI public class TreeHistogram( private val binMap: TreeMap, ) : Histogram1D { @@ -39,7 +40,6 @@ public class TreeHistogram( override val bins: Collection get() = binMap.values } -@OptIn(UnstableKMathAPI::class) @PublishedApi internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) : Histogram1DBuilder { @@ -87,7 +87,6 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) /** * A space for univariate histograms with variable bin borders based on a tree map */ -@UnstableKMathAPI public class TreeHistogramSpace( @PublishedApi internal val binFactory: (Double) -> DoubleDomain1D, ) : Group, ScaleOperations { -- 2.34.1 From 92cffd78d935e8d834ec14887680ccffdaf89586 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 02:23:34 +0700 Subject: [PATCH 17/59] Upgrade gradle tools --- .github/workflows/build.yml | 11 ++-- .github/workflows/pages.yml | 7 +- .github/workflows/publish.yml | 17 ++--- README.md | 80 ++++++++--------------- benchmarks/README.md | 4 ++ buildSrc/gradle.properties | 3 +- buildSrc/settings.gradle.kts | 3 +- docs/templates/README-TEMPLATE.md | 2 +- examples/README.md | 4 ++ gradle.properties | 7 +- gradle/wrapper/gradle-wrapper.jar | Bin 59536 -> 59821 bytes gradle/wrapper/gradle-wrapper.properties | 2 +- kmath-ast/README.md | 55 +++++++++++----- kmath-commons/README.md | 32 +++++++++ kmath-complex/README.md | 10 +-- kmath-core/README.md | 10 +-- kmath-coroutines/README.md | 32 +++++++++ kmath-dimensions/README.md | 32 +++++++++ kmath-ejml/README.md | 10 +-- kmath-for-real/README.md | 10 +-- kmath-functions/README.md | 10 +-- kmath-geometry/README.md | 32 +++++++++ kmath-histograms/README.md | 32 +++++++++ kmath-jafama/README.md | 10 +-- kmath-jupyter/README.md | 32 +++++++++ kmath-kotlingrad/README.md | 10 +-- kmath-memory/README.md | 32 +++++++++ kmath-multik/README.md | 32 +++++++++ kmath-nd4j/README.md | 10 +-- kmath-optimization/README.md | 32 +++++++++ kmath-stat/README.md | 32 +++++++++ kmath-symja/README.md | 32 +++++++++ kmath-tensorflow/README.md | 32 +++++++++ kmath-tensors/README.md | 10 +-- kmath-viktor/README.md | 32 +++++++++ settings.gradle.kts | 2 - 36 files changed, 556 insertions(+), 147 deletions(-) create mode 100644 benchmarks/README.md create mode 100644 examples/README.md create mode 100644 kmath-commons/README.md create mode 100644 kmath-coroutines/README.md create mode 100644 kmath-dimensions/README.md create mode 100644 kmath-geometry/README.md create mode 100644 kmath-histograms/README.md create mode 100644 kmath-jupyter/README.md create mode 100644 kmath-memory/README.md create mode 100644 kmath-multik/README.md create mode 100644 kmath-optimization/README.md create mode 100644 kmath-stat/README.md create mode 100644 kmath-symja/README.md create mode 100644 kmath-tensorflow/README.md create mode 100644 kmath-viktor/README.md diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index f2c76a354..455e0dd2d 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -13,14 +13,11 @@ jobs: runs-on: ${{matrix.os}} timeout-minutes: 40 steps: - - name: Checkout the repo - uses: actions/checkout@v2 - - name: Set up JDK 11 - uses: DeLaGuardo/setup-graalvm@4.0 + - uses: actions/checkout@v2 + - uses: actions/setup-java@v2.5.0 with: - graalvm: 21.2.0 - java: java11 - arch: amd64 + java-version: 11 + distribution: liberica - name: Cache gradle uses: actions/cache@v2 with: diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 23ed54357..e7f5300c7 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -10,11 +10,10 @@ jobs: timeout-minutes: 40 steps: - uses: actions/checkout@v2 - - uses: DeLaGuardo/setup-graalvm@4.0 + - uses: actions/setup-java@v2.5.0 with: - graalvm: 21.2.0 - java: java11 - arch: amd64 + java-version: 11 + distribution: liberica - uses: actions/cache@v2 with: path: ~/.gradle/caches diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index fa3cb700c..17adc5655 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -14,14 +14,11 @@ jobs: os: [ macOS-latest, windows-latest ] runs-on: ${{matrix.os}} steps: - - name: Checkout the repo - uses: actions/checkout@v2 - - name: Set up JDK 11 - uses: DeLaGuardo/setup-graalvm@4.0 + - uses: actions/checkout@v2 + - uses: actions/setup-java@v2.5.0 with: - graalvm: 21.2.0 - java: java11 - arch: amd64 + java-version: 11 + distribution: liberica - name: Cache gradle uses: actions/cache@v2 with: @@ -44,12 +41,12 @@ jobs: if: matrix.os == 'windows-latest' shell: cmd run: > - ./gradlew release --no-daemon --build-cache -Ppublishing.enabled=true + ./gradlew releaseAll --no-daemon --build-cache -Ppublishing.enabled=true -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} - name: Publish Mac Artifacts if: matrix.os == 'macOS-latest' run: > - ./gradlew release --no-daemon --build-cache -Ppublishing.enabled=true -Ppublishing.platform=macosX64 - -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} + ./gradlew releaseMacosX64 releaseIosArm64 releaseIosX64 release --no-daemon --build-cache + -Ppublishing.enabled=true -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} diff --git a/README.md b/README.md index 99dd6d00f..aea94f529 100644 --- a/README.md +++ b/README.md @@ -52,21 +52,18 @@ module definitions below. The module stability could have the following levels: ## Modules -
-* ### [benchmarks](benchmarks) +### [benchmarks](benchmarks) > > > **Maturity**: EXPERIMENTAL -
-* ### [examples](examples) +### [examples](examples) > > > **Maturity**: EXPERIMENTAL -
-* ### [kmath-ast](kmath-ast) +### [kmath-ast](kmath-ast) > > > **Maturity**: EXPERIMENTAL @@ -77,15 +74,13 @@ module definitions below. The module stability could have the following levels: > - [mst-js-codegen](kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt) : Dynamic MST to JS compiler > - [rendering](kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathRenderer.kt) : Extendable MST rendering -
-* ### [kmath-commons](kmath-commons) +### [kmath-commons](kmath-commons) > > > **Maturity**: EXPERIMENTAL -
-* ### [kmath-complex](kmath-complex) +### [kmath-complex](kmath-complex) > Complex numbers and quaternions. > > **Maturity**: PROTOTYPE @@ -94,9 +89,8 @@ module definitions below. The module stability could have the following levels: > - [complex](kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt) : Complex Numbers > - [quaternion](kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt) : Quaternions -
-* ### [kmath-core](kmath-core) +### [kmath-core](kmath-core) > Core classes, algebra definitions, basic linear algebra > > **Maturity**: DEVELOPMENT @@ -112,21 +106,18 @@ performance calculations to code generation. > - [domains](kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains) : Domains > - [autodiff](kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SimpleAutoDiff.kt) : Automatic differentiation -
-* ### [kmath-coroutines](kmath-coroutines) +### [kmath-coroutines](kmath-coroutines) > > > **Maturity**: EXPERIMENTAL -
-* ### [kmath-dimensions](kmath-dimensions) +### [kmath-dimensions](kmath-dimensions) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-ejml](kmath-ejml) +### [kmath-ejml](kmath-ejml) > > > **Maturity**: PROTOTYPE @@ -136,9 +127,8 @@ performance calculations to code generation. > - [ejml-matrix](kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlMatrix.kt) : Matrix implementation. > - [ejml-linear-space](kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlLinearSpace.kt) : LinearSpace implementations. -
-* ### [kmath-for-real](kmath-for-real) +### [kmath-for-real](kmath-for-real) > Extension module that should be used to achieve numpy-like behavior. All operations are specialized to work with `Double` numbers without declaring algebraic contexts. One can still use generic algebras though. @@ -150,9 +140,8 @@ One can still use generic algebras though. > - [DoubleMatrix](kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleMatrix.kt) : Numpy-like operations for 2d real structures > - [grids](kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/structures/grids.kt) : Uniform grid generators -
-* ### [kmath-functions](kmath-functions) +### [kmath-functions](kmath-functions) > > > **Maturity**: EXPERIMENTAL @@ -164,21 +153,18 @@ One can still use generic algebras though. > - [spline interpolation](kmath-functions/src/commonMain/kotlin/space/kscience/kmath/interpolation/SplineInterpolator.kt) : Cubic spline XY interpolator. > - [integration](kmath-functions/#) : Univariate and multivariate quadratures -
-* ### [kmath-geometry](kmath-geometry) +### [kmath-geometry](kmath-geometry) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-histograms](kmath-histograms) +### [kmath-histograms](kmath-histograms) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-jafama](kmath-jafama) +### [kmath-jafama](kmath-jafama) > > > **Maturity**: PROTOTYPE @@ -186,15 +172,13 @@ One can still use generic algebras though. > **Features:** > - [jafama-double](kmath-jafama/src/main/kotlin/space/kscience/kmath/jafama/) : Double ExtendedField implementations based on Jafama -
-* ### [kmath-jupyter](kmath-jupyter) +### [kmath-jupyter](kmath-jupyter) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-kotlingrad](kmath-kotlingrad) +### [kmath-kotlingrad](kmath-kotlingrad) > > > **Maturity**: EXPERIMENTAL @@ -203,21 +187,18 @@ One can still use generic algebras though. > - [differentiable-mst-expression](kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KotlingradExpression.kt) : MST based DifferentiableExpression. > - [scalars-adapters](kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/scalarsAdapters.kt) : Conversions between Kotlin∇'s SFun and MST -
-* ### [kmath-memory](kmath-memory) +### [kmath-memory](kmath-memory) > An API and basic implementation for arranging objects in a continuous memory block. > > **Maturity**: DEVELOPMENT -
-* ### [kmath-multik](kmath-multik) +### [kmath-multik](kmath-multik) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-nd4j](kmath-nd4j) +### [kmath-nd4j](kmath-nd4j) > > > **Maturity**: EXPERIMENTAL @@ -227,33 +208,28 @@ One can still use generic algebras though. > - [nd4jarrayrings](kmath-nd4j/#) : Rings over Nd4jArrayStructure of Int and Long > - [nd4jarrayfields](kmath-nd4j/#) : Fields over Nd4jArrayStructure of Float and Double -
-* ### [kmath-optimization](kmath-optimization) +### [kmath-optimization](kmath-optimization) > > > **Maturity**: EXPERIMENTAL -
-* ### [kmath-stat](kmath-stat) +### [kmath-stat](kmath-stat) > > > **Maturity**: EXPERIMENTAL -
-* ### [kmath-symja](kmath-symja) +### [kmath-symja](kmath-symja) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-tensorflow](kmath-tensorflow) +### [kmath-tensorflow](kmath-tensorflow) > > > **Maturity**: PROTOTYPE -
-* ### [kmath-tensors](kmath-tensors) +### [kmath-tensors](kmath-tensors) > > > **Maturity**: PROTOTYPE @@ -263,13 +239,11 @@ One can still use generic algebras though. > - [tensor algebra with broadcasting](kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BroadcastDoubleTensorAlgebra.kt) : Basic linear algebra operations implemented with broadcasting. > - [linear algebra operations](kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/LinearOpsTensorAlgebra.kt) : Advanced linear algebra operations like LU decomposition, SVD, etc. -
-* ### [kmath-viktor](kmath-viktor) +### [kmath-viktor](kmath-viktor) > > > **Maturity**: DEVELOPMENT -
## Multi-platform support @@ -308,8 +282,8 @@ repositories { } dependencies { - api("space.kscience:kmath-core:0.3.0-dev-17") - // api("space.kscience:kmath-core-jvm:0.3.0-dev-17") for jvm-specific version + api("space.kscience:kmath-core:$version") + // api("space.kscience:kmath-core-jvm:$version") for jvm-specific version } ``` diff --git a/benchmarks/README.md b/benchmarks/README.md new file mode 100644 index 000000000..cd8fbafd3 --- /dev/null +++ b/benchmarks/README.md @@ -0,0 +1,4 @@ +# Module benchmarks + + + diff --git a/buildSrc/gradle.properties b/buildSrc/gradle.properties index 05486d4f6..a0b05e812 100644 --- a/buildSrc/gradle.properties +++ b/buildSrc/gradle.properties @@ -4,5 +4,4 @@ # kotlin.code.style=official - -toolsVersion=0.11.1-kotlin-1.6.10 +toolsVersion=0.11.2-kotlin-1.6.10 diff --git a/buildSrc/settings.gradle.kts b/buildSrc/settings.gradle.kts index 9c5550602..bc530ac03 100644 --- a/buildSrc/settings.gradle.kts +++ b/buildSrc/settings.gradle.kts @@ -7,7 +7,6 @@ enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") enableFeaturePreview("VERSION_CATALOGS") dependencyResolutionManagement { - val toolsVersion: String by extra repositories { @@ -22,4 +21,4 @@ dependencyResolutionManagement { from("ru.mipt.npm:version-catalog:$toolsVersion") } } -} \ No newline at end of file +} diff --git a/docs/templates/README-TEMPLATE.md b/docs/templates/README-TEMPLATE.md index b0c418697..4ffa9e75f 100644 --- a/docs/templates/README-TEMPLATE.md +++ b/docs/templates/README-TEMPLATE.md @@ -52,7 +52,7 @@ module definitions below. The module stability could have the following levels: ## Modules -$modules +${modules} ## Multi-platform support diff --git a/examples/README.md b/examples/README.md new file mode 100644 index 000000000..d4e1c5289 --- /dev/null +++ b/examples/README.md @@ -0,0 +1,4 @@ +# Module examples + + + diff --git a/gradle.properties b/gradle.properties index 7d9628621..a7cd2f876 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,13 +2,10 @@ # Copyright 2018-2021 KMath contributors. # Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. # - kotlin.code.style=official +kotlin.jupyter.add.scanner=false kotlin.mpp.stability.nowarn=true kotlin.native.ignoreDisabledTargets=true - -kotlin.jupyter.add.scanner=false - org.gradle.configureondemand=true -org.gradle.parallel=true org.gradle.jvmargs=-XX:MaxMetaspaceSize=1G +org.gradle.parallel=true diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar index 7454180f2ae8848c63b8b4dea2cb829da983f2fa..41d9927a4d4fb3f96a785543079b8df6723c946b 100644 GIT binary patch delta 8958 zcmY+KWl$VIlZIh&f(Hri?gR<$?iyT!TL`X;1^2~W7YVSq1qtqM!JWlDxLm%}UESUM zndj}Uny%^UnjhVhFb!8V3s(a#fIy>`VW15{5nuy;_V&a5O#0S&!a4dSkUMz_VHu3S zGA@p9Q$T|Sj}tYGWdjH;Mpp8m&yu&YURcrt{K;R|kM~(*{v%QwrBJIUF+K1kX5ZmF zty3i{d`y0;DgE+de>vN@yYqFPe1Ud{!&G*Q?iUc^V=|H%4~2|N zW+DM)W!`b&V2mQ0Y4u_)uB=P@-2`v|Wm{>CxER1P^ z>c}ZPZ)xxdOCDu59{X^~2id7+6l6x)U}C4Em?H~F`uOxS1?}xMxTV|5@}PlN%Cg$( zwY6c}r60=z5ZA1L zTMe;84rLtYvcm?M(H~ZqU;6F7Evo{P7!LGcdwO|qf1w+)MsnvK5^c@Uzj<{ zUoej1>95tuSvDJ|5K6k%&UF*uE6kBn47QJw^yE&#G;u^Z9oYWrK(+oL97hBsUMc_^ z;-lmxebwlB`Er_kXp2$`&o+rPJAN<`WX3ws2K{q@qUp}XTfV{t%KrsZ5vM!Q#4{V& zq>iO$MCiLq#%wXj%`W$_%FRg_WR*quv65TdHhdpV&jlq<=K^K`&!Kl5mA6p4n~p3u zWE{20^hYpn1M}}VmSHBXl1*-)2MP=0_k)EPr#>EoZukiXFDz?Di1I>2@Z^P$pvaF+ zN+qUy63jek2m59;YG)`r^F3-O)0RDIXPhf)XOOdkmu`3SMMSW(g+`Ajt{=h1dt~ks ztrhhP|L4G%5x79N#kwAHh5N){@{fzE7n&%dnisCm65Za<8r_hKvfx4Bg*`%-*-Mvn zFvn~)VP@}1sAyD+B{{8l{EjD10Av&Mz9^Xff*t`lU=q=S#(|>ls520;n3<}X#pyh& z*{CJf7$*&~!9jMnw_D~ikUKJ2+UnXmN6qak{xx%W;BKuXt7@ky!LPI1qk?gDwG@@o zkY+BkIie>{{q==5)kXw(*t#I?__Kwi>`=+s?Gq6X+vtSsaAO&Tf+Bl$vKnzc&%BHM z=loWOQq~n}>l=EL(5&6((ESsQC3^@4jlO5Od{qN#sWV)vqXw}aA>*uvwZopNN(|-T zRTF%5Y_k1R$;(d-)n;hWex{;7b6KgdAVE@&0pd(*qDzBO#YZV%kh%pYt1`hnQ(Fa& zYiDrOTDqk5M7hzp9kI2h!PxNnuJ&xl*zF8sx6!67bA49R1bmUF5bpK&&{eI0U~cH}PM z3aW1$lRb|ItkG5~_eBNu$|I|vYIdAA9a!pVq<+UTx*M}fG`23zxXp&E=FfnY- zEzKj;Cu_s4v>leO7M2-mE(UzKHL4c$c`3dS*19OpLV^4NI*hWWnJQ9lvzP4c;c?do zqrcsKT*i~eIHl0D3r4N{)+RsB6XhrC^;sp2cf_Eq#6*CV;t8v=V!ISe>>9kPgh}NI z=1UZutslxcT$Ad;_P^;Oouoa(cs!Ctpvi>%aQ+Zp=1d|h{W9Wmf7JWxa(~<#tSZ?C%wu4_5F!fc!<@PIBeJ)Nr^$bB6!_Gic_7}c3J{QI~Gg5g5jTp9}V6KYgrgaX>pJt}7$!wOht&KO|+z{Iw@YL|@~D zMww}+lG}rm2^peNx>58ME||ZQxFQeVSX8iogHLq_vXb`>RnoEKaTWBF-$JD#Q4BMv zt2(2Qb*x-?ur1Y(NsW8AdtX0#rDB?O(Vs4_xA(u-o!-tBG03OI!pQD+2UytbL5>lG z*(F)KacHqMa4?dxa(Vcrw>IIAeB$3cx#;;5r2X;HE8|}eYdAgCw#tpXNy7C3w1q`9 zGxZ6;@1G%8shz9e+!K2MO*{_RjO}Jo6eL3{TSZ>nY7)Qs`Dhi5><@oh0r)gT7H-?3 zLDsd^@m%JvrS8sta5`QiZNs^*GT}Hiy^zjK2^Ni%`Z|ma)D2 zuyumbvw$M8$haCTI~6M%d4+P)uX%u{Sfg4Al+F7c6;O-*)DKI7E8izSOKB#FcV{M+ zEvY0FBkq!$J0EW$Cxl}3{JwV^ki-T?q6C30Y5e&p@8Rd?$ST-Ghn*-`tB{k54W<>F z5I)TFpUC!E9298=sk>m#FI4sUDy_!8?51FqqW!9LN1(zuDnB3$!pEUjL>N>RNgAG~-9Xm|1lqHseW(%v&6K(DZ3Pano(1-Qe?3%J&>0`~w^Q-p&@ zg@HjvhJk?*hpF7$9P|gkzz`zBz_5Z!C4_-%fCcAgiSilzFQef!@amHDrW!YZS@?7C zs2Y9~>yqO+rkih?kXztzvnB^6W=f52*iyuZPv$c42$WK7>PHb z6%MYIr5D32KPdwL1hJf{_#jn?`k(taW?mwmZVvrr=y~fNcV$`}v(8};o9AjOJumS4 z`889O91^pkF+|@$d9wVoZ3;^j;^sUs&Ubo_qD&MTL%O z&*SE0ujG~zm;?x)8TLC&ft))nyI zcg44@*Q{cYT+qGrA=In_X{NNCD+B0w#;@g)jvBU;_8od6U>;7HIo@F*=g8CQUo(u^ z3r4FJ7#<@)MXO&5+DgKE&^>^`r!loe7CWE*1k0*0wLFzSOV8jvlX~WOQ?$1v zk$Or}!;ix0g78^6W;+<=J>z@CBs!<<)HvF(Ls-&`matpesJ5kkjC)6nGB@b{ii6-Uoho$BT%iJgugTOeZ$5Xo4D7Pd< zC*LJh5V@2#5%aBZCgzlQi3@<_!VfiL07ywc)ZbwKPfcR|ElQoS(8x|a7#IR}7#Io= zwg4$8S{egr-NffD)Fg&X9bJSoM25pF&%hf>(T&9bI}=#dPQyNYz;ZZ7EZ=u1n701SWKkZ9n(-qU ztN`sdWL1uxQ1mKS@x11;O|@^AD9!NeoPx}?EKIr!2>1Qq4gjfGU)tr6?Z5l7JAS3j zZeq{vG{rb%DFE4%$szK}d2UzB{4>L?Tv+NAlE*&Nq6g+XauaSI+N2Y8PJLw+aNg1p zbxr|hI8wcMP&&+(Cu|%+Jq|r>+BHk@{AvfBXKiVldN)@}TBS0LdIpnANCVE26WL-} zV}HJ^?m&$Rkq;Zf*i-hoasnpJVyTH__dbGWrB_R55d*>pTyl6(?$EO@>RCmTX1Hzr zT2)rOng?D4FfZ_C49hjMV*UonG2DlG$^+k=Y%|?Dqae4}JOU=8=fgY4Uh!pa9eEqf zFX&WLPu!jArN*^(>|H>dj~g`ONZhaaD%h_HHrHkk%d~TR_RrX{&eM#P@3x=S^%_6h zh=A)A{id16$zEFq@-D7La;kTuE!oopx^9{uA3y<}9 z^bQ@U<&pJV6kq7LRF47&!UAvgkBx=)KS_X!NY28^gQr27P=gKh0+E>$aCx&^vj2uc}ycsfSEP zedhTgUwPx%?;+dESs!g1z}5q9EC+fol}tAH9#fhZQ?q1GjyIaR@}lGCSpM-014T~l zEwriqt~ftwz=@2tn$xP&-rJt?nn5sy8sJ5Roy;pavj@O+tm}d_qmAlvhG(&k>(arz z;e|SiTr+0<&6(-An0*4{7akwUk~Yf4M!!YKj^swp9WOa%al`%R>V7mi z+5+UodFAaPdi4(8_FO&O!Ymb#@yxkuVMrog(7gkj$G@FLA#ENMxG)4f<}S%Fn?Up$+C%{02AgMKa^ z4SFGWp6U>{Q6VRJV}yjxXT*e`1XaX}(dW1F&RNhpTzvCtzuu;LMhMfJ2LBEy?{^GHG!OF!! zDvs64TG)?MX&9NCE#H3(M0K>O>`ca0WT2YR>PTe&tn?~0FV!MRtdb@v?MAUG&Ef7v zW%7>H(;Mm)RJkt18GXv!&np z?RUxOrCfs;m{fBz5MVlq59idhov21di5>WXWD-594L-X5;|@kyWi@N+(jLuh=o+5l zGGTi~)nflP_G}Yg5Pi%pl88U4+^*ihDoMP&zA*^xJE_X*Ah!jODrijCqQ^{=&hD7& z^)qv3;cu?olaT3pc{)Kcy9jA2E8I)#Kn8qO>70SQ5P8YSCN=_+_&)qg)OYBg|-k^d3*@jRAeB?;yd-O1A0wJ z?K*RDm|wE<(PBz~+C%2CTtzCTUohxP2*1kE8Of~{KRAvMrO_}NN&@P7SUO{;zx0iK z@or9R8ydYOFZf(cHASCAatL%;62IL27~SmASr(7F&NMr+#gNw@z1VM z_ALFwo3)SoANEwRerBdRV`>y`t72#aF2ConmWQp(Xy|msN9$yxhZ1jAQ67lq{vbC5 zujj|MlGo`6Bfn0TfKgi(k=gq0`K~W+X(@GzYlPI4g0M;owH3yG14rhK>lG8lS{`!K z+Nc@glT-DGz?Ym?v#Hq|_mEdPAlHH5jZuh*6glq!+>Lk$S%ED2@+ea6CE@&1-9a?s znglt|fmIK}fg<9@XgHe4*q!aO<-;Xj$T?IzB-{&2`#eA6rdtCi80mpP&vw(Uytxu$#YzNI_cB>LS zmim>ys;ir;*Dzbr22ZDxO2s;671&J0U<9(n1yj)J zHFNz=ufPcQVEG+ePjB<5C;=H0{>Mi*xD>hQq8`Vi7TjJ$V04$`h3EZGL|}a07oQdR z?{cR(z+d>arn^AUug&voOzzi$ZqaS)blz-z3zr;10x;oP2)|Cyb^WtN2*wNn`YX!Y z+$Pji<7|!XyMCEw4so}xXLU)p)BA~2fl>y2Tt}o9*BPm?AXA8UE8a;>rOgyCwZBFa zyl42y`bc3}+hiZL_|L_LY29vVerM+BVE@YxK>TGm@dHi@Uw*7AIq?QA9?THL603J% zIBJ4y3n8OFzsOI;NH%DZ!MDwMl<#$)d9eVVeqVl(5ZX$PPbt*p_(_9VSXhaUPa9Qu z7)q4vqYKX7ieVSjOmVEbLj4VYtnDpe*0Y&+>0dS^bJ<8s*eHq3tjRAw^+Mu4W^-E= z4;&namG4G;3pVDyPkUw#0kWEO1;HI6M51(1<0|*pa(I!sj}F^)avrE`ShVMKBz}nE zzKgOPMSEp6M>hJzyTHHcjV%W*;Tdb}1xJjCP#=iQuBk_Eho6yCRVp&e!}4IBJ&?ksVc&u#g3+G$oNlJ?mWfADjeBS-Ph3`DKk-~Z70XugH8sq2eba@4 zIC1H_J$`9b$K`J)sGX3d!&>OmC@@rx1TL~NinQOYy72Q_+^&Mg>Ku(fTgaXdr$p_V z#gav1o{k~c>#)u3r@~6v^o)Lf=C{rAlL@!s457pq)pO;Cojx7U{urO4cvXP|E>+dV zmr2?!-5)tk-&*ap^D^2x7NG6nOop2zNFQ9v8-EZ{WCz-h36C)<^|f{V#R_WE^@(T0+d-at5hXX{U?zak*ac-XnyINo+yBD~~3O1I=a z99|CI>502&s-Qi5bv>^2#cQ%ut<4d7KgQ^kE|=%6#VlGiY8$rdJUH{sra;P~cyb_i zeX(kS%w0C?mjhJl9TZp8RS;N~y3(EXEz13oPhOSE4WaTljGkVXWd~|#)vsG6_76I)Kb z8ro?;{j^lxNsaxE-cfP;g(e;mhh3)&ba}li?woV2#7ByioiD>s%L_D;?#;C#z;a(N z-_WY<=SH42m9bFQ>Nb z@4K$@4l8pD7AKxCR>t0%`Qoy9=hA?<<^Vcj8;-E+oBe3ReW1`el8np8E$k{LgFQ}2 z2t8a`wOXFdJ9!5$&mEfD1CnJ)TB+RJih88-Zos9@HZ# zL#{qfbF0ARTXkR@G{lwlOH~nnL)1jcyu!qv2`57S&%oKz0}r{~l9U_UHaJ5!8#nrs z?2FrL`mxnzu&{bweD&62)ilz*?pYIvt`T!XFVVA78})p1YEy7 z8fK#s?b~Yo$n7&_a?EBdXH-_W)Z44?!;DFx6pZ?~RArtBI*Qm4~6nX6Z_T*i$bQPE;Qz?DAPstpGSqr-AJ zo%m9cA`oDDm?&dTaoh_>@F>a?!y4qt_;NGN9Z<%SS;fX-cSu|>+Pba22`CRb#|HZa z;{)yHE>M-pc1C0mrnT~80!u&dvVTYFV8xTQ#g;6{c<9d!FDqU%TK5T6h*w*p980D~ zUyCb`y3{-?(mJFP)0*-Nt;mI$-gc4VQumh|rs&j_^R{sgTPF`1Xja2YWstsKFuQ(d zmZMxV$p$|qQUXchu&8%J(9|)B?`~rIx&)LqDS>ob5%gTeTP#Sbny#y*rnJ&?(l=!( zoV~}LJ1DPLnF8oyM(2ScrQ0{Q4m4-BWnS4wilgCW-~~;}pw=&<+HggRD_3c@3RQIr z9+-%!%}u_{`YS=&>h%kPO3ce}>y!d-zqiniNR-b5r97u;+K6HA2tS>Z#cV{+eFI`* zd8RMGAUtX1KWfPV;q<-5JAykS+2sY$2~UX+4461a(%{P#{rwFPu0xpIuYlbgD{C7C z=U{FUarVTYX6ZUq3wE@G^QT4H2Re;n$Fz9cJ>hABl)9T8pozqbA1)H-%1=WKm^QMu zjnUZ&Pu>q+X&6Co*y#@pxc-4waKMInEPGmE_>3@Ym3S*dedSradmc5mlJn`i0vMW6 zhBnGQD^Z;&S0lnS0curqDO@({J7kTtRE+Ra?nl^HP9<)W&C>~`!258f$XDbyQOQXG zP8hhySnarOpgu8xv8@WlXnm(Uk~)_3$Sg0vTbU3 z{W!5B(L3{Yy3K5PN<@jEarAtja`}@KYva&zFRF*s+_%jIXh$T(S=an8?=Ry3H*NRqWgsM`&!#|@kf1>=4q%bFw7^Rhz!z5I zyI^zU8_R1WN9`88Z=n>pIZQ`Ixr~_9G%Q}@A7rd#*%y7G zXl^Id=^ZL?Rx}}gWXCqzj9C6;x(~mAH|$JteXa1MH<6UQig@!Hf~t}B%tP0I|H&;y zO6N0}svOa1a^PyP9N5?4W6VF%=Bj{qHUgc8@siw4bafT=UPFSoQqKgyUX>sXTBZ=x zOh^Ad!{kOM9v{%5y}`-8u*T&C7Vq6mD%GR}UeU(*epO&qgC-CkD;%=l)ZuinSzHM` z{@`j&_vC6dDe{Yb9k@1zeV_K6!l(@=6ucoI=R^cH=6{i71%4W3$J-?<8Qn#$-DMtA z6Qqi)t?4ifrt%3jSA#6ji#{f(($KBL-iQh-xrC||3U3lq`9>r)>X%oLvtimuHW-)} zy}>9~|M>w4eES`g7;iBM%Se5-OP%1U6gNWp3AZqT8C6OlFFfQ$|7LL;tBV)(qlp4K zruar^K8FnJN3@_}B;G`a~H`t|3+6d>q3#`ctTkE-D^1#d9NalQ04lH*qUW2!V zhk7#z8OwHhSl8w14;KctfO8ubZJ4$dEdpXE78wABz=n5*=q9ex3S}`e7x~~V-jmHOhtX2*n+pBslo3uosdE7xABK=V#-t{1Hd~?i z{i~%Bw6NYF+F$aK$M`r#xe=NxhA5=p%i7!$);sd>Q}#`G?Q~fygrMXmZw?0#5#17W}6Tj+&kFexG{!mYl5FoA99}3G9l;3lVQ^ z48^~gsVppE*x91WheqI(A%F0Z#$#1UJP1R12Mj9r)y(A?a+iquX+d8WD4WAQJ_!oq z9rTISr7bPd(GTP57xm$}C}&kjMivi;zi^Y9g3&X0A;ovdJ?{%_wHgt%%9P&N4H z^XzV(uNA4 zAP`hgP6BEN5`YXh|DF~6Pud?~gWfhUKoPX4>z|}0aocC&K+AoV%|SX*N!wGq3|y< zg4lP(04XIPmt6}$N!dTk+pZv>u;MTB{L4hp9uXk7>aS!6jqM2lVr%{)H3$O127TSZ z0x9hi0k-P?nWFdQ0K`pykqUIT&jD~B0tHP{ffS(}fZ(aW$oBWTSfHO!A^><6vA?qar%tzN-5NQO zL&|F{nGiQyzNJ+bM$Y`n=Lx^3wTG^o2bGB@cwr1eb+6c-1tN=U+Db;bc~eJ!hwM{SbI=#g?$!PjDB+) zPgU_2EIxocr*EOJG52-~!gml&|D|C2OQ3Y(zAhL}iae4-Ut0F*!z!VEdfw8#`LAi# zhJ_EM*~;S|FMV6y%-SduHjPOI3cFM(GpH|HES<}*=vqY+64%dJYc|k?n6Br7)D#~# zEqO(xepfaf2F{>{E2`xb=AO%A<7RtUq6kU_Iu0m?@0K(+<}u3gVw5fy=Y4CC*{IE3 zLP3YBJ7x+U(os5=&NT%gKi23bbaZ`@;%ln)wp4GpDUT$J8NtFDHJzIe_-t}{!HAsh zJ4<^WovY};)9IKAskSebdQiXv$y5}THuJZ}ouoElIZRui=6lrupV|_Jz=9^&;@HwL;J#@23k?A;k`0Bgf;ioO>W`IQ+4? z7A)eKoY4%+g%=w;=Vm8}H>@U*=*AWNtPqgWRqib#5RTGA@Q=43FrQn3J`GkTUV5yp0U`EOTqjfp+-9;0F8!dMEwwcK%(6`8sDD^aR04 zd6O5vh|Xk?&3dy4f|1QK&Ulf{h6Iq;d-&*ti#Ck>wZFG;GHwc?b;X~eBITx49>2d8 z4HcK&1&DvEGT6kXdzAm4oO8%c}8OBt~8H956_;YP-ss*uMf==a+%w~F>Qkm7r)IAuxuoX}h92$gHqbFUun#8m zWHdy`Zrm#=Pa98x8cO0vd@Tgkr*lm0{dky+Gocr0P8y%HGEI#c3qLqIRc`Oq_C%*; zG+QTr(#Q|yHKv6R@!DmLlwJQ3FAB)Yor-I4zyDyqM4yp5n2TrQH>gRt*Zw0+WI-Sj`EgmYHh=t9! zF6lz^xpqGGpo6!5`sc0a^FVhy_Uxq|@~(1@IIzV)nTpY9sY`CV!?8e&bB8=M&sYEb z2i}fvKdhp9Hs68Y-!QJ<=wE(iQ5+49tqt;Rh|jhYrI5VW-mIz|UY{h8E=rC5sh#DU z?wGgk-Tn!I?+Zer7pHlF_Z^!Kd1qkS3&lv#%s6-<5Y%jQL${cge5=G5Ab?D&|9$Y~ zf%rJC2+=2vg;y0-SJb3<@3%}BO$T$C66q$L_H33a`VUbgW~N(4B=v5(<=My|#|J7q z*Ox4wL4kbJd_~EjLTABSu4U7Jk#`y(6O*U6(k6XxM}CtGZB(H@3~kh*zaGRXM}Iwp zQ%xFk2>@wiZrVCV_G4G~v;NebCQ%T7{SDyPpSv&dT@Cn)Mx@IK*IdNrj{*4pkV4wv z)y0J538h>cpB7iPSzA~x24T`{dzNkpvGIqvt1Dvdq@o-`B=$hkczX8$yFMhsWNK-X zxr$kR$tMD0@W)Vxe1^t9qVmsg&K^F@u84)(n2dttIEAZFN6VD$&tskpG%SI7whGL3 z)DeRiwe&?8m7U{G`oW8!SCi*dM>oYL%UKQnKxV_0RXAEBQg1kStExGEUVwLJ0orGGwb7uv+kPDl7_E2*iD|J*=8A@;XCvwq0aw5oJYN*Yh&o=l} z2z8YKb-fIAH5spql4eXqp*)o2*b>#1@DSt?zZi{GPj0gH&Nm+EI<3^z0w%YTEV4xw zI6$+=Faa|Y4o5i0zm5lOg|&tmnJ806DBovU@Ll6XsA;NRrTK~t*AAJIAS=v-UZ%Pr z$oddI@NRir&erzCwq|)ciJemr-E061j{0Vc@Ys7K(mW|JYj*$+i1Q8XlIK8T?TYS(AXu$`2U zQ@fHxc=AVHl_}cRZQ)w0anMEoqRKKIvS^`<-aMf*FM`NsG&Uowneo+Ji$7DUDYc7*Hjg;-&aHM%3 zXO6cz$$G};Uqh+iY7Wpme>PHG4cu(q;xyskNLs$^uRRMfEg?8Cj~aE-ajM%CXkx0F z>C?g3tIA#9sBQOpe`J+04{q7^TqhFk^F1jFtk4JDRO*`d-fx`GYHb=&(JiaM1b?Y^ zO3Kj3sj76ieol|N$;>j@t#tKj=@*gP+mv}KwlTcPYgR$+)2(gk)2JNE=jSauPq!$< z<|?Sb%W)wS)b>b6i{8!x!^!xIdU3{CJFVnTcw0j{M%DUCF=_>eYYEUWnA-|B(+KYL z_W_`JI&&u^@t0})@DH^1LDuT0s3dMpCHIbYBgOT4Zh_4yHbSqRbtIKndeT4Q*Jg91 z@>rO!^t-G~*AIW;FQ$3J=b;oGg8?CTa~qNCb>&cgp@e;?0AqA&paz~(%PYO+QBo4( zp?}ZdSMWx0iJm7HVNk9A#^9Osa#GPJ!_pYEW}($8>&2}fbr@&ygZ?${A7_9?X$(&5 z#~-hxdPQwCNEpf=^+WH-3`2LxrrBMTa}~qJC9S;VzhG!On^JLyW6WkF{8aAE$sM+( zxr8xLW(KIjI`Rm(24r3OJBk<3GF=G!uSP0-G&AY32mLm8q=#Xom&Pqv=1C{d3>1^ zAjsmV@XZ%BKq^eUfBpa8KvO8ob|F3hAjJv*yo2Bhl0)KUus{qA9m8jf)KnOGGTa6~4>3@J_VzkL|vYPl*uL+Ot*Q7W!f5rJw5+AsjP_IfL+-S*2p| zB7!FhjvkUTxQkGWGSg{X;h~dK>gAJivW?88Nu!3o>ySDaABn$rAYt086#27fbjPQS zhq>55ASvm*60qRdVOY9=bU^+{Pi#!OaZwENN;zy5?EztOHK-Q5;rCuiFl}BSc1YaQ zC-S{=KsGDz@Ji9O5W;XxE0xI|@3o6(2~i4b8Ii9VT;^G$*dRw(V?=br)D&q^XkeBX z+gl~+R@rVD-Hwv@7RHV?Bip5KMI)aV^&snt?H<$Nt=OPx#VxF&BGi?2A2+lNOYywNUGMeGL;|(=UjGDtLG0sN&LpGx;|U;xa13s z;W_|SPk^G}!M9_^pO zA3bt3-tca%^42sHeDtfcC0S3w3H1ny!Bxpa=*k?XRPpx9Bb-gx1J9Yvx)4J(8cG+q z(iCPZ9dsf3#QVyZgD_MW#G#qgV)olu$59&3(PzQfw@%4uZ~<5J=ABvdY43(Qnp{;G zHg3>@T#>DbTuhFl3)fb3TFqdh)V2aq7!;&JOHseTWukvA7}(iGUq;v-{2J0iHSNHq z;+)h!p6Ok^+Sp8-jgL($n6Qu47xyE`cFO5SdZR6;R!FET`tm#0D37z339Suxjpv+s z*=%2-N$N?X&0?x_uut3erF@aBGj;9$k9?3FlbDO{RQa1_qtxrh4!4#fjp4x~akvdTp@ zos?^Q&XE;3N93s4rHQGPrV7+au1$$aB6$hLy*Yz_kN$~dweb9PcB!eYVQTGjFuJP> zZCEwBtb>TIgIO^qAzq@Bv-qud_ZD-2W<_at&ml-gv`tPt$@DF5`HlA zM>DmmMkpv&Zm-8)Y#0bLQf4MpD4_-7M8eu6rh(tL8dq8onHs#R9J~dGd2IaXXMC~h z91pKhnQa%Fsn29nAA1;x(%oC zhca~qQDJaMf?wFrl-Pj;e$bZMYmMF!Y3Lv&Sb?Sjn#!NVx&NDyc^$b4uYyo2OmERa zRz;yDGd@JTykzFLe|Wk-y7#3x`6$wt$zR8r48mdUvfbeL+4D|Z``~7$PrE@qc7rZe zVsIoIbCwzjLZ@_M1*bD{HaYn();Z1-q*-I{tEnTZ(}Zmk&%MXSNBX>o| z-u*RNkAyKC-Srp7c-=@5f)xMWg>o2WWl}j6j9=8+D8;T z>0*0q#;qw8%U8i;6s0fu#I*%(g*@@a2Er@@nyI}{=@W{Z-;`=wN4N~>6Xrh&z#g}l zN1g5}0-#(nHUTv_rl2{yUZ;h#t&Fd?tY!7L%ClY)>uH-Ny2ET$lW$S)IQiN79H)D^ zb&0AXYkupy0~w8)*>Sj_p9}4L?lGTq%VG|2p`nWGhnM^!g|j-|O{%9Q%swOq63|*W zw$(N_laI}`ilB+o!a-wl?er~;;3+)$_akSQ!8YO_&-e*SI7n^(QQ;X0ZE`{4f!gAl z5$d+9CKVNonM!NO_frREICIAxOv)wm>}-k?iRisM`R7;=lyo|E_YR~FpS&PS`Lg0f zl-ON<0S%Uix8J%#yZdkCz4YNhcec<|7*P(JsM#>-L>+tYg_71q9~70FAc^6KW5jql zw!crdgVLH1G_eET=|SEc977;)ezVC|{PJZfra|}@rD;0s&@61mTEBJtILllg{%{vN zfhb&lq0yChaLhnJ-Qb62MB7`>M;|_ceHKZAeeh@#8tbrK!ArP6oXIhMK;dhEJTY`@ z0Tq>MIe0`7tGv)N*F0IGYSJv0vN?Az8g+4K9S!pW2~9F4W(_U_T=jCZrzuZ3*|__T zONp_UWmyePv8C~rckc?Xji;Z5OEqg zC*Um)i;Wh4TEwqReQdVVbUKT^2>Tpi6z_^-uF*adUFug4i@JhzpWT^Sk&E>CyP2?H zWf6x}ehuTs6wvzCnTU&gYzT029Nz19(In1WC z`(1IGmi!O%2AR|BjQa4Q0~u)kM%}?xQyjWuQ16^Gp++;`vr7!k--UZWM*~7Zl|ceO@I3`OpaRhD;YoCuo5IC0uHx>9 z478hu@H|e0Zlo)Zj@01#;8BDs@991xe~^9uG2}UXLM(m7fa}AMwX*tjioBeV&Q8Gx zSq$6wZFkRBK`cMI>R(@W@+lo2t)L+4q-negWRLWZBz*|%=W4v62JrmzNuOtA*x)QE z5L%=OH#@KMdB%Jp^r?0tE}5-*6oP`-lO7Sf)0)n*e<{HA=&qhLR)oD8-+V}Z4=md) z+k9lKf64DB2hAT)UaCP~di?-V3~JBH7itYyk~L6hrnxM%?RKntqd`=!b|e7eFnAcu z3*V;g{xr7TSTm$}DY%~SMpl>m{Sj!We+WfxSEor?YeiAxYUy25pn(?T()E>ByP^c@ zipwvWrhIK((R((VU+;@LmOnDu)ZXB3YArzzin!Z^0;PyJWnlfflo|q8(QY;o1*5CO z##hnkO{uynTMdk`~DOC#1 zdiYxQoy}=@7(ke#A8$YZZVtk4wo$8x28&I;cY3Ro-|kW=*yiiHgCLZeAr)UtVx>Tu z|LvL0hq|1-jC0I4x#>&QZCfrVB=zT!nR|~Uz`9%~2 znl{uZ{VEszW`Fad^q_HB!K9*|U-stK%?~;g?&&+12A}Rq$z($Bzuk^2X(Y=hF?-dQ ztc3DsQKI;qhWIV`99Q#R3xnU0AvY!i*BECj-z9l74|%O=V@nlv|qqC^r^-~C?E zGW%c|uYgnfJ(gjsTm_cIqcv*mYM{+i+&@F@+69ZQOK&u#v4oxUSQJ=tvqQ3W=*m;| z>SkBi8LYb-qRY7Sthh*0%3XAC%$z1rhOJzuX=PkTOa=DlocZUpE#KxVNH5)_4n=T( zGi3YrH7e~sPNYVBd~Grcq#CF~rN{p9Zza-Ntnwfma@TB)=3g36*0lSZg#ixEjFe%+ zX=&LDZ5zqculZ`=RYc^ln(~;nN|Qh6gN=!6f9-N2h+3NWbIxYud&;4SX*tWf5slk4 z{q@@l71UAZgj~*6edXb57fBUxvAS7s(RI=X868JM0+^DCn2yC>;v%S;qPOjB>YVsz(Zx9a>>BK&M zIQK>7_n)4ud0X5YM}^i*keH{ehLsiy9@NvOpsFeQjdI6anLGvVbBw_*fU1TzdVS$i z*4j7z!I5RF#rSz|8ibi$;qE{4`aqWYik7QB5U&F5C*;TO_x+gtzPGpzNt!7~nsBT7)Ckc(K~%uv&{{6A`mmBJVAk-{s~52Vu|HbCH7_W1~ZCX^RflOakGg=jo2Z z<*s;5-J+2@^LRDZ-7EV&Pq+FTErw@pfFqvx^i%E7Fx#^n(E`m2(c>K-O5`M`Yek9el zzTGs5qD6*G;y#~xu3>qWuO?-amKYtvRA}I9z#UspEeM;wOERYeot_n_EUMJf$4_u?E!6X~?q)tPoZb^_;8Y_Ox2h1m<+Le-fsRd|T8db<8#$bqez zua^Z|>h%zdnuU^ww$#-dZ9NTM`FN+!IlLkz*FqWb!x^Z|C{KyGjZ+>G;;7Mb@LY|H zc+Gp`L((Dw7pnDlHNm&;SfHedhx*kad$I^uGz{`0BYelq0yEUHpNKSkvj$|dpvY3{7*YGyhXA^LP0&wOw9oNoC=QoVx1<2Dne8qqZL zm>nFh5DX(-RnQwvHCZQwn^#Z=E!SPVlaRJ78Bo@}!!9dRt^qZy?-*`Pt4WSmgucJv zV1yFkcjlEM^uz-;b#Q7ZCP@Lk)m}uPX={R4B=56k7WNh11BN~0T*vr@!!ow^B0hOR zQ)4)&(e%>bNNL%bm<&8H{*l_L7s0$2GUgX2Vd;=4d9Dm2v3TaL+;L>{K7h7 zV#k?xDPm(NDE31$ z<}|X)pEY6myjK+^gaIMk&Yj2~F0rSKemNqlsVm4c|N7mp_C*L01s;GNx#D-*&gk!qQr}^?_r@q!8fuXw!)fA7xkd} zb>vHvdx~H$5qqAWrow7}+8zBM65-JOt5z za=T6f7MK`XJuQog8kIEboPdhcaVJeHy)5z7EBLK5NRr()E|#K0L0N^JD@pUA^Czb` zbUZ_558y+vqAGeyHCbrvOvLD67Ph}06959VzQ_|>RrXQAqE+AQ(-AaKdxoWaF8hdt z{O3W@b^*o#-f1VuU>YMV03ELF7zkCN4Q&b#prz%3Nne0lSbRo@@ z^ihv%oIl~Qyl6Q;a#$*jOC%x0_;eis*)J7=f@Ct*)xF5 zo}u~@-I}2|$b%5L7>@+Z?4o+1r&v6ceIy+vroK&jCQ<4q&45HP2wCol4hVm3pZtjf zHz1D7oyaSKJ~T{Gx}7ONLA)D5k(%%`WswrDyzX*rn}i}}TB4^y#@mAwPzoC)`?rYv zHgx|trUN#mu*VzUV~8TnJM2Qh*ZM5B{x&y>5An`(M7=Z*Q>TdiH@j*2=moNuOtvpz z+G`@~-`%~+AgPKgke@XiRPgndh@bp*-HRsh;HTtz@-y_uhb%7ylVOTqG0#u?Vn5c5 zEp*XRo|8hcgG^$#{$O9CJ&NE;TrfRpSnLmes&MO{m=N%zc`}gb!eQ7odl$oy1%PI} z#AIxx%oRVy&{O~9xnK4$EY>(eQj}!HKIV$Fz*H=-=Kn)N0D6u`(;iO|VraI4fu_W` z;b5{7;Lyx4za}DU#+U7}=H0dAS#YJJ&g2!P@Htu-AL&w=-)*%P9h2{wR|@?Ff9~)b z^+e_3Hetq7W%ls{!?<6&Y$Z;NNB41pvrv)|MET6AZXFXJeFqbFW5@i5WGzl?bP+~? z*&_puH;wKv2)9T_d+P`bLvJFqX#j&xa*-;0nGBbQf0DC>o~=J_Wmtf*2SZQr?{i~X z9-IbRH8{iy?<0v9Ir1?$66+igy|yDQ5J~A9sFX@Pe<*kCY8+MwH?I z`P}zfQ6l^AO8ehZ=l^ZR;R%uu4;BK*=?W9t|0{+-at(MQZ(CtG=EJFNaFMlKCMXu30(gJUqj5+ z`GM|!keqcj;FKTa_qq;{*dHRXAq157hlB@kL#8%yAm2AgfU|*rDKX@FLlp=HL8ddv zAWLCHe@DcDeB2}fl7#=0+#<05c3=VqM*O3bkr@9X4nO|)q0hU;Gye{L8ZN*NH8Id@mP-u;Fmb8YuorjLrW&ndip8CN%_qp982r w1WEnz9^$&s1hkp_3#lPJQ~!HI7WYYjA7>z!`?f%npAh2%rB@vD|Lau$2O)#1n*aa+ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 2e6e5897b..aa991fcea 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,5 +1,5 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-7.4.2-bin.zip zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/kmath-ast/README.md b/kmath-ast/README.md index bedf17486..4872a3a26 100644 --- a/kmath-ast/README.md +++ b/kmath-ast/README.md @@ -10,17 +10,17 @@ Extensions to MST API: transformations, dynamic compilation and visualization. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-ast:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-ast:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-ast:0.3.0-dev-17' + implementation 'space.kscience:kmath-ast:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -31,7 +31,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ast:0.3.0-dev-17") + implementation("space.kscience:kmath-ast:0.3.0-dev-20") } ``` @@ -66,20 +66,19 @@ For example, the following code: ```kotlin import space.kscience.kmath.asm.compileToExpression -import space.kscience.kmath.complex.ComplexField +import space.kscience.kmath.operations.DoubleField -"x+2".parseMath().compileToExpression(ComplexField) +"x^3-x+3".parseMath().compileToExpression(DoubleField) ``` … leads to generation of bytecode, which can be decompiled to the following Java class: ```java -import java.util.Map; -import kotlin.jvm.functions.Function2; -import space.kscience.kmath.asm.internal.MapIntrinsics; -import space.kscience.kmath.complex.Complex; -import space.kscience.kmath.expressions.Expression; -import space.kscience.kmath.expressions.Symbol; +import java.util.*; +import kotlin.jvm.functions.*; +import space.kscience.kmath.asm.internal.*; +import space.kscience.kmath.complex.*; +import space.kscience.kmath.expressions.*; public final class CompiledExpression_45045_0 implements Expression { private final Object[] constants; @@ -91,6 +90,32 @@ public final class CompiledExpression_45045_0 implements Expression { } ``` +For `LongRing`, `IntRing`, and `DoubleField` specialization is supported for better performance: + +```java +import java.util.*; +import space.kscience.kmath.asm.internal.*; +import space.kscience.kmath.expressions.*; + +public final class CompiledExpression_-386104628_0 implements DoubleExpression { + private final SymbolIndexer indexer; + + public SymbolIndexer getIndexer() { + return this.indexer; + } + + public double invoke(double[] arguments) { + double var2 = arguments[0]; + return Math.pow(var2, 3.0D) - var2 + 3.0D; + } + + public final Double invoke(Map arguments) { + double var2 = ((Double)MapIntrinsics.getOrFail(arguments, "x")).doubleValue(); + return Math.pow(var2, 3.0D) - var2 + 3.0D; + } +} +``` + Setting JVM system property `space.kscience.kmath.ast.dump.generated.classes` to `1` makes the translator dump class files to program's working directory, so they can be reviewed manually. #### Limitations @@ -134,9 +159,9 @@ MstField { x + 2 }.compileToExpression(DoubleField) An example of emitted Wasm IR in the form of WAT: ```lisp -(func $executable (param $0 f64) (result f64) +(func \$executable (param \$0 f64) (result f64) (f64.add - (local.get $0) + (local.get \$0) (f64.const 2) ) ) diff --git a/kmath-commons/README.md b/kmath-commons/README.md new file mode 100644 index 000000000..a17a39205 --- /dev/null +++ b/kmath-commons/README.md @@ -0,0 +1,32 @@ +# Module kmath-commons + +Commons math binding for kmath + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-commons:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-commons:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-commons:0.3.0-dev-20") +} +``` diff --git a/kmath-complex/README.md b/kmath-complex/README.md index 92f2435ba..b55ce0fea 100644 --- a/kmath-complex/README.md +++ b/kmath-complex/README.md @@ -8,17 +8,17 @@ Complex and hypercomplex number systems in KMath. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-complex:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-complex:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-complex:0.3.0-dev-17' + implementation 'space.kscience:kmath-complex:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-complex:0.3.0-dev-17") + implementation("space.kscience:kmath-complex:0.3.0-dev-20") } ``` diff --git a/kmath-core/README.md b/kmath-core/README.md index e765ad50c..31965ef92 100644 --- a/kmath-core/README.md +++ b/kmath-core/README.md @@ -15,17 +15,17 @@ performance calculations to code generation. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-core:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-core:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-core:0.3.0-dev-17' + implementation 'space.kscience:kmath-core:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -36,6 +36,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-core:0.3.0-dev-17") + implementation("space.kscience:kmath-core:0.3.0-dev-20") } ``` diff --git a/kmath-coroutines/README.md b/kmath-coroutines/README.md new file mode 100644 index 000000000..0d83a6c60 --- /dev/null +++ b/kmath-coroutines/README.md @@ -0,0 +1,32 @@ +# Module kmath-coroutines + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-coroutines:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-coroutines:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-coroutines:0.3.0-dev-20") +} +``` diff --git a/kmath-dimensions/README.md b/kmath-dimensions/README.md new file mode 100644 index 000000000..52097cf40 --- /dev/null +++ b/kmath-dimensions/README.md @@ -0,0 +1,32 @@ +# Module kmath-dimensions + +A proof of concept module for adding type-safe dimensions to structures + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-dimensions:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-dimensions:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-dimensions:0.3.0-dev-20") +} +``` diff --git a/kmath-ejml/README.md b/kmath-ejml/README.md index fcd092bf1..3fe6d9e1a 100644 --- a/kmath-ejml/README.md +++ b/kmath-ejml/README.md @@ -9,17 +9,17 @@ EJML based linear algebra implementation. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-ejml:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-ejml:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-ejml:0.3.0-dev-17' + implementation 'space.kscience:kmath-ejml:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ejml:0.3.0-dev-17") + implementation("space.kscience:kmath-ejml:0.3.0-dev-20") } ``` diff --git a/kmath-for-real/README.md b/kmath-for-real/README.md index 938327612..197190dcd 100644 --- a/kmath-for-real/README.md +++ b/kmath-for-real/README.md @@ -9,17 +9,17 @@ Specialization of KMath APIs for Double numbers. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-for-real:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-for-real:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-for-real:0.3.0-dev-17' + implementation 'space.kscience:kmath-for-real:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-for-real:0.3.0-dev-17") + implementation("space.kscience:kmath-for-real:0.3.0-dev-20") } ``` diff --git a/kmath-functions/README.md b/kmath-functions/README.md index 3d4beee47..6379ad0b5 100644 --- a/kmath-functions/README.md +++ b/kmath-functions/README.md @@ -11,17 +11,17 @@ Functions and interpolations. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-functions:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-functions:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-functions:0.3.0-dev-17' + implementation 'space.kscience:kmath-functions:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -32,6 +32,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-functions:0.3.0-dev-17") + implementation("space.kscience:kmath-functions:0.3.0-dev-20") } ``` diff --git a/kmath-geometry/README.md b/kmath-geometry/README.md new file mode 100644 index 000000000..6b8fb25a0 --- /dev/null +++ b/kmath-geometry/README.md @@ -0,0 +1,32 @@ +# Module kmath-geometry + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-geometry:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-geometry:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-geometry:0.3.0-dev-20") +} +``` diff --git a/kmath-histograms/README.md b/kmath-histograms/README.md new file mode 100644 index 000000000..0b8a632d6 --- /dev/null +++ b/kmath-histograms/README.md @@ -0,0 +1,32 @@ +# Module kmath-histograms + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-histograms:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-histograms:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-histograms:0.3.0-dev-20") +} +``` diff --git a/kmath-jafama/README.md b/kmath-jafama/README.md index 760244751..a274b3d88 100644 --- a/kmath-jafama/README.md +++ b/kmath-jafama/README.md @@ -7,17 +7,17 @@ Integration with [Jafama](https://github.com/jeffhain/jafama). ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-jafama:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-jafama:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-jafama:0.3.0-dev-17' + implementation 'space.kscience:kmath-jafama:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -28,7 +28,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-jafama:0.3.0-dev-17") + implementation("space.kscience:kmath-jafama:0.3.0-dev-20") } ``` diff --git a/kmath-jupyter/README.md b/kmath-jupyter/README.md new file mode 100644 index 000000000..8014b969d --- /dev/null +++ b/kmath-jupyter/README.md @@ -0,0 +1,32 @@ +# Module kmath-jupyter + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-jupyter:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-jupyter:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-jupyter:0.3.0-dev-20") +} +``` diff --git a/kmath-kotlingrad/README.md b/kmath-kotlingrad/README.md index 588ccb9b4..08c913090 100644 --- a/kmath-kotlingrad/README.md +++ b/kmath-kotlingrad/README.md @@ -8,17 +8,17 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-kotlingrad:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-kotlingrad:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-kotlingrad:0.3.0-dev-17' + implementation 'space.kscience:kmath-kotlingrad:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-kotlingrad:0.3.0-dev-17") + implementation("space.kscience:kmath-kotlingrad:0.3.0-dev-20") } ``` diff --git a/kmath-memory/README.md b/kmath-memory/README.md new file mode 100644 index 000000000..d37087a66 --- /dev/null +++ b/kmath-memory/README.md @@ -0,0 +1,32 @@ +# Module kmath-memory + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-memory:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-memory:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-memory:0.3.0-dev-20") +} +``` diff --git a/kmath-multik/README.md b/kmath-multik/README.md new file mode 100644 index 000000000..167445f52 --- /dev/null +++ b/kmath-multik/README.md @@ -0,0 +1,32 @@ +# Module kmath-multik + +JetBrains Multik connector + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-multik:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-multik:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-multik:0.3.0-dev-20") +} +``` diff --git a/kmath-nd4j/README.md b/kmath-nd4j/README.md index 7ca9cd4fd..225de18e9 100644 --- a/kmath-nd4j/README.md +++ b/kmath-nd4j/README.md @@ -9,17 +9,17 @@ ND4J based implementations of KMath abstractions. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-nd4j:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-nd4j:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-nd4j:0.3.0-dev-17' + implementation 'space.kscience:kmath-nd4j:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -30,7 +30,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-nd4j:0.3.0-dev-17") + implementation("space.kscience:kmath-nd4j:0.3.0-dev-20") } ``` diff --git a/kmath-optimization/README.md b/kmath-optimization/README.md new file mode 100644 index 000000000..137975c90 --- /dev/null +++ b/kmath-optimization/README.md @@ -0,0 +1,32 @@ +# Module kmath-optimization + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-optimization:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-optimization:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-optimization:0.3.0-dev-20") +} +``` diff --git a/kmath-stat/README.md b/kmath-stat/README.md new file mode 100644 index 000000000..762e61237 --- /dev/null +++ b/kmath-stat/README.md @@ -0,0 +1,32 @@ +# Module kmath-stat + + + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-stat:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-stat:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-stat:0.3.0-dev-20") +} +``` diff --git a/kmath-symja/README.md b/kmath-symja/README.md new file mode 100644 index 000000000..e3c717cff --- /dev/null +++ b/kmath-symja/README.md @@ -0,0 +1,32 @@ +# Module kmath-symja + +Symja integration module + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-symja:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-symja:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-symja:0.3.0-dev-20") +} +``` diff --git a/kmath-tensorflow/README.md b/kmath-tensorflow/README.md new file mode 100644 index 000000000..f1dfa0202 --- /dev/null +++ b/kmath-tensorflow/README.md @@ -0,0 +1,32 @@ +# Module kmath-tensorflow + +Google tensorflow connector + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-tensorflow:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-tensorflow:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-tensorflow:0.3.0-dev-20") +} +``` diff --git a/kmath-tensors/README.md b/kmath-tensors/README.md index 42ce91336..3d7dfd1fb 100644 --- a/kmath-tensors/README.md +++ b/kmath-tensors/README.md @@ -9,17 +9,17 @@ Common linear algebra operations on tensors. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-tensors:0.3.0-dev-17`. +The Maven coordinates of this project are `space.kscience:kmath-tensors:0.3.0-dev-20`. -**Gradle:** -```gradle +**Gradle Groovy:** +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() } dependencies { - implementation 'space.kscience:kmath-tensors:0.3.0-dev-17' + implementation 'space.kscience:kmath-tensors:0.3.0-dev-20' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-tensors:0.3.0-dev-17") + implementation("space.kscience:kmath-tensors:0.3.0-dev-20") } ``` diff --git a/kmath-viktor/README.md b/kmath-viktor/README.md new file mode 100644 index 000000000..229d4dcd4 --- /dev/null +++ b/kmath-viktor/README.md @@ -0,0 +1,32 @@ +# Module kmath-viktor + +Binding for https://github.com/JetBrains-Research/viktor + +## Usage + +## Artifact: + +The Maven coordinates of this project are `space.kscience:kmath-viktor:0.3.0-dev-20`. + +**Gradle Groovy:** +```groovy +repositories { + maven { url 'https://repo.kotlin.link' } + mavenCentral() +} + +dependencies { + implementation 'space.kscience:kmath-viktor:0.3.0-dev-20' +} +``` +**Gradle Kotlin DSL:** +```kotlin +repositories { + maven("https://repo.kotlin.link") + mavenCentral() +} + +dependencies { + implementation("space.kscience:kmath-viktor:0.3.0-dev-20") +} +``` diff --git a/settings.gradle.kts b/settings.gradle.kts index a8b473fee..b3c275810 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -1,8 +1,6 @@ rootProject.name = "kmath" enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") -enableFeaturePreview("VERSION_CATALOGS") - include( ":kmath-memory", ":kmath-complex", -- 2.34.1 From 13fb49e48c84217dd07b7f3343ba2c0f08962081 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 02:27:50 +0700 Subject: [PATCH 18/59] Rename version catalog --- buildSrc/build.gradle.kts | 8 ++++---- buildSrc/settings.gradle.kts | 3 +-- 2 files changed, 5 insertions(+), 6 deletions(-) diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts index b69ebe6cd..fa5142538 100644 --- a/buildSrc/build.gradle.kts +++ b/buildSrc/build.gradle.kts @@ -1,7 +1,7 @@ plugins { `kotlin-dsl` `version-catalog` - alias(npmlibs.plugins.kotlin.plugin.serialization) + alias(miptNpmLibs.plugins.kotlin.plugin.serialization) } java.targetCompatibility = JavaVersion.VERSION_11 @@ -14,8 +14,8 @@ repositories { } val toolsVersion: String by extra -val kotlinVersion = npmlibs.versions.kotlin.asProvider().get() -val benchmarksVersion = npmlibs.versions.kotlinx.benchmark.get() +val kotlinVersion = miptNpmLibs.versions.kotlin.asProvider().get() +val benchmarksVersion = miptNpmLibs.versions.kotlinx.benchmark.get() dependencies { api("ru.mipt.npm:gradle-tools:$toolsVersion") @@ -23,7 +23,7 @@ dependencies { api("org.jetbrains.kotlinx:kotlinx-benchmark-plugin:$benchmarksVersion") api("org.jetbrains.kotlin:kotlin-allopen:$kotlinVersion") //to be used inside build-script only - implementation(npmlibs.kotlinx.serialization.json) + implementation(miptNpmLibs.kotlinx.serialization.json) } kotlin.sourceSets.all { diff --git a/buildSrc/settings.gradle.kts b/buildSrc/settings.gradle.kts index bc530ac03..7c1df133d 100644 --- a/buildSrc/settings.gradle.kts +++ b/buildSrc/settings.gradle.kts @@ -4,7 +4,6 @@ */ enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") -enableFeaturePreview("VERSION_CATALOGS") dependencyResolutionManagement { val toolsVersion: String by extra @@ -17,7 +16,7 @@ dependencyResolutionManagement { } versionCatalogs { - create("npmlibs") { + create("miptNpmLibs") { from("ru.mipt.npm:version-catalog:$toolsVersion") } } -- 2.34.1 From 38fd3e24c8261eb4da302d499c13d0d063d93712 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 02:37:14 +0700 Subject: [PATCH 19/59] Use correct class name for kotlin JVM compilation --- benchmarks/build.gradle.kts | 2 +- examples/build.gradle.kts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/benchmarks/build.gradle.kts b/benchmarks/build.gradle.kts index f8d39b9c5..22712816d 100644 --- a/benchmarks/build.gradle.kts +++ b/benchmarks/build.gradle.kts @@ -155,7 +155,7 @@ kotlin.sourceSets.all { } } -tasks.withType { +tasks.withType { kotlinOptions { jvmTarget = "11" freeCompilerArgs = freeCompilerArgs + "-Xjvm-default=all" + "-Xlambdas=indy" diff --git a/examples/build.gradle.kts b/examples/build.gradle.kts index 36715cd78..60f8f5aed 100644 --- a/examples/build.gradle.kts +++ b/examples/build.gradle.kts @@ -58,7 +58,7 @@ kotlin.sourceSets.all { } } -tasks.withType { +tasks.withType { kotlinOptions { jvmTarget = "11" freeCompilerArgs = freeCompilerArgs + "-Xjvm-default=all" + "-Xopt-in=kotlin.RequiresOptIn" + "-Xlambdas=indy" -- 2.34.1 From 3277a99ed3bb3668160de14d3e4e23ad9b587600 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 02:58:12 +0700 Subject: [PATCH 20/59] Never use GitHub Packages to publish project with --- build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index 3372d505d..445976853 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -56,7 +56,7 @@ subprojects { readme.readmeTemplate = file("docs/templates/README-TEMPLATE.md") ksciencePublish { - github("kmath") + github("kmath", addToRelease = false) space() sonatype() } -- 2.34.1 From bae465fe865b0b8288861b78b62c04f4b5eef8c3 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 03:06:07 +0700 Subject: [PATCH 21/59] Update GitHub actions --- .github/workflows/build.yml | 8 ++++---- .github/workflows/pages.yml | 20 +++++++++++++++----- .github/workflows/publish.yml | 11 +++++------ 3 files changed, 24 insertions(+), 15 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 455e0dd2d..0834c2656 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -13,13 +13,13 @@ jobs: runs-on: ${{matrix.os}} timeout-minutes: 40 steps: - - uses: actions/checkout@v2 - - uses: actions/setup-java@v2.5.0 + - uses: actions/checkout@v3.0.0 + - uses: actions/setup-java@v3.0.0 with: java-version: 11 distribution: liberica - name: Cache gradle - uses: actions/cache@v2 + uses: actions/cache@v3.0.1 with: path: | ~/.gradle/caches @@ -28,7 +28,7 @@ jobs: restore-keys: | ${{ runner.os }}-gradle- - name: Cache konan - uses: actions/cache@v2 + uses: actions/cache@v3.0.1 with: path: ~/.konan key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index e7f5300c7..0158c82ac 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -9,19 +9,29 @@ jobs: runs-on: ubuntu-20.04 timeout-minutes: 40 steps: - - uses: actions/checkout@v2 - - uses: actions/setup-java@v2.5.0 + - uses: actions/checkout@v3.0.0 + - uses: actions/setup-java@v3.0.0 with: java-version: 11 distribution: liberica - - uses: actions/cache@v2 + - name: Cache gradle + uses: actions/cache@v3.0.1 with: - path: ~/.gradle/caches + path: | + ~/.gradle/caches + ~/.gradle/wrapper + key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} + restore-keys: | + ${{ runner.os }}-gradle- + - name: Cache konan + uses: actions/cache@v3.0.1 + with: + path: ~/.konan key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} restore-keys: | ${{ runner.os }}-gradle- - run: ./gradlew dokkaHtmlMultiModule --build-cache --no-daemon --no-parallel --stacktrace - - uses: JamesIves/github-pages-deploy-action@4.1.0 + - uses: JamesIves/github-pages-deploy-action@4.2.5 with: branch: gh-pages folder: build/dokka/htmlMultiModule diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 17adc5655..83755793a 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -14,13 +14,13 @@ jobs: os: [ macOS-latest, windows-latest ] runs-on: ${{matrix.os}} steps: - - uses: actions/checkout@v2 - - uses: actions/setup-java@v2.5.0 + - uses: actions/checkout@v3.0.0 + - uses: actions/setup-java@v3.0.0 with: java-version: 11 distribution: liberica - name: Cache gradle - uses: actions/cache@v2 + uses: actions/cache@v3.0.1 with: path: | ~/.gradle/caches @@ -29,14 +29,13 @@ jobs: restore-keys: | ${{ runner.os }}-gradle- - name: Cache konan - uses: actions/cache@v2 + uses: actions/cache@v3.0.1 with: path: ~/.konan key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} restore-keys: | ${{ runner.os }}-gradle- - - name: Gradle Wrapper Validation - uses: gradle/wrapper-validation-action@v1.0.4 + - uses: gradle/wrapper-validation-action@v1.0.4 - name: Publish Windows Artifacts if: matrix.os == 'windows-latest' shell: cmd -- 2.34.1 From 97a320c9ef8cd3cdbb73256499200a23be51b84d Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Fri, 1 Apr 2022 14:02:03 +0700 Subject: [PATCH 22/59] Use gradle-build-action --- .github/workflows/build.yml | 14 +++----------- .github/workflows/pages.yml | 13 +++---------- .github/workflows/publish.yml | 34 ++++++++++++++++------------------ 3 files changed, 22 insertions(+), 39 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 0834c2656..cffef64b0 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -18,15 +18,6 @@ jobs: with: java-version: 11 distribution: liberica - - name: Cache gradle - uses: actions/cache@v3.0.1 - with: - path: | - ~/.gradle/caches - ~/.gradle/wrapper - key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} - restore-keys: | - ${{ runner.os }}-gradle- - name: Cache konan uses: actions/cache@v3.0.1 with: @@ -36,5 +27,6 @@ jobs: ${{ runner.os }}-gradle- - name: Gradle Wrapper Validation uses: gradle/wrapper-validation-action@v1.0.4 - - name: Build - run: ./gradlew build --build-cache --no-daemon --stacktrace + - uses: gradle/gradle-build-action@v2.1.5 + with: + arguments: build diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 0158c82ac..9b76fd16e 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -14,15 +14,6 @@ jobs: with: java-version: 11 distribution: liberica - - name: Cache gradle - uses: actions/cache@v3.0.1 - with: - path: | - ~/.gradle/caches - ~/.gradle/wrapper - key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} - restore-keys: | - ${{ runner.os }}-gradle- - name: Cache konan uses: actions/cache@v3.0.1 with: @@ -30,7 +21,9 @@ jobs: key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} restore-keys: | ${{ runner.os }}-gradle- - - run: ./gradlew dokkaHtmlMultiModule --build-cache --no-daemon --no-parallel --stacktrace + - uses: gradle/gradle-build-action@v2.1.5 + with: + arguments: dokkaHtmlMultiModule --no-parallel - uses: JamesIves/github-pages-deploy-action@4.2.5 with: branch: gh-pages diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 83755793a..8e9b98dcb 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -19,15 +19,6 @@ jobs: with: java-version: 11 distribution: liberica - - name: Cache gradle - uses: actions/cache@v3.0.1 - with: - path: | - ~/.gradle/caches - ~/.gradle/wrapper - key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} - restore-keys: | - ${{ runner.os }}-gradle- - name: Cache konan uses: actions/cache@v3.0.1 with: @@ -38,14 +29,21 @@ jobs: - uses: gradle/wrapper-validation-action@v1.0.4 - name: Publish Windows Artifacts if: matrix.os == 'windows-latest' - shell: cmd - run: > - ./gradlew releaseAll --no-daemon --build-cache -Ppublishing.enabled=true - -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} - -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} + uses: gradle/gradle-build-action@v2.1.5 + with: + arguments: | + releaseAll + -Ppublishing.enabled=true + -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} + -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} - name: Publish Mac Artifacts if: matrix.os == 'macOS-latest' - run: > - ./gradlew releaseMacosX64 releaseIosArm64 releaseIosX64 release --no-daemon --build-cache - -Ppublishing.enabled=true -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} - -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} + uses: gradle/gradle-build-action@v2.1.5 + with: + arguments: | + releaseMacosX64 + releaseIosArm64 + releaseIosX64 + -Ppublishing.enabled=true + -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} + -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} -- 2.34.1 From 73f72f12bca21554764e2b24dcb5fd4e22a64983 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 5 Apr 2022 23:23:29 +0300 Subject: [PATCH 23/59] [WIP] Another histogram refactor --- CHANGELOG.md | 1 + .../space/kscience/kmath/domains/Domain1D.kt | 17 ++++ .../space/kscience/kmath/misc/sorting.kt | 75 +++++++++++---- .../space/kscience/kmath/misc/PermSortTest.kt | 25 +++-- kmath-for-real/build.gradle.kts | 15 +-- kmath-histograms/build.gradle.kts | 2 + ...togramSpace.kt => DoubleHistogramGroup.kt} | 8 +- .../kscience/kmath/histogram/Histogram1D.kt | 10 +- ...ogramSpace.kt => IndexedHistogramGroup.kt} | 6 +- .../kmath/histogram/UniformHistogram1D.kt | 94 ++++++++++++++++++- .../histogram/MultivariateHistogramTest.kt | 6 +- .../kmath/histogram/UniformHistogram1DTest.kt | 34 +++++++ .../kmath/distributions/Distribution.kt | 4 +- .../kmath/distributions/NormalDistribution.kt | 15 +-- .../space/kscience/kmath/stat/Sampler.kt | 9 ++ .../kmath/stat/UniformDistribution.kt | 4 +- 16 files changed, 258 insertions(+), 67 deletions(-) rename kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/{DoubleHistogramSpace.kt => DoubleHistogramGroup.kt} (96%) rename kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/{IndexedHistogramSpace.kt => IndexedHistogramGroup.kt} (93%) create mode 100644 kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index a19b1f467..d710c330b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -48,6 +48,7 @@ - Operations -> Ops - Default Buffer and ND algebras are now Ops and lack neutral elements (0, 1) as well as algebra-level shapes. - Tensor algebra takes read-only structures as input and inherits AlgebraND +- `UnivariateDistribution` renamed to `Distribution1D` ### Deprecated - Specialized `DoubleBufferAlgebra` diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt index ccd1c3edb..3d531349c 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain1D.kt @@ -35,6 +35,23 @@ public class DoubleDomain1D( } override fun volume(): Double = range.endInclusive - range.start + + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + + other as DoubleDomain1D + + if (doubleRange != other.doubleRange) return false + + return true + } + + override fun hashCode(): Int = doubleRange.hashCode() + + override fun toString(): String = doubleRange.toString() + + } @UnstableKMathAPI diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/sorting.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/sorting.kt index a144e49b4..dc5421136 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/sorting.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/sorting.kt @@ -3,43 +3,71 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. */ + package space.kscience.kmath.misc -import kotlin.comparisons.* import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.VirtualBuffer /** - * Return a new list filled with buffer indices. Indice order is defined by sorting associated buffer value. - * This feature allows to sort buffer values without reordering its content. + * Return a new array filled with buffer indices. Indices order is defined by sorting associated buffer value. + * This feature allows sorting buffer values without reordering its content. * - * @return List of buffer indices, sorted by associated value. + * @return Buffer indices, sorted by associated value. */ -@PerformancePitfall @UnstableKMathAPI -public fun > Buffer.permSort() : IntArray = _permSortWith(compareBy { get(it) }) +public fun > Buffer.indicesSorted(): IntArray = permSortIndicesWith(compareBy { get(it) }) + +/** + * Create a zero-copy virtual buffer that contains the same elements but in ascending order + */ +@OptIn(UnstableKMathAPI::class) +public fun > Buffer.sorted(): Buffer { + val permutations = indicesSorted() + return VirtualBuffer(size) { this[permutations[it]] } +} -@PerformancePitfall @UnstableKMathAPI -public fun > Buffer.permSortDescending() : IntArray = _permSortWith(compareByDescending { get(it) }) +public fun > Buffer.indicesSortedDescending(): IntArray = + permSortIndicesWith(compareByDescending { get(it) }) + +/** + * Create a zero-copy virtual buffer that contains the same elements but in descending order + */ +@OptIn(UnstableKMathAPI::class) +public fun > Buffer.sortedDescending(): Buffer { + val permutations = indicesSortedDescending() + return VirtualBuffer(size) { this[permutations[it]] } +} -@PerformancePitfall @UnstableKMathAPI -public fun > Buffer.permSortBy(selector: (V) -> C) : IntArray = _permSortWith(compareBy { selector(get(it)) }) +public fun > Buffer.indicesSortedBy(selector: (V) -> C): IntArray = + permSortIndicesWith(compareBy { selector(get(it)) }) + +@OptIn(UnstableKMathAPI::class) +public fun > Buffer.sortedBy(selector: (V) -> C): Buffer { + val permutations = indicesSortedBy(selector) + return VirtualBuffer(size) { this[permutations[it]] } +} -@PerformancePitfall @UnstableKMathAPI -public fun > Buffer.permSortByDescending(selector: (V) -> C) : IntArray = _permSortWith(compareByDescending { selector(get(it)) }) +public fun > Buffer.indicesSortedByDescending(selector: (V) -> C): IntArray = + permSortIndicesWith(compareByDescending { selector(get(it)) }) + +@OptIn(UnstableKMathAPI::class) +public fun > Buffer.sortedByDescending(selector: (V) -> C): Buffer { + val permutations = indicesSortedByDescending(selector) + return VirtualBuffer(size) { this[permutations[it]] } +} -@PerformancePitfall @UnstableKMathAPI -public fun Buffer.permSortWith(comparator : Comparator) : IntArray = _permSortWith { i1, i2 -> comparator.compare(get(i1), get(i2)) } +public fun Buffer.indicesSortedWith(comparator: Comparator): IntArray = + permSortIndicesWith { i1, i2 -> comparator.compare(get(i1), get(i2)) } -@PerformancePitfall -@UnstableKMathAPI -private fun Buffer._permSortWith(comparator : Comparator) : IntArray { - if (size < 2) return IntArray(size) +private fun Buffer.permSortIndicesWith(comparator: Comparator): IntArray { + if (size < 2) return IntArray(size) { 0 } - /* TODO: optimisation : keep a constant big array of indices (Ex: from 0 to 4096), then create indice + /* TODO: optimisation : keep a constant big array of indices (Ex: from 0 to 4096), then create indices * arrays more efficiently by copying subpart of cached one. For bigger needs, we could copy entire * cached array, then fill remaining indices manually. Not done for now, because: * 1. doing it right would require some statistics about common used buffer sizes. @@ -53,3 +81,12 @@ private fun Buffer._permSortWith(comparator : Comparator) : IntArray */ return packedIndices.sortedWith(comparator).toIntArray() } + +/** + * Checks that the [Buffer] is sorted (ascending) and throws [IllegalArgumentException] if it is not. + */ +public fun > Buffer.requireSorted() { + for (i in 0..(size - 2)) { + require(get(i + 1) >= get(i)) { "The buffer is not sorted at index $i" } + } +} diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/PermSortTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/PermSortTest.kt index 0a2bb9138..4a724ac5f 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/PermSortTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/PermSortTest.kt @@ -6,14 +6,13 @@ package space.kscience.kmath.misc import space.kscience.kmath.misc.PermSortTest.Platform.* -import kotlin.random.Random -import kotlin.test.Test -import kotlin.test.assertEquals -import kotlin.test.assertTrue - import space.kscience.kmath.structures.IntBuffer import space.kscience.kmath.structures.asBuffer +import kotlin.random.Random +import kotlin.test.Test import kotlin.test.assertContentEquals +import kotlin.test.assertEquals +import kotlin.test.assertTrue class PermSortTest { @@ -29,9 +28,9 @@ class PermSortTest { @Test fun testOnEmptyBuffer() { val emptyBuffer = IntBuffer(0) {it} - var permutations = emptyBuffer.permSort() + var permutations = emptyBuffer.indicesSorted() assertTrue(permutations.isEmpty(), "permutation on an empty buffer should return an empty result") - permutations = emptyBuffer.permSortDescending() + permutations = emptyBuffer.indicesSortedDescending() assertTrue(permutations.isEmpty(), "permutation on an empty buffer should return an empty result") } @@ -47,25 +46,25 @@ class PermSortTest { @Test fun testPermSortBy() { - val permutations = platforms.permSortBy { it.name } + val permutations = platforms.indicesSortedBy { it.name } val expected = listOf(ANDROID, JS, JVM, NATIVE, WASM) assertContentEquals(expected, permutations.map { platforms[it] }, "Ascending PermSort by name") } @Test fun testPermSortByDescending() { - val permutations = platforms.permSortByDescending { it.name } + val permutations = platforms.indicesSortedByDescending { it.name } val expected = listOf(WASM, NATIVE, JVM, JS, ANDROID) assertContentEquals(expected, permutations.map { platforms[it] }, "Descending PermSort by name") } @Test fun testPermSortWith() { - var permutations = platforms.permSortWith { p1, p2 -> p1.name.length.compareTo(p2.name.length) } + var permutations = platforms.indicesSortedWith { p1, p2 -> p1.name.length.compareTo(p2.name.length) } val expected = listOf(JS, JVM, WASM, NATIVE, ANDROID) assertContentEquals(expected, permutations.map { platforms[it] }, "PermSort using custom ascending comparator") - permutations = platforms.permSortWith(compareByDescending { it.name.length }) + permutations = platforms.indicesSortedWith(compareByDescending { it.name.length }) assertContentEquals(expected.reversed(), permutations.map { platforms[it] }, "PermSort using custom descending comparator") } @@ -75,7 +74,7 @@ class PermSortTest { println("Test randomization seed: $seed") val buffer = Random(seed).buffer(bufferSize) - val indices = buffer.permSort() + val indices = buffer.indicesSorted() assertEquals(bufferSize, indices.size) // Ensure no doublon is present in indices @@ -87,7 +86,7 @@ class PermSortTest { assertTrue(current <= next, "Permutation indices not properly sorted") } - val descIndices = buffer.permSortDescending() + val descIndices = buffer.indicesSortedDescending() assertEquals(bufferSize, descIndices.size) // Ensure no doublon is present in indices assertEquals(descIndices.toSet().size, descIndices.size) diff --git a/kmath-for-real/build.gradle.kts b/kmath-for-real/build.gradle.kts index 4cccaef5c..18c2c50ad 100644 --- a/kmath-for-real/build.gradle.kts +++ b/kmath-for-real/build.gradle.kts @@ -21,19 +21,22 @@ readme { feature( id = "DoubleVector", - description = "Numpy-like operations for Buffers/Points", ref = "src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt" - ) + ){ + "Numpy-like operations for Buffers/Points" + } feature( id = "DoubleMatrix", - description = "Numpy-like operations for 2d real structures", ref = "src/commonMain/kotlin/space/kscience/kmath/real/DoubleMatrix.kt" - ) + ){ + "Numpy-like operations for 2d real structures" + } feature( id = "grids", - description = "Uniform grid generators", ref = "src/commonMain/kotlin/space/kscience/kmath/structures/grids.kt" - ) + ){ + "Uniform grid generators" + } } diff --git a/kmath-histograms/build.gradle.kts b/kmath-histograms/build.gradle.kts index 7e511faa0..51271bb0a 100644 --- a/kmath-histograms/build.gradle.kts +++ b/kmath-histograms/build.gradle.kts @@ -17,6 +17,8 @@ kotlin.sourceSets { commonTest { dependencies { implementation(project(":kmath-for-real")) + implementation(projects.kmath.kmathStat) + implementation("org.jetbrains.kotlinx:kotlinx-coroutines-test:1.6.0") } } } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt similarity index 96% rename from kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt rename to kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt index c0df8c2cc..a80ed119c 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt @@ -16,11 +16,11 @@ import kotlin.math.floor /** * Multivariate histogram space for hyper-square real-field bins. */ -public class DoubleHistogramSpace( +public class DoubleHistogramGroup( private val lower: Buffer, private val upper: Buffer, private val binNums: IntArray = IntArray(lower.size) { 20 }, -) : IndexedHistogramSpace { +) : IndexedHistogramGroup { init { // argument checks @@ -105,7 +105,7 @@ public class DoubleHistogramSpace( */ public fun fromRanges( vararg ranges: ClosedFloatingPointRange, - ): DoubleHistogramSpace = DoubleHistogramSpace( + ): DoubleHistogramGroup = DoubleHistogramGroup( ranges.map(ClosedFloatingPointRange::start).asBuffer(), ranges.map(ClosedFloatingPointRange::endInclusive).asBuffer() ) @@ -121,7 +121,7 @@ public class DoubleHistogramSpace( */ public fun fromRanges( vararg ranges: Pair, Int>, - ): DoubleHistogramSpace = DoubleHistogramSpace( + ): DoubleHistogramGroup = DoubleHistogramGroup( ListBuffer( ranges .map(Pair, Int>::first) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt index 4f193f943..237bd87b9 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt @@ -6,6 +6,7 @@ package space.kscience.kmath.histogram import space.kscience.kmath.domains.Domain1D +import space.kscience.kmath.linear.Point import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.asSequence import space.kscience.kmath.structures.Buffer @@ -18,7 +19,7 @@ import space.kscience.kmath.structures.Buffer * @property standardDeviation Standard deviation of the bin value. Zero or negative if not applicable */ @UnstableKMathAPI -public class Bin1D, out V>( +public data class Bin1D, out V>( public val domain: Domain1D, override val binValue: V, ) : Bin, ClosedRange by domain.range { @@ -35,12 +36,15 @@ public interface Histogram1D, V> : Histogram override operator fun get(point: Buffer): Bin1D? = get(point[0]) } -@UnstableKMathAPI public interface Histogram1DBuilder : HistogramBuilder { /** * Thread safe put operation */ public fun putValue(at: T, value: V = defaultValue) + + override fun putValue(point: Point, value: V) { + putValue(point[0], value) + } } @UnstableKMathAPI @@ -52,5 +56,5 @@ public fun Histogram1DBuilder.fill(array: DoubleArray): Unit = array.forEach(this::putValue) @UnstableKMathAPI -public fun Histogram1DBuilder.fill(buffer: Buffer): Unit = +public fun Histogram1DBuilder.fill(buffer: Buffer): Unit = buffer.asSequence().forEach(this::putValue) \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt similarity index 93% rename from kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt rename to kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt index 3e4b07984..9749f8403 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramSpace.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt @@ -28,7 +28,7 @@ public data class DomainBin, out V>( * @param V the type of bin value */ public class IndexedHistogram, V : Any>( - public val histogramSpace: IndexedHistogramSpace, + public val histogramSpace: IndexedHistogramGroup, public val values: StructureND, ) : Histogram> { @@ -48,8 +48,8 @@ public class IndexedHistogram, V : Any>( /** * A space for producing histograms with values in a NDStructure */ -public interface IndexedHistogramSpace, V : Any> - : Group>, ScaleOperations> { +public interface IndexedHistogramGroup, V : Any> : Group>, + ScaleOperations> { public val shape: Shape public val histogramValueAlgebra: FieldND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index ed8b2e29d..44638c29b 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -5,8 +5,92 @@ package space.kscience.kmath.histogram -//class UniformHistogram1D( -// public val borders: Buffer, -// public val values: Buffer, -//) : Histogram1D { -//} \ No newline at end of file +import space.kscience.kmath.domains.DoubleDomain1D +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.Group +import space.kscience.kmath.operations.Ring +import space.kscience.kmath.operations.ScaleOperations +import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.Buffer +import kotlin.math.floor + +@OptIn(UnstableKMathAPI::class) +public class UniformHistogram1D( + public val group: UniformHistogram1DGroup, + public val values: Map, +) : Histogram1D { + + private val startPoint get() = group.startPoint + private val binSize get() = group.binSize + + private fun produceBin(index: Int, value: V): Bin1D { + val domain = DoubleDomain1D((startPoint + index * binSize)..(startPoint + (index + 1) * binSize)) + return Bin1D(domain, value) + } + + override val bins: Iterable> get() = values.map { produceBin(it.key, it.value) } + + override fun get(value: Double): Bin1D? { + val index: Int = group.getIndex(value) + val v = values[index] + return v?.let { produceBin(index, it) } + } +} + +public class UniformHistogram1DGroup( + public val valueAlgebra: A, + public val binSize: Double, + public val startPoint: Double = 0.0, +) : Group>, ScaleOperations> where A : Ring, A : ScaleOperations { + override val zero: UniformHistogram1D by lazy { UniformHistogram1D(this, emptyMap()) } + + public fun getIndex(at: Double): Int = floor((at - startPoint) / binSize).toInt() + + override fun add(left: UniformHistogram1D, right: UniformHistogram1D): UniformHistogram1D = valueAlgebra { + require(left.group == this@UniformHistogram1DGroup) + require(right.group == this@UniformHistogram1DGroup) + val keys = left.values.keys + right.values.keys + UniformHistogram1D( + this@UniformHistogram1DGroup, + keys.associateWith { (left.values[it] ?: valueAlgebra.zero) + (right.values[it] ?: valueAlgebra.zero) } + ) + } + + override fun UniformHistogram1D.unaryMinus(): UniformHistogram1D = valueAlgebra { + UniformHistogram1D(this@UniformHistogram1DGroup, values.mapValues { -it.value }) + } + + override fun scale( + a: UniformHistogram1D, + value: Double, + ): UniformHistogram1D = UniformHistogram1D( + this@UniformHistogram1DGroup, + a.values.mapValues { valueAlgebra.scale(it.value, value) } + ) + + public inline fun produce(block: Histogram1DBuilder.() -> Unit): UniformHistogram1D { + val map = HashMap() + val builder = object : Histogram1DBuilder { + override val defaultValue: V get() = valueAlgebra.zero + + override fun putValue(at: Double, value: V) { + val index = getIndex(at) + map[index] = with(valueAlgebra) { (map[index] ?: zero) + one } + } + } + builder.block() + return UniformHistogram1D(this, map) + } +} + +public fun Histogram.Companion.uniform1D( + algebra: A, + binSize: Double, + startPoint: Double = 0.0, +): UniformHistogram1DGroup where A : Ring, A : ScaleOperations = + UniformHistogram1DGroup(algebra, binSize, startPoint) + +@UnstableKMathAPI +public fun UniformHistogram1DGroup.produce( + buffer: Buffer, +): UniformHistogram1D = produce { fill(buffer) } \ No newline at end of file diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt index 31a29676c..1426b35fa 100644 --- a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt @@ -14,7 +14,7 @@ import kotlin.test.* internal class MultivariateHistogramTest { @Test fun testSinglePutHistogram() { - val hSpace = DoubleHistogramSpace.fromRanges( + val hSpace = DoubleHistogramGroup.fromRanges( (-1.0..1.0), (-1.0..1.0) ) @@ -29,7 +29,7 @@ internal class MultivariateHistogramTest { @Test fun testSequentialPut() { - val hSpace = DoubleHistogramSpace.fromRanges( + val hSpace = DoubleHistogramGroup.fromRanges( (-1.0..1.0), (-1.0..1.0), (-1.0..1.0) @@ -49,7 +49,7 @@ internal class MultivariateHistogramTest { @Test fun testHistogramAlgebra() { - DoubleHistogramSpace.fromRanges( + DoubleHistogramGroup.fromRanges( (-1.0..1.0), (-1.0..1.0), (-1.0..1.0) diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt new file mode 100644 index 000000000..d23afdb8b --- /dev/null +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt @@ -0,0 +1,34 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.histogram + +import kotlinx.coroutines.ExperimentalCoroutinesApi +import kotlinx.coroutines.test.runTest +import space.kscience.kmath.distributions.NormalDistribution +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.stat.nextBuffer +import kotlin.test.Test +import kotlin.test.assertEquals + +@OptIn(ExperimentalCoroutinesApi::class, UnstableKMathAPI::class) +internal class UniformHistogram1DTest { + @Test + fun normal() = runTest { + val generator = RandomGenerator.default(123) + val distribution = NormalDistribution(0.0, 1.0) + with(Histogram.uniform1D(DoubleField, 0.1)) { + val h1 = produce(distribution.nextBuffer(generator, 10000)) + + val h2 = produce(distribution.nextBuffer(generator, 50000)) + + val h3 = h1 + h2 + + assertEquals(60000, h3.bins.sumOf { it.binValue }.toInt()) + } + } +} \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/Distribution.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/Distribution.kt index 3d3f95f8f..8dbcb3367 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/Distribution.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/Distribution.kt @@ -27,7 +27,7 @@ public interface Distribution : Sampler { public companion object } -public interface UnivariateDistribution> : Distribution { +public interface Distribution1D> : Distribution { /** * Cumulative distribution for ordered parameter (CDF) */ @@ -37,7 +37,7 @@ public interface UnivariateDistribution> : Distribution { /** * Compute probability integral in an interval */ -public fun > UnivariateDistribution.integral(from: T, to: T): Double { +public fun > Distribution1D.integral(from: T, to: T): Double { require(to > from) return cumulative(to) - cumulative(from) } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/NormalDistribution.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/NormalDistribution.kt index 66e041f05..cfc6eba04 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/NormalDistribution.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/NormalDistribution.kt @@ -14,14 +14,9 @@ import space.kscience.kmath.stat.RandomGenerator import kotlin.math.* /** - * Implements [UnivariateDistribution] for the normal (gaussian) distribution. + * Implements [Distribution1D] for the normal (gaussian) distribution. */ -public class NormalDistribution(public val sampler: GaussianSampler) : UnivariateDistribution { - public constructor( - mean: Double, - standardDeviation: Double, - normalized: NormalizedGaussianSampler = ZigguratNormalizedGaussianSampler, - ) : this(GaussianSampler(mean, standardDeviation, normalized)) +public class NormalDistribution(public val sampler: GaussianSampler) : Distribution1D { override fun probability(arg: Double): Double { val x1 = (arg - sampler.mean) / sampler.standardDeviation @@ -43,3 +38,9 @@ public class NormalDistribution(public val sampler: GaussianSampler) : Univariat private val SQRT2 = sqrt(2.0) } } + +public fun NormalDistribution( + mean: Double, + standardDeviation: Double, + normalized: NormalizedGaussianSampler = ZigguratNormalizedGaussianSampler, +): NormalDistribution = NormalDistribution(GaussianSampler(mean, standardDeviation, normalized)) diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt index 0dd121f3b..c96ecdc8c 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt @@ -67,3 +67,12 @@ public fun Sampler.sampleBuffer(generator: RandomGenerator, size: Int): @JvmName("sampleIntBuffer") public fun Sampler.sampleBuffer(generator: RandomGenerator, size: Int): Chain> = sampleBuffer(generator, size, ::IntBuffer) + + +/** + * Samples a [Buffer] of values from this [Sampler]. + */ +public suspend fun Sampler.nextBuffer(generator: RandomGenerator, size: Int): Buffer = + sampleBuffer(generator, size).first() + +//TODO add `context(RandomGenerator) Sampler.nextBuffer \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt index 970a3aab5..20cc0e802 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt @@ -8,9 +8,9 @@ package space.kscience.kmath.stat import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.SimpleChain import space.kscience.kmath.distributions.Distribution -import space.kscience.kmath.distributions.UnivariateDistribution +import space.kscience.kmath.distributions.Distribution1D -public class UniformDistribution(public val range: ClosedFloatingPointRange) : UnivariateDistribution { +public class UniformDistribution(public val range: ClosedFloatingPointRange) : Distribution1D { private val length: Double = range.endInclusive - range.start override fun probability(arg: Double): Double = if (arg in range) 1.0 / length else 0.0 -- 2.34.1 From a2c0bc8a1012b437b1e91edd09e00327467e01f0 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 8 Apr 2022 19:41:41 +0300 Subject: [PATCH 24/59] Another histogram refactor --- .../kmath/histogram/UniformHistogram1D.kt | 24 +++++++++++++++++++ .../kmath/histogram/UniformHistogram1DTest.kt | 16 ++++++++++++- 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index 44638c29b..e2811602c 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -81,6 +81,30 @@ public class UniformHistogram1DGroup( builder.block() return UniformHistogram1D(this, map) } + + /** + * Re-bin given histogram to be compatible if exiting bin fully falls inside existing bin, this bin value + * is increased by one. If not, all bins including values from this bin are increased by fraction + * (conserving the norming). + */ + @UnstableKMathAPI + public fun produceFrom(histogram: Histogram1D): UniformHistogram1D = + if ((histogram as? UniformHistogram1D)?.group == this) histogram + else { + val map = HashMap() + histogram.bins.forEach { bin -> + val range = bin.domain.range + val indexOfLeft = getIndex(range.start) + val indexOfRight = getIndex(range.endInclusive) + val numBins = indexOfRight - indexOfLeft + 1 + for (i in indexOfLeft..indexOfRight) { + map[indexOfLeft] = with(valueAlgebra) { + (map[indexOfLeft] ?: zero) + bin.binValue / numBins + } + } + } + UniformHistogram1D(this, map) + } } public fun Histogram.Companion.uniform1D( diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt index d23afdb8b..8d5cb8fb1 100644 --- a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt @@ -12,14 +12,15 @@ import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.stat.RandomGenerator import space.kscience.kmath.stat.nextBuffer +import kotlin.native.concurrent.ThreadLocal import kotlin.test.Test import kotlin.test.assertEquals @OptIn(ExperimentalCoroutinesApi::class, UnstableKMathAPI::class) internal class UniformHistogram1DTest { + @Test fun normal() = runTest { - val generator = RandomGenerator.default(123) val distribution = NormalDistribution(0.0, 1.0) with(Histogram.uniform1D(DoubleField, 0.1)) { val h1 = produce(distribution.nextBuffer(generator, 10000)) @@ -31,4 +32,17 @@ internal class UniformHistogram1DTest { assertEquals(60000, h3.bins.sumOf { it.binValue }.toInt()) } } + + @Test + fun rebin() = runTest { + val h1 = Histogram.uniform1D(DoubleField, 0.1).produce(generator.nextDoubleBuffer(10000)) + val h2 = Histogram.uniform1D(DoubleField,0.3).produceFrom(h1) + + assertEquals(10000, h2.bins.sumOf { it.binValue }.toInt()) + } + + @ThreadLocal + companion object{ + private val generator = RandomGenerator.default(123) + } } \ No newline at end of file -- 2.34.1 From 3a2faa7da480cee97d2ddb682721ee85f4a57366 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sat, 9 Apr 2022 10:18:18 +0300 Subject: [PATCH 25/59] Generalize UniformHistogram1D --- .../kmath/histogram/UniformHistogram1D.kt | 40 +++++++++++++------ .../kmath/histogram/UniformHistogram1DTest.kt | 14 +++++-- 2 files changed, 39 insertions(+), 15 deletions(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index e2811602c..758e7969a 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -37,37 +37,53 @@ public class UniformHistogram1D( } } +/** + * An algebra for uniform histograms in 1D real space + */ public class UniformHistogram1DGroup( public val valueAlgebra: A, public val binSize: Double, public val startPoint: Double = 0.0, -) : Group>, ScaleOperations> where A : Ring, A : ScaleOperations { +) : Group>, ScaleOperations> where A : Ring, A : ScaleOperations { + override val zero: UniformHistogram1D by lazy { UniformHistogram1D(this, emptyMap()) } - public fun getIndex(at: Double): Int = floor((at - startPoint) / binSize).toInt() + /** + * Get index of a bin + */ + @PublishedApi + internal fun getIndex(at: Double): Int = floor((at - startPoint) / binSize).toInt() - override fun add(left: UniformHistogram1D, right: UniformHistogram1D): UniformHistogram1D = valueAlgebra { - require(left.group == this@UniformHistogram1DGroup) - require(right.group == this@UniformHistogram1DGroup) - val keys = left.values.keys + right.values.keys + override fun add( + left: Histogram1D, + right: Histogram1D, + ): UniformHistogram1D = valueAlgebra { + val leftUniform = produceFrom(left) + val rightUniform = produceFrom(right) + val keys = leftUniform.values.keys + rightUniform.values.keys UniformHistogram1D( this@UniformHistogram1DGroup, - keys.associateWith { (left.values[it] ?: valueAlgebra.zero) + (right.values[it] ?: valueAlgebra.zero) } + keys.associateWith { + (leftUniform.values[it] ?: valueAlgebra.zero) + (rightUniform.values[it] ?: valueAlgebra.zero) + } ) } - override fun UniformHistogram1D.unaryMinus(): UniformHistogram1D = valueAlgebra { - UniformHistogram1D(this@UniformHistogram1DGroup, values.mapValues { -it.value }) + override fun Histogram1D.unaryMinus(): UniformHistogram1D = valueAlgebra { + UniformHistogram1D(this@UniformHistogram1DGroup, produceFrom(this@unaryMinus).values.mapValues { -it.value }) } override fun scale( - a: UniformHistogram1D, + a: Histogram1D, value: Double, ): UniformHistogram1D = UniformHistogram1D( this@UniformHistogram1DGroup, - a.values.mapValues { valueAlgebra.scale(it.value, value) } + produceFrom(a).values.mapValues { valueAlgebra.scale(it.value, value) } ) + /** + * + */ public inline fun produce(block: Histogram1DBuilder.() -> Unit): UniformHistogram1D { val map = HashMap() val builder = object : Histogram1DBuilder { @@ -87,7 +103,7 @@ public class UniformHistogram1DGroup( * is increased by one. If not, all bins including values from this bin are increased by fraction * (conserving the norming). */ - @UnstableKMathAPI + @OptIn(UnstableKMathAPI::class) public fun produceFrom(histogram: Histogram1D): UniformHistogram1D = if ((histogram as? UniformHistogram1D)?.group == this) histogram else { diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt index 8d5cb8fb1..09bf3939d 100644 --- a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/UniformHistogram1DTest.kt @@ -34,9 +34,17 @@ internal class UniformHistogram1DTest { } @Test - fun rebin() = runTest { - val h1 = Histogram.uniform1D(DoubleField, 0.1).produce(generator.nextDoubleBuffer(10000)) - val h2 = Histogram.uniform1D(DoubleField,0.3).produceFrom(h1) + fun rebinDown() = runTest { + val h1 = Histogram.uniform1D(DoubleField, 0.01).produce(generator.nextDoubleBuffer(10000)) + val h2 = Histogram.uniform1D(DoubleField,0.03).produceFrom(h1) + + assertEquals(10000, h2.bins.sumOf { it.binValue }.toInt()) + } + + @Test + fun rebinUp() = runTest { + val h1 = Histogram.uniform1D(DoubleField, 0.03).produce(generator.nextDoubleBuffer(10000)) + val h2 = Histogram.uniform1D(DoubleField,0.01).produceFrom(h1) assertEquals(10000, h2.bins.sumOf { it.binValue }.toInt()) } -- 2.34.1 From eba3a2526e0ca604947e71b5125565f57497623a Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 09:48:55 +0300 Subject: [PATCH 26/59] [final] Generalize UniformHistogram1D --- .../kscience/kmath/histogram/Histogram1D.kt | 9 ++-- .../kmath/histogram/UniformHistogram1D.kt | 54 +++++++++++++------ 2 files changed, 43 insertions(+), 20 deletions(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt index 237bd87b9..0c9352e76 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt @@ -6,6 +6,7 @@ package space.kscience.kmath.histogram import space.kscience.kmath.domains.Domain1D +import space.kscience.kmath.domains.center import space.kscience.kmath.linear.Point import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.asSequence @@ -16,7 +17,6 @@ import space.kscience.kmath.structures.Buffer * A univariate bin based on a range * * @property binValue The value of histogram including weighting - * @property standardDeviation Standard deviation of the bin value. Zero or negative if not applicable */ @UnstableKMathAPI public data class Bin1D, out V>( @@ -56,5 +56,8 @@ public fun Histogram1DBuilder.fill(array: DoubleArray): Unit = array.forEach(this::putValue) @UnstableKMathAPI -public fun Histogram1DBuilder.fill(buffer: Buffer): Unit = - buffer.asSequence().forEach(this::putValue) \ No newline at end of file +public fun Histogram1DBuilder.fill(buffer: Buffer): Unit = + buffer.asSequence().forEach(this::putValue) + +@OptIn(UnstableKMathAPI::class) +public val Bin1D.center: Double get() = domain.center \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index 758e7969a..93eca192f 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -17,7 +17,7 @@ import kotlin.math.floor @OptIn(UnstableKMathAPI::class) public class UniformHistogram1D( public val group: UniformHistogram1DGroup, - public val values: Map, + internal val values: Map, ) : Histogram1D { private val startPoint get() = group.startPoint @@ -82,7 +82,7 @@ public class UniformHistogram1DGroup( ) /** - * + * Fill histogram. */ public inline fun produce(block: Histogram1DBuilder.() -> Unit): UniformHistogram1D { val map = HashMap() @@ -104,23 +104,25 @@ public class UniformHistogram1DGroup( * (conserving the norming). */ @OptIn(UnstableKMathAPI::class) - public fun produceFrom(histogram: Histogram1D): UniformHistogram1D = - if ((histogram as? UniformHistogram1D)?.group == this) histogram - else { - val map = HashMap() - histogram.bins.forEach { bin -> - val range = bin.domain.range - val indexOfLeft = getIndex(range.start) - val indexOfRight = getIndex(range.endInclusive) - val numBins = indexOfRight - indexOfLeft + 1 - for (i in indexOfLeft..indexOfRight) { - map[indexOfLeft] = with(valueAlgebra) { - (map[indexOfLeft] ?: zero) + bin.binValue / numBins - } + public fun produceFrom( + histogram: Histogram1D, + ): UniformHistogram1D = if ((histogram as? UniformHistogram1D)?.group == this) { + histogram + } else { + val map = HashMap() + histogram.bins.forEach { bin -> + val range = bin.domain.range + val indexOfLeft = getIndex(range.start) + val indexOfRight = getIndex(range.endInclusive) + val numBins = indexOfRight - indexOfLeft + 1 + for (i in indexOfLeft..indexOfRight) { + map[indexOfLeft] = with(valueAlgebra) { + (map[indexOfLeft] ?: zero) + bin.binValue / numBins } } - UniformHistogram1D(this, map) } + UniformHistogram1D(this, map) + } } public fun Histogram.Companion.uniform1D( @@ -133,4 +135,22 @@ public fun Histogram.Companion.uniform1D( @UnstableKMathAPI public fun UniformHistogram1DGroup.produce( buffer: Buffer, -): UniformHistogram1D = produce { fill(buffer) } \ No newline at end of file +): UniformHistogram1D = produce { fill(buffer) } + +/** + * Map of bin centers to bin values + */ +@OptIn(UnstableKMathAPI::class) +public val UniformHistogram1D.binValues: Map + get() = bins.associate { it.center to it.binValue } + + +//TODO add normalized values inside Field-based histogram spaces with context receivers +///** +// * Map of bin centers to normalized bin values (bin size as normalization) +// */ +//@OptIn(UnstableKMathAPI::class) +//public val UniformHistogram1D.binValuesNormalized: Map +// get() = group.valueAlgebra { +// bins.associate { it.center to it.binValue / group.binSize } +// } \ No newline at end of file -- 2.34.1 From 86d89f89f904c8dd7bd70f5f596c78d63560a82f Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 10:29:44 +0300 Subject: [PATCH 27/59] Update kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt Co-authored-by: Iaroslav Postovalov <38042667+CommanderTvis@users.noreply.github.com> --- .../space/kscience/kmath/histogram/IndexedHistogramGroup.kt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt index 9749f8403..b1d317a15 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt @@ -68,8 +68,9 @@ public interface IndexedHistogramGroup, V : Any> : Group.() -> Unit): IndexedHistogram override fun add(left: IndexedHistogram, right: IndexedHistogram): IndexedHistogram { - require(left.histogramSpace == this) { "Can't operate on a histogram produced by external space" } - require(right.histogramSpace == this) { "Can't operate on a histogram produced by external space" } + require(left.histogramSpace == this && right.histogramSpace == this) { + "A histogram belonging to a different group cannot be operated." + } return IndexedHistogram(this, histogramValueAlgebra { left.values + right.values }) } -- 2.34.1 From 40b088149bece382affa6016954e0f28fb0e35b5 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 10:29:59 +0300 Subject: [PATCH 28/59] Update kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt Co-authored-by: Iaroslav Postovalov <38042667+CommanderTvis@users.noreply.github.com> --- .../space/kscience/kmath/histogram/IndexedHistogramGroup.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt index b1d317a15..22306049c 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt @@ -75,7 +75,7 @@ public interface IndexedHistogramGroup, V : Any> : Group, value: Double): IndexedHistogram { - require(a.histogramSpace == this) { "Can't operate on a histogram produced by external space" } + require(a.histogramSpace == this) { "A histogram belonging to a different group cannot be operated." } return IndexedHistogram(this, histogramValueAlgebra { a.values * value }) } -- 2.34.1 From 229c36b6616f1a24b85e327673c6283f3d2f9279 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 10:32:36 +0300 Subject: [PATCH 29/59] Accept changes --- .../kmath/histogram/IndexedHistogramGroup.kt | 16 ++++++++-------- .../kmath/histogram/UniformHistogram1D.kt | 2 +- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt index 22306049c..6c04f01bf 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt @@ -28,20 +28,20 @@ public data class DomainBin, out V>( * @param V the type of bin value */ public class IndexedHistogram, V : Any>( - public val histogramSpace: IndexedHistogramGroup, + public val histogramGroup: IndexedHistogramGroup, public val values: StructureND, ) : Histogram> { override fun get(point: Point): DomainBin? { - val index = histogramSpace.getIndex(point) ?: return null - return histogramSpace.produceBin(index, values[index]) + val index = histogramGroup.getIndex(point) ?: return null + return histogramGroup.produceBin(index, values[index]) } - override val dimension: Int get() = histogramSpace.shape.size + override val dimension: Int get() = histogramGroup.shape.size override val bins: Iterable> - get() = DefaultStrides(histogramSpace.shape).asSequence().map { - histogramSpace.produceBin(it, values[it]) + get() = DefaultStrides(histogramGroup.shape).asSequence().map { + histogramGroup.produceBin(it, values[it]) }.asIterable() } @@ -68,14 +68,14 @@ public interface IndexedHistogramGroup, V : Any> : Group.() -> Unit): IndexedHistogram override fun add(left: IndexedHistogram, right: IndexedHistogram): IndexedHistogram { - require(left.histogramSpace == this && right.histogramSpace == this) { + require(left.histogramGroup == this && right.histogramGroup == this) { "A histogram belonging to a different group cannot be operated." } return IndexedHistogram(this, histogramValueAlgebra { left.values + right.values }) } override fun scale(a: IndexedHistogram, value: Double): IndexedHistogram { - require(a.histogramSpace == this) { "A histogram belonging to a different group cannot be operated." } + require(a.histogramGroup == this) { "A histogram belonging to a different group cannot be operated." } return IndexedHistogram(this, histogramValueAlgebra { a.values * value }) } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index 93eca192f..cb6572af9 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -46,7 +46,7 @@ public class UniformHistogram1DGroup( public val startPoint: Double = 0.0, ) : Group>, ScaleOperations> where A : Ring, A : ScaleOperations { - override val zero: UniformHistogram1D by lazy { UniformHistogram1D(this, emptyMap()) } + override val zero: UniformHistogram1D = UniformHistogram1D(this, emptyMap()) /** * Get index of a bin -- 2.34.1 From 27a252b63700782b5005ac987686641a9f151031 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 11:31:52 +0300 Subject: [PATCH 30/59] Accept changes, Update documentation --- .../space/kscience/kmath/domains/HyperSquareDomain.kt | 11 ++++++----- .../kscience/kmath/histogram/DoubleHistogramGroup.kt | 4 ++-- .../kscience/kmath/histogram/IndexedHistogramGroup.kt | 6 +++--- 3 files changed, 11 insertions(+), 10 deletions(-) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt index 2fac442e7..485416a69 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/HyperSquareDomain.kt @@ -11,16 +11,17 @@ import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.indices /** - * - * HyperSquareDomain class. - * - * @author Alexander Nozik + * A hyper-square (or hyper-cube) real-space domain. It is formed by a [Buffer] of [lower] boundaries + * and a [Buffer] of upper boundaries. Upper should be greater or equals than lower. */ @UnstableKMathAPI public class HyperSquareDomain(public val lower: Buffer, public val upper: Buffer) : DoubleDomain { init { require(lower.size == upper.size) { - "Domain borders size mismatch. Lower borders size is ${lower.size}, but upper borders size is ${upper.size}" + "Domain borders size mismatch. Lower borders size is ${lower.size}, but upper borders size is ${upper.size}." + } + require(lower.indices.all { lower[it] <= upper[it] }) { + "Domain borders order mismatch. Lower borders must be less or equals than upper borders." } } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt index a80ed119c..bb66b5dc5 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt @@ -45,7 +45,7 @@ public class DoubleHistogramGroup( else -> floor((value - lower[axis]) / binSize[axis]).toInt() } - override fun getIndex(point: Buffer): IntArray = IntArray(dimension) { + override fun getIndexOrNull(point: Buffer): IntArray = IntArray(dimension) { getIndex(it, point[it]) } @@ -82,7 +82,7 @@ public class DoubleHistogramGroup( override val defaultValue: Double get() = 1.0 override fun putValue(point: Point, value: Double) { - val index = getIndex(point) + val index = getIndexOrNull(point) ndCounter[index].add(value) } } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt index 6c04f01bf..70913ecfb 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt @@ -33,7 +33,7 @@ public class IndexedHistogram, V : Any>( ) : Histogram> { override fun get(point: Point): DomainBin? { - val index = histogramGroup.getIndex(point) ?: return null + val index = histogramGroup.getIndexOrNull(point) ?: return null return histogramGroup.produceBin(index, values[index]) } @@ -54,9 +54,9 @@ public interface IndexedHistogramGroup, V : Any> : Group //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), /** - * Resolve index of the bin including given [point] + * Resolve index of the bin including given [point]. Return null if point is outside histogram area */ - public fun getIndex(point: Point): IntArray? + public fun getIndexOrNull(point: Point): IntArray? /** * Get a bin domain represented by given index -- 2.34.1 From 6247e79884069853f2c523013744826147b06354 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 13:41:41 +0300 Subject: [PATCH 31/59] Refactor multivariate histograms --- CHANGELOG.md | 1 + gradle.properties | 2 + .../space/kscience/kmath/nd/AlgebraND.kt | 2 +- .../space/kscience/kmath/nd/BufferND.kt | 23 ++- .../space/kscience/kmath/histogram/Counter.kt | 3 +- .../kmath/histogram/DoubleHistogramGroup.kt | 140 --------------- .../kscience/kmath/histogram/Histogram.kt | 9 + .../kscience/kmath/histogram/HistogramND.kt | 76 ++++++++ .../kmath/histogram/IndexedHistogramGroup.kt | 84 --------- .../histogram/UniformHistogramGroupND.kt | 163 ++++++++++++++++++ .../histogram/MultivariateHistogramTest.kt | 9 +- .../kmath/histogram/TreeHistogramSpace.kt | 2 +- 12 files changed, 275 insertions(+), 239 deletions(-) delete mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt create mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt delete mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt create mode 100644 kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index d710c330b..bc5447449 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -49,6 +49,7 @@ - Default Buffer and ND algebras are now Ops and lack neutral elements (0, 1) as well as algebra-level shapes. - Tensor algebra takes read-only structures as input and inherits AlgebraND - `UnivariateDistribution` renamed to `Distribution1D` +- Rework of histograms. ### Deprecated - Specialized `DoubleBufferAlgebra` diff --git a/gradle.properties b/gradle.properties index a7cd2f876..847c3dda6 100644 --- a/gradle.properties +++ b/gradle.properties @@ -6,6 +6,8 @@ kotlin.code.style=official kotlin.jupyter.add.scanner=false kotlin.mpp.stability.nowarn=true kotlin.native.ignoreDisabledTargets=true +kotlin.incremental.js.ir=true + org.gradle.configureondemand=true org.gradle.jvmargs=-XX:MaxMetaspaceSize=1G org.gradle.parallel=true diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt index a071c1eb3..a9712e870 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt @@ -194,7 +194,7 @@ public interface RingOpsND> : RingOps>, Gro override fun multiply(left: StructureND, right: StructureND): StructureND = zip(left, right) { aValue, bValue -> multiply(aValue, bValue) } - //TODO move to extensions after KEEP-176 + //TODO move to extensions with context receivers /** * Multiplies an ND structure by an element of it. diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt index 539499794..2401f6319 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt @@ -32,18 +32,23 @@ public open class BufferND( /** * Transform structure to a new structure using provided [BufferFactory] and optimizing if argument is [BufferND] */ -public inline fun StructureND.mapToBuffer( - factory: BufferFactory = Buffer.Companion::auto, +public inline fun StructureND.mapToBuffer( + factory: BufferFactory, crossinline transform: (T) -> R, -): BufferND { - return if (this is BufferND) - BufferND(this.indices, factory.invoke(indices.linearSize) { transform(buffer[it]) }) - else { - val strides = DefaultStrides(shape) - BufferND(strides, factory.invoke(strides.linearSize) { transform(get(strides.index(it))) }) - } +): BufferND = if (this is BufferND) + BufferND(this.indices, factory.invoke(indices.linearSize) { transform(buffer[it]) }) +else { + val strides = DefaultStrides(shape) + BufferND(strides, factory.invoke(strides.linearSize) { transform(get(strides.index(it))) }) } +/** + * Transform structure to a new structure using inferred [BufferFactory] + */ +public inline fun StructureND.mapToBuffer( + crossinline transform: (T) -> R, +): BufferND = mapToBuffer(Buffer.Companion::auto, transform) + /** * Represents [MutableStructureND] over [MutableBuffer]. * diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Counter.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Counter.kt index 291284444..fe3278026 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Counter.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Counter.kt @@ -18,7 +18,8 @@ public interface Counter { public val value: T public companion object { - public fun double(): ObjectCounter = ObjectCounter(DoubleField) + public fun ofDouble(): ObjectCounter = ObjectCounter(DoubleField) + public fun of(group: Group): ObjectCounter = ObjectCounter(group) } } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt deleted file mode 100644 index bb66b5dc5..000000000 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/DoubleHistogramGroup.kt +++ /dev/null @@ -1,140 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -package space.kscience.kmath.histogram - -import space.kscience.kmath.domains.HyperSquareDomain -import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.nd.* -import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.structures.* -import kotlin.math.floor - -/** - * Multivariate histogram space for hyper-square real-field bins. - */ -public class DoubleHistogramGroup( - private val lower: Buffer, - private val upper: Buffer, - private val binNums: IntArray = IntArray(lower.size) { 20 }, -) : IndexedHistogramGroup { - - init { - // argument checks - require(lower.size == upper.size) { "Dimension mismatch in histogram lower and upper limits." } - require(lower.size == binNums.size) { "Dimension mismatch in bin count." } - require(!lower.indices.any { upper[it] - lower[it] < 0 }) { "Range for one of axis is not strictly positive" } - } - - public val dimension: Int get() = lower.size - - override val shape: IntArray = IntArray(binNums.size) { binNums[it] + 2 } - override val histogramValueAlgebra: DoubleFieldND = DoubleField.ndAlgebra(*shape) - - private val binSize = DoubleBuffer(dimension) { (upper[it] - lower[it]) / binNums[it] } - - /** - * Get internal [StructureND] bin index for given axis - */ - private fun getIndex(axis: Int, value: Double): Int = when { - value >= upper[axis] -> binNums[axis] + 1 // overflow - value < lower[axis] -> 0 // underflow - else -> floor((value - lower[axis]) / binSize[axis]).toInt() - } - - override fun getIndexOrNull(point: Buffer): IntArray = IntArray(dimension) { - getIndex(it, point[it]) - } - - @OptIn(UnstableKMathAPI::class) - override fun getDomain(index: IntArray): HyperSquareDomain { - val lowerBoundary = index.mapIndexed { axis, i -> - when (i) { - 0 -> Double.NEGATIVE_INFINITY - shape[axis] - 1 -> upper[axis] - else -> lower[axis] + (i.toDouble()) * binSize[axis] - } - }.asBuffer() - - val upperBoundary = index.mapIndexed { axis, i -> - when (i) { - 0 -> lower[axis] - shape[axis] - 1 -> Double.POSITIVE_INFINITY - else -> lower[axis] + (i.toDouble() + 1) * binSize[axis] - } - }.asBuffer() - - return HyperSquareDomain(lowerBoundary, upperBoundary) - } - - @OptIn(UnstableKMathAPI::class) - override fun produceBin(index: IntArray, value: Double): DomainBin { - val domain = getDomain(index) - return DomainBin(domain, value) - } - - override fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram { - val ndCounter = StructureND.auto(shape) { Counter.double() } - val hBuilder = object : HistogramBuilder { - override val defaultValue: Double get() = 1.0 - - override fun putValue(point: Point, value: Double) { - val index = getIndexOrNull(point) - ndCounter[index].add(value) - } - } - hBuilder.apply(builder) - val values: BufferND = ndCounter.mapToBuffer { it.value } - return IndexedHistogram(this, values) - } - - override fun IndexedHistogram.unaryMinus(): IndexedHistogram = this * (-1) - - public companion object { - /** - * Use it like - * ``` - *FastHistogram.fromRanges( - * (-1.0..1.0), - * (-1.0..1.0) - *) - *``` - */ - public fun fromRanges( - vararg ranges: ClosedFloatingPointRange, - ): DoubleHistogramGroup = DoubleHistogramGroup( - ranges.map(ClosedFloatingPointRange::start).asBuffer(), - ranges.map(ClosedFloatingPointRange::endInclusive).asBuffer() - ) - - /** - * Use it like - * ``` - *FastHistogram.fromRanges( - * (-1.0..1.0) to 50, - * (-1.0..1.0) to 32 - *) - *``` - */ - public fun fromRanges( - vararg ranges: Pair, Int>, - ): DoubleHistogramGroup = DoubleHistogramGroup( - ListBuffer( - ranges - .map(Pair, Int>::first) - .map(ClosedFloatingPointRange::start) - ), - - ListBuffer( - ranges - .map(Pair, Int>::first) - .map(ClosedFloatingPointRange::endInclusive) - ), - - ranges.map(Pair, Int>::second).toIntArray() - ) - } -} \ No newline at end of file diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt index f9550df17..12edafd81 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram.kt @@ -20,6 +20,15 @@ public interface Bin : Domain { public val binValue: V } +/** + * A simple histogram bin based on domain + */ +public data class DomainBin, D : Domain, out V>( + public val domain: D, + override val binValue: V, +) : Bin, Domain by domain + + public interface Histogram> { /** * Find existing bin, corresponding to given coordinates diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt new file mode 100644 index 000000000..2af03abd4 --- /dev/null +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt @@ -0,0 +1,76 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.histogram + +import space.kscience.kmath.domains.Domain +import space.kscience.kmath.linear.Point +import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.nd.FieldOpsND +import space.kscience.kmath.nd.Shape +import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.operations.Group +import space.kscience.kmath.operations.ScaleOperations +import space.kscience.kmath.operations.invoke + +/** + * @param T the type of the argument space + * @param V the type of bin value + */ +public class HistogramND, D : Domain, V : Any>( + public val group: HistogramGroupND, + internal val values: StructureND, +) : Histogram> { + + override fun get(point: Point): DomainBin? { + val index = group.getIndexOrNull(point) ?: return null + return group.produceBin(index, values[index]) + } + + override val dimension: Int get() = group.shape.size + + override val bins: Iterable> + get() = DefaultStrides(group.shape).asSequence().map { + group.produceBin(it, values[it]) + }.asIterable() +} + +/** + * A space for producing histograms with values in a NDStructure + */ +public interface HistogramGroupND, D : Domain, V : Any> : + Group>, ScaleOperations> { + public val shape: Shape + public val valueAlgebra: FieldOpsND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), + + /** + * Resolve index of the bin including given [point]. Return null if point is outside histogram area + */ + public fun getIndexOrNull(point: Point): IntArray? + + /** + * Get a bin domain represented by given index + */ + public fun getDomain(index: IntArray): Domain? + + public fun produceBin(index: IntArray, value: V): DomainBin + + public fun produce(builder: HistogramBuilder.() -> Unit): HistogramND + + override fun add(left: HistogramND, right: HistogramND): HistogramND { + require(left.group == this && right.group == this) { + "A histogram belonging to a different group cannot be operated." + } + return HistogramND(this, valueAlgebra { left.values + right.values }) + } + + override fun scale(a: HistogramND, value: Double): HistogramND { + require(a.group == this) { "A histogram belonging to a different group cannot be operated." } + return HistogramND(this, valueAlgebra { a.values * value }) + } + + override val zero: HistogramND get() = produce { } +} + diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt deleted file mode 100644 index 70913ecfb..000000000 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/IndexedHistogramGroup.kt +++ /dev/null @@ -1,84 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -package space.kscience.kmath.histogram - -import space.kscience.kmath.domains.Domain -import space.kscience.kmath.linear.Point -import space.kscience.kmath.nd.DefaultStrides -import space.kscience.kmath.nd.FieldND -import space.kscience.kmath.nd.Shape -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.operations.Group -import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.operations.invoke - -/** - * A simple histogram bin based on domain - */ -public data class DomainBin, out V>( - public val domain: Domain, - override val binValue: V, -) : Bin, Domain by domain - -/** - * @param T the type of the argument space - * @param V the type of bin value - */ -public class IndexedHistogram, V : Any>( - public val histogramGroup: IndexedHistogramGroup, - public val values: StructureND, -) : Histogram> { - - override fun get(point: Point): DomainBin? { - val index = histogramGroup.getIndexOrNull(point) ?: return null - return histogramGroup.produceBin(index, values[index]) - } - - override val dimension: Int get() = histogramGroup.shape.size - - override val bins: Iterable> - get() = DefaultStrides(histogramGroup.shape).asSequence().map { - histogramGroup.produceBin(it, values[it]) - }.asIterable() -} - -/** - * A space for producing histograms with values in a NDStructure - */ -public interface IndexedHistogramGroup, V : Any> : Group>, - ScaleOperations> { - public val shape: Shape - public val histogramValueAlgebra: FieldND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), - - /** - * Resolve index of the bin including given [point]. Return null if point is outside histogram area - */ - public fun getIndexOrNull(point: Point): IntArray? - - /** - * Get a bin domain represented by given index - */ - public fun getDomain(index: IntArray): Domain? - - public fun produceBin(index: IntArray, value: V): DomainBin - - public fun produce(builder: HistogramBuilder.() -> Unit): IndexedHistogram - - override fun add(left: IndexedHistogram, right: IndexedHistogram): IndexedHistogram { - require(left.histogramGroup == this && right.histogramGroup == this) { - "A histogram belonging to a different group cannot be operated." - } - return IndexedHistogram(this, histogramValueAlgebra { left.values + right.values }) - } - - override fun scale(a: IndexedHistogram, value: Double): IndexedHistogram { - require(a.histogramGroup == this) { "A histogram belonging to a different group cannot be operated." } - return IndexedHistogram(this, histogramValueAlgebra { a.values * value }) - } - - override val zero: IndexedHistogram get() = produce { } -} - diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt new file mode 100644 index 000000000..b93da10b2 --- /dev/null +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt @@ -0,0 +1,163 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +@file:OptIn(UnstableKMathAPI::class) + +package space.kscience.kmath.histogram + +import space.kscience.kmath.domains.HyperSquareDomain +import space.kscience.kmath.linear.Point +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.nd.* +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.Field +import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.* +import kotlin.math.floor + +public typealias HyperSquareBin = DomainBin + +/** + * Multivariate histogram space for hyper-square real-field bins. + * @param bufferFactory is an optional parameter used to optimize buffer production. + */ +public class UniformHistogramGroupND>( + override val valueAlgebra: FieldOpsND, + private val lower: Buffer, + private val upper: Buffer, + private val binNums: IntArray = IntArray(lower.size) { 20 }, + private val bufferFactory: BufferFactory = Buffer.Companion::boxing, +) : HistogramGroupND { + + init { + // argument checks + require(lower.size == upper.size) { "Dimension mismatch in histogram lower and upper limits." } + require(lower.size == binNums.size) { "Dimension mismatch in bin count." } + require(!lower.indices.any { upper[it] - lower[it] < 0 }) { "Range for one of axis is not strictly positive" } + } + + public val dimension: Int get() = lower.size + + override val shape: IntArray = IntArray(binNums.size) { binNums[it] + 2 } + + private val binSize = DoubleBuffer(dimension) { (upper[it] - lower[it]) / binNums[it] } + + /** + * Get internal [StructureND] bin index for given axis + */ + private fun getIndex(axis: Int, value: Double): Int = when { + value >= upper[axis] -> binNums[axis] + 1 // overflow + value < lower[axis] -> 0 // underflow + else -> floor((value - lower[axis]) / binSize[axis]).toInt() + } + + override fun getIndexOrNull(point: Buffer): IntArray = IntArray(dimension) { + getIndex(it, point[it]) + } + + override fun getDomain(index: IntArray): HyperSquareDomain { + val lowerBoundary = index.mapIndexed { axis, i -> + when (i) { + 0 -> Double.NEGATIVE_INFINITY + shape[axis] - 1 -> upper[axis] + else -> lower[axis] + (i.toDouble()) * binSize[axis] + } + }.asBuffer() + + val upperBoundary = index.mapIndexed { axis, i -> + when (i) { + 0 -> lower[axis] + shape[axis] - 1 -> Double.POSITIVE_INFINITY + else -> lower[axis] + (i.toDouble() + 1) * binSize[axis] + } + }.asBuffer() + + return HyperSquareDomain(lowerBoundary, upperBoundary) + } + + override fun produceBin(index: IntArray, value: V): HyperSquareBin { + val domain = getDomain(index) + return DomainBin(domain, value) + } + + + override fun produce(builder: HistogramBuilder.() -> Unit): HistogramND { + val ndCounter = StructureND.buffered(shape) { Counter.of(valueAlgebra.elementAlgebra) } + val hBuilder = object : HistogramBuilder { + override val defaultValue: V get() = valueAlgebra.elementAlgebra.one + + override fun putValue(point: Point, value: V) = with(valueAlgebra.elementAlgebra) { + val index = getIndexOrNull(point) + ndCounter[index].add(value) + } + } + hBuilder.apply(builder) + val values: BufferND = ndCounter.mapToBuffer(bufferFactory) { it.value } + return HistogramND(this, values) + } + + override fun HistogramND.unaryMinus(): HistogramND = + this * (-1) +} + +/** + * Use it like + * ``` + *FastHistogram.fromRanges( + * (-1.0..1.0), + * (-1.0..1.0) + *) + *``` + */ +public fun > Histogram.Companion.uniformNDFromRanges( + valueAlgebra: FieldOpsND, + vararg ranges: ClosedFloatingPointRange, + bufferFactory: BufferFactory = Buffer.Companion::boxing, +): UniformHistogramGroupND = UniformHistogramGroupND( + valueAlgebra, + ranges.map(ClosedFloatingPointRange::start).asBuffer(), + ranges.map(ClosedFloatingPointRange::endInclusive).asBuffer(), + bufferFactory = bufferFactory +) + +public fun Histogram.Companion.uniformDoubleNDFromRanges( + vararg ranges: ClosedFloatingPointRange, +): UniformHistogramGroupND = + uniformNDFromRanges(DoubleFieldOpsND, *ranges, bufferFactory = ::DoubleBuffer) + + +/** + * Use it like + * ``` + *FastHistogram.fromRanges( + * (-1.0..1.0) to 50, + * (-1.0..1.0) to 32 + *) + *``` + */ +public fun > Histogram.Companion.uniformNDFromRanges( + valueAlgebra: FieldOpsND, + vararg ranges: Pair, Int>, + bufferFactory: BufferFactory = Buffer.Companion::boxing, +): UniformHistogramGroupND = UniformHistogramGroupND( + valueAlgebra, + ListBuffer( + ranges + .map(Pair, Int>::first) + .map(ClosedFloatingPointRange::start) + ), + ListBuffer( + ranges + .map(Pair, Int>::first) + .map(ClosedFloatingPointRange::endInclusive) + ), + ranges.map(Pair, Int>::second).toIntArray(), + bufferFactory = bufferFactory +) + +public fun Histogram.Companion.uniformDoubleNDFromRanges( + vararg ranges: Pair, Int>, +): UniformHistogramGroupND = + uniformNDFromRanges(DoubleFieldOpsND, *ranges, bufferFactory = ::DoubleBuffer) \ No newline at end of file diff --git a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt index 1426b35fa..ca7c2f324 100644 --- a/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt +++ b/kmath-histograms/src/commonTest/kotlin/space/kscience/kmath/histogram/MultivariateHistogramTest.kt @@ -3,8 +3,11 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:OptIn(UnstableKMathAPI::class) + package space.kscience.kmath.histogram +import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.DefaultStrides import space.kscience.kmath.operations.invoke import space.kscience.kmath.real.DoubleVector @@ -14,7 +17,7 @@ import kotlin.test.* internal class MultivariateHistogramTest { @Test fun testSinglePutHistogram() { - val hSpace = DoubleHistogramGroup.fromRanges( + val hSpace = Histogram.uniformDoubleNDFromRanges( (-1.0..1.0), (-1.0..1.0) ) @@ -29,7 +32,7 @@ internal class MultivariateHistogramTest { @Test fun testSequentialPut() { - val hSpace = DoubleHistogramGroup.fromRanges( + val hSpace = Histogram.uniformDoubleNDFromRanges( (-1.0..1.0), (-1.0..1.0), (-1.0..1.0) @@ -49,7 +52,7 @@ internal class MultivariateHistogramTest { @Test fun testHistogramAlgebra() { - DoubleHistogramGroup.fromRanges( + Histogram.uniformDoubleNDFromRanges( (-1.0..1.0), (-1.0..1.0), (-1.0..1.0) diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt index e85bb0a3c..bff20c22c 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt @@ -45,7 +45,7 @@ internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) override val defaultValue: Double get() = 1.0 - internal class BinCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.double()) : + internal class BinCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.ofDouble()) : ClosedRange by domain.range private val bins: TreeMap = TreeMap() -- 2.34.1 From 1295a407c37db40c0fa993c7b7c45068e623c079 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 15:29:46 +0300 Subject: [PATCH 32/59] Refactor tree histogram --- gradle.properties | 2 +- .../space/kscience/kmath/structures/Buffer.kt | 10 + .../kscience/kmath/histogram/Histogram1D.kt | 1 + .../kscience/kmath/histogram/HistogramND.kt | 6 +- .../kmath/histogram/UniformHistogram1D.kt | 4 +- .../histogram/UniformHistogramGroupND.kt | 16 +- .../kmath/histogram/TreeHistogramGroup.kt | 179 ++++++++++++++++ .../kmath/histogram/TreeHistogramSpace.kt | 199 ------------------ .../kmath/histogram/TreeHistogramTest.kt | 11 +- 9 files changed, 212 insertions(+), 216 deletions(-) create mode 100644 kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt delete mode 100644 kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt diff --git a/gradle.properties b/gradle.properties index 847c3dda6..80108737e 100644 --- a/gradle.properties +++ b/gradle.properties @@ -6,7 +6,7 @@ kotlin.code.style=official kotlin.jupyter.add.scanner=false kotlin.mpp.stability.nowarn=true kotlin.native.ignoreDisabledTargets=true -kotlin.incremental.js.ir=true +#kotlin.incremental.js.ir=true org.gradle.configureondemand=true org.gradle.jvmargs=-XX:MaxMetaspaceSize=1G diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt index 58c6d5ded..a1b0307c4 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt @@ -105,6 +105,16 @@ public interface Buffer { */ public val Buffer<*>.indices: IntRange get() = 0 until size +public fun Buffer.first(): T { + require(size > 0) { "Can't get the first element of empty buffer" } + return get(0) +} + +public fun Buffer.last(): T { + require(size > 0) { "Can't get the last element of empty buffer" } + return get(size - 1) +} + /** * Immutable wrapper for [MutableBuffer]. * diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt index 0c9352e76..710e4478b 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/Histogram1D.kt @@ -43,6 +43,7 @@ public interface Histogram1DBuilder : HistogramBuilder, value: V) { + require(point.size == 1) { "Only points with single value could be used in Histogram1D" } putValue(point[0], value) } } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt index 2af03abd4..68b24db5d 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/HistogramND.kt @@ -43,7 +43,7 @@ public class HistogramND, D : Domain, V : Any>( public interface HistogramGroupND, D : Domain, V : Any> : Group>, ScaleOperations> { public val shape: Shape - public val valueAlgebra: FieldOpsND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), + public val valueAlgebraND: FieldOpsND //= NDAlgebra.space(valueSpace, Buffer.Companion::boxing, *shape), /** * Resolve index of the bin including given [point]. Return null if point is outside histogram area @@ -63,12 +63,12 @@ public interface HistogramGroupND, D : Domain, V : Any> : require(left.group == this && right.group == this) { "A histogram belonging to a different group cannot be operated." } - return HistogramND(this, valueAlgebra { left.values + right.values }) + return HistogramND(this, valueAlgebraND { left.values + right.values }) } override fun scale(a: HistogramND, value: Double): HistogramND { require(a.group == this) { "A histogram belonging to a different group cannot be operated." } - return HistogramND(this, valueAlgebra { a.values * value }) + return HistogramND(this, valueAlgebraND { a.values * value }) } override val zero: HistogramND get() = produce { } diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt index cb6572af9..e13928394 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogram1D.kt @@ -126,11 +126,11 @@ public class UniformHistogram1DGroup( } public fun Histogram.Companion.uniform1D( - algebra: A, + valueAlgebra: A, binSize: Double, startPoint: Double = 0.0, ): UniformHistogram1DGroup where A : Ring, A : ScaleOperations = - UniformHistogram1DGroup(algebra, binSize, startPoint) + UniformHistogram1DGroup(valueAlgebra, binSize, startPoint) @UnstableKMathAPI public fun UniformHistogram1DGroup.produce( diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt index b93da10b2..90ec29ce3 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt @@ -24,7 +24,7 @@ public typealias HyperSquareBin = DomainBin * @param bufferFactory is an optional parameter used to optimize buffer production. */ public class UniformHistogramGroupND>( - override val valueAlgebra: FieldOpsND, + override val valueAlgebraND: FieldOpsND, private val lower: Buffer, private val upper: Buffer, private val binNums: IntArray = IntArray(lower.size) { 20 }, @@ -84,11 +84,11 @@ public class UniformHistogramGroupND>( override fun produce(builder: HistogramBuilder.() -> Unit): HistogramND { - val ndCounter = StructureND.buffered(shape) { Counter.of(valueAlgebra.elementAlgebra) } + val ndCounter = StructureND.buffered(shape) { Counter.of(valueAlgebraND.elementAlgebra) } val hBuilder = object : HistogramBuilder { - override val defaultValue: V get() = valueAlgebra.elementAlgebra.one + override val defaultValue: V get() = valueAlgebraND.elementAlgebra.one - override fun putValue(point: Point, value: V) = with(valueAlgebra.elementAlgebra) { + override fun putValue(point: Point, value: V) = with(valueAlgebraND.elementAlgebra) { val index = getIndexOrNull(point) ndCounter[index].add(value) } @@ -112,11 +112,11 @@ public class UniformHistogramGroupND>( *``` */ public fun > Histogram.Companion.uniformNDFromRanges( - valueAlgebra: FieldOpsND, + valueAlgebraND: FieldOpsND, vararg ranges: ClosedFloatingPointRange, bufferFactory: BufferFactory = Buffer.Companion::boxing, ): UniformHistogramGroupND = UniformHistogramGroupND( - valueAlgebra, + valueAlgebraND, ranges.map(ClosedFloatingPointRange::start).asBuffer(), ranges.map(ClosedFloatingPointRange::endInclusive).asBuffer(), bufferFactory = bufferFactory @@ -138,11 +138,11 @@ public fun Histogram.Companion.uniformDoubleNDFromRanges( *``` */ public fun > Histogram.Companion.uniformNDFromRanges( - valueAlgebra: FieldOpsND, + valueAlgebraND: FieldOpsND, vararg ranges: Pair, Int>, bufferFactory: BufferFactory = Buffer.Companion::boxing, ): UniformHistogramGroupND = UniformHistogramGroupND( - valueAlgebra, + valueAlgebraND, ListBuffer( ranges .map(Pair, Int>::first) diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt new file mode 100644 index 000000000..6bec01f9b --- /dev/null +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt @@ -0,0 +1,179 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +@file:OptIn(UnstableKMathAPI::class) + +package space.kscience.kmath.histogram + +import space.kscience.kmath.domains.DoubleDomain1D +import space.kscience.kmath.domains.center +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.misc.sorted +import space.kscience.kmath.operations.Group +import space.kscience.kmath.operations.Ring +import space.kscience.kmath.operations.ScaleOperations +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.first +import space.kscience.kmath.structures.indices +import space.kscience.kmath.structures.last +import java.util.* + +private fun > TreeMap.getBin(value: Double): B? { + // check ceiling entry and return it if it is what needed + val ceil = ceilingEntry(value)?.value + if (ceil != null && value in ceil) return ceil + //check floor entry + val floor = floorEntry(value)?.value + if (floor != null && value in floor) return floor + //neither is valid, not found + return null +} + +//public data class ValueAndError(val value: Double, val error: Double) +// +//public typealias WeightedBin1D = Bin1D + +/** + * A histogram based on a tree map of values + */ +public class TreeHistogram( + private val binMap: TreeMap>, +) : Histogram1D { + override fun get(value: Double): Bin1D? = binMap.getBin(value) + override val bins: Collection> get() = binMap.values +} + +/** + * A space for univariate histograms with variable bin borders based on a tree map + */ +public class TreeHistogramGroup( + public val valueAlgebra: A, + @PublishedApi internal val binFactory: (Double) -> DoubleDomain1D, +) : Group>, ScaleOperations> where A : Ring, A : ScaleOperations { + + internal inner class DomainCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.of(valueAlgebra)) : + ClosedRange by domain.range + + @PublishedApi + internal inner class TreeHistogramBuilder : Histogram1DBuilder { + + override val defaultValue: V get() = valueAlgebra.one + + private val bins: TreeMap = TreeMap() + + private fun createBin(value: Double): DomainCounter { + val binDefinition: DoubleDomain1D = binFactory(value) + val newBin = DomainCounter(binDefinition) + synchronized(this) { + bins[binDefinition.center] = newBin + } + return newBin + } + + /** + * Thread safe put operation + */ + override fun putValue(at: Double, value: V) { + (bins.getBin(at) ?: createBin(at)).counter.add(value) + } + + fun build(): TreeHistogram { + val map = bins.mapValuesTo(TreeMap>()) { (_, binCounter) -> + Bin1D(binCounter.domain, binCounter.counter.value) + } + return TreeHistogram(map) + } + } + + public inline fun produce(block: Histogram1DBuilder.() -> Unit): TreeHistogram = + TreeHistogramBuilder().apply(block).build() + + override fun add( + left: TreeHistogram, + right: TreeHistogram, + ): TreeHistogram { + val bins = TreeMap>().apply { + (left.bins.map { it.domain } union right.bins.map { it.domain }).forEach { def -> + put( + def.center, + Bin1D( + def, + with(valueAlgebra) { + (left[def.center]?.binValue ?: zero) + (right[def.center]?.binValue ?: zero) + } + ) + ) + } + } + return TreeHistogram(bins) + } + + override fun scale(a: TreeHistogram, value: Double): TreeHistogram { + val bins = TreeMap>().apply { + a.bins.forEach { bin -> + put( + bin.domain.center, + Bin1D(bin.domain, valueAlgebra.scale(bin.binValue, value)) + ) + } + } + + return TreeHistogram(bins) + } + + override fun TreeHistogram.unaryMinus(): TreeHistogram = this * (-1) + + override val zero: TreeHistogram = produce { } +} + + +///** +// * Build and fill a histogram with custom borders. Returns a read-only histogram. +// */ +//public inline fun Histogram.custom( +// borders: DoubleArray, +// builder: Histogram1DBuilder.() -> Unit, +//): TreeHistogram = custom(borders).fill(builder) +// +// +///** +// * Build and fill a [DoubleHistogram1D]. Returns a read-only histogram. +// */ +//public fun uniform( +// binSize: Double, +// start: Double = 0.0, +//): TreeHistogramSpace = TreeHistogramSpace { value -> +// val center = start + binSize * floor((value - start) / binSize + 0.5) +// DoubleDomain1D((center - binSize / 2)..(center + binSize / 2)) +//} + +/** + * Create a histogram group with custom cell borders + */ +public fun Histogram.Companion.custom1D( + valueAlgebra: A, + borders: Buffer, +): TreeHistogramGroup where A : Ring, A : ScaleOperations { + val sorted = borders.sorted() + + return TreeHistogramGroup(valueAlgebra) { value -> + when { + value <= sorted.first() -> DoubleDomain1D( + Double.NEGATIVE_INFINITY..sorted.first() + ) + + value > sorted.last() -> DoubleDomain1D( + sorted.last()..Double.POSITIVE_INFINITY + ) + + else -> { + val index = sorted.indices.first { value <= sorted[it] } + val left = sorted[index - 1] + val right = sorted[index] + DoubleDomain1D(left..right) + } + } + } +} \ No newline at end of file diff --git a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt deleted file mode 100644 index bff20c22c..000000000 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramSpace.kt +++ /dev/null @@ -1,199 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -@file:OptIn(UnstableKMathAPI::class) - -package space.kscience.kmath.histogram - -import space.kscience.kmath.domains.DoubleDomain1D -import space.kscience.kmath.domains.center -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Group -import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.structures.Buffer -import java.util.* -import kotlin.math.abs -import kotlin.math.floor -import kotlin.math.sqrt - -private fun > TreeMap.getBin(value: Double): B? { - // check ceiling entry and return it if it is what needed - val ceil = ceilingEntry(value)?.value - if (ceil != null && value in ceil) return ceil - //check floor entry - val floor = floorEntry(value)?.value - if (floor != null && value in floor) return floor - //neither is valid, not found - return null -} - -public data class ValueAndError(val value: Double, val error: Double) - -public typealias WeightedBin1D = Bin1D - -public class TreeHistogram( - private val binMap: TreeMap, -) : Histogram1D { - override fun get(value: Double): WeightedBin1D? = binMap.getBin(value) - override val bins: Collection get() = binMap.values -} - -@PublishedApi -internal class TreeHistogramBuilder(val binFactory: (Double) -> DoubleDomain1D) : Histogram1DBuilder { - - override val defaultValue: Double get() = 1.0 - - internal class BinCounter(val domain: DoubleDomain1D, val counter: Counter = Counter.ofDouble()) : - ClosedRange by domain.range - - private val bins: TreeMap = TreeMap() - - fun get(value: Double): BinCounter? = bins.getBin(value) - - fun createBin(value: Double): BinCounter { - val binDefinition: DoubleDomain1D = binFactory(value) - val newBin = BinCounter(binDefinition) - synchronized(this) { - bins[binDefinition.center] = newBin - } - return newBin - } - - /** - * Thread safe put operation - */ - override fun putValue(at: Double, value: Double) { - (get(at) ?: createBin(at)).apply { - counter.add(value) - } - } - - override fun putValue(point: Buffer, value: Double) { - require(point.size == 1) { "Only points with single value could be used in univariate histogram" } - putValue(point[0], value.toDouble()) - } - - fun build(): TreeHistogram { - val map = bins.mapValuesTo(TreeMap()) { (_, binCounter) -> - val count: Double = binCounter.counter.value - WeightedBin1D(binCounter.domain, ValueAndError(count, sqrt(count))) - } - return TreeHistogram(map) - } -} - -/** - * A space for univariate histograms with variable bin borders based on a tree map - */ -public class TreeHistogramSpace( - @PublishedApi internal val binFactory: (Double) -> DoubleDomain1D, -) : Group, ScaleOperations { - - public inline fun fill(block: Histogram1DBuilder.() -> Unit): TreeHistogram = - TreeHistogramBuilder(binFactory).apply(block).build() - - override fun add( - left: TreeHistogram, - right: TreeHistogram, - ): TreeHistogram { -// require(a.context == this) { "Histogram $a does not belong to this context" } -// require(b.context == this) { "Histogram $b does not belong to this context" } - val bins = TreeMap().apply { - (left.bins.map { it.domain } union right.bins.map { it.domain }).forEach { def -> - put( - def.center, - WeightedBin1D( - def, - ValueAndError( - (left[def.center]?.binValue?.value ?: 0.0) + (right[def.center]?.binValue?.value ?: 0.0), - (left[def.center]?.binValue?.error ?: 0.0) + (right[def.center]?.binValue?.error ?: 0.0) - ) - ) - ) - } - } - return TreeHistogram(bins) - } - - override fun scale(a: TreeHistogram, value: Double): TreeHistogram { - val bins = TreeMap().apply { - a.bins.forEach { bin -> - put( - bin.domain.center, - WeightedBin1D( - bin.domain, - ValueAndError( - bin.binValue.value * value, - abs(bin.binValue.error * value) - ) - ) - ) - } - } - - return TreeHistogram(bins) - } - - override fun TreeHistogram.unaryMinus(): TreeHistogram = this * (-1) - - override val zero: TreeHistogram by lazy { fill { } } - - public companion object { - /** - * Build and fill a [TreeHistogram]. Returns a read-only histogram. - */ - public inline fun uniform( - binSize: Double, - start: Double = 0.0, - builder: Histogram1DBuilder.() -> Unit, - ): TreeHistogram = uniform(binSize, start).fill(builder) - - /** - * Build and fill a histogram with custom borders. Returns a read-only histogram. - */ - public inline fun custom( - borders: DoubleArray, - builder: Histogram1DBuilder.() -> Unit, - ): TreeHistogram = custom(borders).fill(builder) - - - /** - * Build and fill a [DoubleHistogram1D]. Returns a read-only histogram. - */ - public fun uniform( - binSize: Double, - start: Double = 0.0, - ): TreeHistogramSpace = TreeHistogramSpace { value -> - val center = start + binSize * floor((value - start) / binSize + 0.5) - DoubleDomain1D((center - binSize / 2)..(center + binSize / 2)) - } - - /** - * Create a histogram with custom cell borders - */ - public fun custom(borders: DoubleArray): TreeHistogramSpace { - val sorted = borders.sortedArray() - - return TreeHistogramSpace { value -> - when { - value < sorted.first() -> DoubleDomain1D( - Double.NEGATIVE_INFINITY..sorted.first() - ) - - value > sorted.last() -> DoubleDomain1D( - sorted.last()..Double.POSITIVE_INFINITY - ) - - else -> { - val index = sorted.indices.first { value > sorted[it] } - val left = sorted[index] - val right = sorted[index + 1] - DoubleDomain1D(left..right) - } - } - } - } - } -} \ No newline at end of file diff --git a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt index f1a8f953b..c4eeb53cc 100644 --- a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt +++ b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt @@ -6,19 +6,24 @@ package space.kscience.kmath.histogram import org.junit.jupiter.api.Test +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.real.step import kotlin.random.Random +import kotlin.test.assertEquals import kotlin.test.assertTrue class TreeHistogramTest { @Test fun normalFill() { - val histogram = TreeHistogramSpace.uniform(0.1) { + val random = Random(123) + val histogram = Histogram.custom1D(DoubleField, 0.0..1.0 step 0.1).produce { repeat(100_000) { - putValue(Random.nextDouble()) + putValue(random.nextDouble()) } } - assertTrue { histogram.bins.count() > 10 } + assertTrue { histogram.bins.count() > 8} + assertEquals(100_000, histogram.bins.sumOf { it.binValue }.toInt()) } } \ No newline at end of file -- 2.34.1 From b509dc917d1836c4b37e4129138d85e1736ad7ef Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 10 Apr 2022 23:00:55 +0300 Subject: [PATCH 33/59] ValueAndErrorField --- CHANGELOG.md | 2 + .../kscience/kmath/functions/integrate.kt | 2 +- .../kmath/functions/interpolateSquare.kt | 2 +- .../kmath/operations/BufferAlgebra.kt | 22 ++++---- .../kscience/kmath/functions/functionTypes.kt | 4 +- .../kscience/kmath/stat/ValueAndErrorField.kt | 56 +++++++++++++++++++ 6 files changed, 73 insertions(+), 15 deletions(-) create mode 100644 kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index bc5447449..b3c9b7b6d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -19,6 +19,7 @@ - Complex power - Separate methods for UInt, Int and Number powers. NaN safety. - Tensorflow prototype +- `ValueAndErrorField` ### Changed - Exponential operations merged with hyperbolic functions @@ -50,6 +51,7 @@ - Tensor algebra takes read-only structures as input and inherits AlgebraND - `UnivariateDistribution` renamed to `Distribution1D` - Rework of histograms. +- `UnivariateFunction` -> `Function1D`, `MultivariateFunction` -> `FunctionND` ### Deprecated - Specialized `DoubleBufferAlgebra` diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt index f60b1ab45..59eaba5bd 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt @@ -13,7 +13,7 @@ import kotlin.math.pow fun main() { //Define a function - val function: UnivariateFunction = { x -> 3 * x.pow(2) + 2 * x + 1 } + val function: Function1D = { x -> 3 * x.pow(2) + 2 * x + 1 } //get the result of the integration val result = DoubleField.gaussIntegrator.integrate(0.0..10.0, function = function) diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt index feefedece..a50df0931 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt @@ -18,7 +18,7 @@ import space.kscience.plotly.scatter @OptIn(UnstablePlotlyAPI::class) fun main() { - val function: UnivariateFunction = { x -> + val function: Function1D = { x -> if (x in 30.0..50.0) { 1.0 } else { diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BufferAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BufferAlgebra.kt index 653552044..51fff8b69 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BufferAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BufferAlgebra.kt @@ -5,7 +5,6 @@ package space.kscience.kmath.operations -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.DoubleBuffer @@ -53,7 +52,7 @@ public interface BufferAlgebra> : Algebra> { */ private inline fun > BufferAlgebra.mapInline( buffer: Buffer, - crossinline block: A.(T) -> T + crossinline block: A.(T) -> T, ): Buffer = bufferFactory(buffer.size) { elementAlgebra.block(buffer[it]) } /** @@ -61,7 +60,7 @@ private inline fun > BufferAlgebra.mapInline( */ private inline fun > BufferAlgebra.mapIndexedInline( buffer: Buffer, - crossinline block: A.(index: Int, arg: T) -> T + crossinline block: A.(index: Int, arg: T) -> T, ): Buffer = bufferFactory(buffer.size) { elementAlgebra.block(it, buffer[it]) } /** @@ -70,7 +69,7 @@ private inline fun > BufferAlgebra.mapIndexedInline( private inline fun > BufferAlgebra.zipInline( l: Buffer, r: Buffer, - crossinline block: A.(l: T, r: T) -> T + crossinline block: A.(l: T, r: T) -> T, ): Buffer { require(l.size == r.size) { "Incompatible buffer sizes. left: ${l.size}, right: ${r.size}" } return bufferFactory(l.size) { elementAlgebra.block(l[it], r[it]) } @@ -127,13 +126,13 @@ public fun > BufferAlgebra.atanh(arg: Buff mapInline(arg) { atanh(it) } public fun > BufferAlgebra.pow(arg: Buffer, pow: Number): Buffer = - mapInline(arg) {it.pow(pow) } + mapInline(arg) { it.pow(pow) } -public open class BufferRingOps>( +public open class BufferRingOps>( override val elementAlgebra: A, override val bufferFactory: BufferFactory, -) : BufferAlgebra, RingOps>{ +) : BufferAlgebra, RingOps> { override fun add(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l + r } override fun multiply(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l * r } @@ -152,10 +151,11 @@ public val ShortRing.bufferAlgebra: BufferRingOps public open class BufferFieldOps>( elementAlgebra: A, bufferFactory: BufferFactory, -) : BufferRingOps(elementAlgebra, bufferFactory), BufferAlgebra, FieldOps>, ScaleOperations> { +) : BufferRingOps(elementAlgebra, bufferFactory), BufferAlgebra, FieldOps>, + ScaleOperations> { - override fun add(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l + r } - override fun multiply(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l * r } +// override fun add(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l + r } +// override fun multiply(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l * r } override fun divide(left: Buffer, right: Buffer): Buffer = zipInline(left, right) { l, r -> l / r } override fun scale(a: Buffer, value: Double): Buffer = a.map { scale(it, value) } @@ -168,7 +168,7 @@ public open class BufferFieldOps>( public class BufferField>( elementAlgebra: A, bufferFactory: BufferFactory, - override val size: Int + override val size: Int, ) : BufferFieldOps(elementAlgebra, bufferFactory), Field>, WithSize { override val zero: Buffer = bufferFactory(size) { elementAlgebra.zero } diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/functionTypes.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/functionTypes.kt index 88b24c756..0e814993c 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/functionTypes.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/functionTypes.kt @@ -7,6 +7,6 @@ package space.kscience.kmath.functions import space.kscience.kmath.structures.Buffer -public typealias UnivariateFunction = (T) -> T +public typealias Function1D = (T) -> T -public typealias MultivariateFunction = (Buffer) -> T \ No newline at end of file +public typealias FunctionND = (Buffer) -> T \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt new file mode 100644 index 000000000..5949213e7 --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt @@ -0,0 +1,56 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.stat + +import space.kscience.kmath.operations.Field +import kotlin.math.pow +import kotlin.math.sqrt + +/** + * A combination of a random [value] and its [dispersion]. + * + * [dispersion] must be positive. + */ +public data class ValueAndError(val value: Double, val dispersion: Double) { + init { + require(dispersion >= 0) { "Dispersion must be non-negative" } + } + + val error: Double get() = sqrt(dispersion) +} + +/** + * An algebra for double value + its error combination. The multiplication assumes linear error propagation + */ +public object ValueAndErrorField : Field { + + override val zero: ValueAndError = ValueAndError(0.0, 0.0) + + override val one: ValueAndError = ValueAndError(1.0, 0.0) + + override fun add(left: ValueAndError, right: ValueAndError): ValueAndError = + ValueAndError(left.value + right.value, left.dispersion + right.dispersion) + + override fun ValueAndError.unaryMinus(): ValueAndError = + ValueAndError(-value, dispersion) + + //TODO study performance impact of pow(2). On JVM it does not exist: https://stackoverflow.com/questions/29144275/xx-vs-math-powx-2-java-performance + + override fun multiply(left: ValueAndError, right: ValueAndError): ValueAndError { + val value = left.value * right.value + val dispersion = (left.dispersion / left.value.pow(2) + right.dispersion / right.value.pow(2)) * value.pow(2) + return ValueAndError(value, dispersion) + } + + override fun divide(left: ValueAndError, right: ValueAndError): ValueAndError { + val value = left.value / right.value + val dispersion = (left.dispersion / left.value.pow(2) + right.dispersion / right.value.pow(2)) * value.pow(2) + return ValueAndError(value, dispersion) + } + + override fun scale(a: ValueAndError, value: Double): ValueAndError = + ValueAndError(a.value * value, a.dispersion * value.pow(2)) +} \ No newline at end of file -- 2.34.1 From 7e4d2230444ff8902ef50c667bbeb75c7b1eb900 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 11 Apr 2022 14:56:48 +0300 Subject: [PATCH 34/59] Fixed missing TF basic operations --- .../kmath/tensorflow/TensorFlowAlgebra.kt | 16 ++++++++----- .../tensors/api/AnalyticTensorAlgebra.kt | 24 +++++++++---------- 2 files changed, 22 insertions(+), 18 deletions(-) diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt index b40739ee0..7185b84d6 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/TensorFlowAlgebra.kt @@ -6,11 +6,9 @@ import org.tensorflow.Operand import org.tensorflow.Output import org.tensorflow.Session import org.tensorflow.ndarray.NdArray +import org.tensorflow.ndarray.index.Indices import org.tensorflow.op.Ops -import org.tensorflow.op.core.Constant -import org.tensorflow.op.core.Max -import org.tensorflow.op.core.Min -import org.tensorflow.op.core.Sum +import org.tensorflow.op.core.* import org.tensorflow.types.TInt32 import org.tensorflow.types.family.TNumber import org.tensorflow.types.family.TType @@ -182,7 +180,7 @@ public abstract class TensorFlowAlgebra> internal c override fun StructureND.unaryMinus(): TensorFlowOutput = operate(ops.math::neg) override fun Tensor.get(i: Int): Tensor = operate { - TODO("Not yet implemented") + StridedSliceHelper.stridedSlice(ops.scope(), it, Indices.at(i.toLong())) } override fun Tensor.transpose(i: Int, j: Int): Tensor = operate { @@ -210,7 +208,13 @@ public abstract class TensorFlowAlgebra> internal c dim1: Int, dim2: Int, ): TensorFlowOutput = diagonalEntries.operate { - TODO("Not yet implemented") + ops.linalg.matrixDiagV3( + /* diagonal = */ it, + /* k = */ ops.constant(offset), + /* numRows = */ ops.constant(dim1), + /* numCols = */ ops.constant(dim2), + /* paddingValue = */ const(elementAlgebra.zero) + ) } override fun StructureND.sum(): T = operate { diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt index 3ed34ae5e..b32fcf608 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt @@ -123,27 +123,27 @@ public interface AnalyticTensorAlgebra> : //For information: https://pytorch.org/docs/stable/generated/torch.floor.html#torch.floor public fun StructureND.floor(): Tensor - override fun sin(arg: StructureND): StructureND = arg.sin() + override fun sin(arg: StructureND): Tensor = arg.sin() - override fun cos(arg: StructureND): StructureND = arg.cos() + override fun cos(arg: StructureND): Tensor = arg.cos() - override fun asin(arg: StructureND): StructureND = arg.asin() + override fun asin(arg: StructureND): Tensor = arg.asin() - override fun acos(arg: StructureND): StructureND = arg.acos() + override fun acos(arg: StructureND): Tensor = arg.acos() - override fun atan(arg: StructureND): StructureND = arg.atan() + override fun atan(arg: StructureND): Tensor = arg.atan() - override fun exp(arg: StructureND): StructureND = arg.exp() + override fun exp(arg: StructureND): Tensor = arg.exp() - override fun ln(arg: StructureND): StructureND = arg.ln() + override fun ln(arg: StructureND): Tensor = arg.ln() - override fun sinh(arg: StructureND): StructureND = arg.sinh() + override fun sinh(arg: StructureND): Tensor = arg.sinh() - override fun cosh(arg: StructureND): StructureND = arg.cosh() + override fun cosh(arg: StructureND): Tensor = arg.cosh() - override fun asinh(arg: StructureND): StructureND = arg.asinh() + override fun asinh(arg: StructureND): Tensor = arg.asinh() - override fun acosh(arg: StructureND): StructureND = arg.acosh() + override fun acosh(arg: StructureND): Tensor = arg.acosh() - override fun atanh(arg: StructureND): StructureND = arg.atanh() + override fun atanh(arg: StructureND): Tensor = arg.atanh() } \ No newline at end of file -- 2.34.1 From 916bc69e4b6ff002126c3457ddcb3ea8f5701e0f Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 11 Apr 2022 17:32:16 +0300 Subject: [PATCH 35/59] Revert changes in tensor algebra to remove name conflicts --- .../tensors/api/AnalyticTensorAlgebra.kt | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt index b32fcf608..3ed34ae5e 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/AnalyticTensorAlgebra.kt @@ -123,27 +123,27 @@ public interface AnalyticTensorAlgebra> : //For information: https://pytorch.org/docs/stable/generated/torch.floor.html#torch.floor public fun StructureND.floor(): Tensor - override fun sin(arg: StructureND): Tensor = arg.sin() + override fun sin(arg: StructureND): StructureND = arg.sin() - override fun cos(arg: StructureND): Tensor = arg.cos() + override fun cos(arg: StructureND): StructureND = arg.cos() - override fun asin(arg: StructureND): Tensor = arg.asin() + override fun asin(arg: StructureND): StructureND = arg.asin() - override fun acos(arg: StructureND): Tensor = arg.acos() + override fun acos(arg: StructureND): StructureND = arg.acos() - override fun atan(arg: StructureND): Tensor = arg.atan() + override fun atan(arg: StructureND): StructureND = arg.atan() - override fun exp(arg: StructureND): Tensor = arg.exp() + override fun exp(arg: StructureND): StructureND = arg.exp() - override fun ln(arg: StructureND): Tensor = arg.ln() + override fun ln(arg: StructureND): StructureND = arg.ln() - override fun sinh(arg: StructureND): Tensor = arg.sinh() + override fun sinh(arg: StructureND): StructureND = arg.sinh() - override fun cosh(arg: StructureND): Tensor = arg.cosh() + override fun cosh(arg: StructureND): StructureND = arg.cosh() - override fun asinh(arg: StructureND): Tensor = arg.asinh() + override fun asinh(arg: StructureND): StructureND = arg.asinh() - override fun acosh(arg: StructureND): Tensor = arg.acosh() + override fun acosh(arg: StructureND): StructureND = arg.acosh() - override fun atanh(arg: StructureND): Tensor = arg.atanh() + override fun atanh(arg: StructureND): StructureND = arg.atanh() } \ No newline at end of file -- 2.34.1 From 74e6bc65a315dbc0623ac8b1bfbc9fe1bcfd62df Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 11 Apr 2022 20:07:40 +0300 Subject: [PATCH 36/59] 0.3.0 release --- CHANGELOG.md | 28 +- build.gradle.kts | 2 +- kmath-ast/README.md | 6 +- kmath-commons/README.md | 6 +- kmath-complex/README.md | 6 +- kmath-core/README.md | 6 +- kmath-core/api/kmath-core.api | 926 +++++++++++++++++++++--------- kmath-coroutines/README.md | 6 +- kmath-dimensions/README.md | 6 +- kmath-ejml/README.md | 6 +- kmath-for-real/README.md | 6 +- kmath-functions/README.md | 6 +- kmath-geometry/README.md | 6 +- kmath-histograms/README.md | 6 +- kmath-jafama/README.md | 6 +- kmath-jupyter/README.md | 6 +- kmath-kotlingrad/README.md | 6 +- kmath-memory/README.md | 6 +- kmath-multik/README.md | 6 +- kmath-nd4j/README.md | 6 +- kmath-optimization/README.md | 6 +- kmath-stat/README.md | 6 +- kmath-symja/README.md | 6 +- kmath-tensorflow/README.md | 6 +- kmath-tensors/README.md | 6 +- kmath-viktor/README.md | 6 +- kmath-viktor/api/kmath-viktor.api | 72 ++- 27 files changed, 793 insertions(+), 373 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index b3c9b7b6d..28240dc68 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,19 @@ ## [Unreleased] ### Added + +### Changed + +### Deprecated + +### Removed + +### Fixed + +### Security + +## [0.3.0] +### Added - `ScaleOperations` interface - `Field` extends `ScaleOperations` - Basic integration API @@ -21,6 +34,7 @@ - Tensorflow prototype - `ValueAndErrorField` + ### Changed - Exponential operations merged with hyperbolic functions - Space is replaced by Group. Space is reserved for vector spaces. @@ -53,9 +67,11 @@ - Rework of histograms. - `UnivariateFunction` -> `Function1D`, `MultivariateFunction` -> `FunctionND` + ### Deprecated - Specialized `DoubleBufferAlgebra` + ### Removed - Nearest in Domain. To be implemented in geometry package. - Number multiplication and division in main Algebra chain @@ -66,10 +82,12 @@ - Second generic from DifferentiableExpression - Algebra elements are completely removed. Use algebra contexts instead. + ### Fixed - Ring inherits RingOperations, not GroupOperations - Univariate histogram filling + ### Security ## [0.2.0] @@ -92,6 +110,7 @@ - New `MatrixFeature` interfaces for matrix decompositions - Basic Quaternion vector support in `kmath-complex`. + ### Changed - Package changed from `scientifik` to `space.kscience` - Gradle version: 6.6 -> 6.8.2 @@ -116,7 +135,6 @@ - `symbol` method in `Algebra` renamed to `bindSymbol` to avoid ambiguity - Add `out` projection to `Buffer` generic -### Deprecated ### Removed - `kmath-koma` module because it doesn't support Kotlin 1.4. @@ -126,13 +144,11 @@ - `Real` class - StructureND identity and equals + ### Fixed - `symbol` method in `MstExtendedField` (https://github.com/mipt-npm/kmath/pull/140) -### Security - ## [0.1.4] - ### Added - Functional Expressions API - Mathematical Syntax Tree, its interpreter and API @@ -150,6 +166,7 @@ - Full hyperbolic functions support and default implementations within `ExtendedField` - Norm support for `Complex` + ### Changed - `readAsMemory` now has `throws IOException` in JVM signature. - Several functions taking functional types were made `inline`. @@ -161,9 +178,10 @@ - Gradle version: 6.3 -> 6.6 - Moved probability distributions to commons-rng and to `kmath-prob` + ### Fixed - Missing copy method in Memory implementation on JS (https://github.com/mipt-npm/kmath/pull/106) - D3.dim value in `kmath-dimensions` - Multiplication in integer rings in `kmath-core` (https://github.com/mipt-npm/kmath/pull/101) - Commons RNG compatibility (https://github.com/mipt-npm/kmath/issues/93) -- Multiplication of BigInt by scalar +- Multiplication of BigInt by scalar \ No newline at end of file diff --git a/build.gradle.kts b/build.gradle.kts index 1e703c5e1..10f2385f5 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -11,7 +11,7 @@ allprojects { } group = "space.kscience" - version = "0.3.0-dev-21" + version = "0.3.0" } subprojects { diff --git a/kmath-ast/README.md b/kmath-ast/README.md index 4872a3a26..5d5630f46 100644 --- a/kmath-ast/README.md +++ b/kmath-ast/README.md @@ -10,7 +10,7 @@ Extensions to MST API: transformations, dynamic compilation and visualization. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-ast:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-ast:0.3.0`. **Gradle Groovy:** ```groovy @@ -20,7 +20,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-ast:0.3.0-dev-20' + implementation 'space.kscience:kmath-ast:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -31,7 +31,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ast:0.3.0-dev-20") + implementation("space.kscience:kmath-ast:0.3.0") } ``` diff --git a/kmath-commons/README.md b/kmath-commons/README.md index a17a39205..7195e6fb1 100644 --- a/kmath-commons/README.md +++ b/kmath-commons/README.md @@ -6,7 +6,7 @@ Commons math binding for kmath ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-commons:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-commons:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-commons:0.3.0-dev-20' + implementation 'space.kscience:kmath-commons:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-commons:0.3.0-dev-20") + implementation("space.kscience:kmath-commons:0.3.0") } ``` diff --git a/kmath-complex/README.md b/kmath-complex/README.md index b55ce0fea..4646c6a80 100644 --- a/kmath-complex/README.md +++ b/kmath-complex/README.md @@ -8,7 +8,7 @@ Complex and hypercomplex number systems in KMath. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-complex:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-complex:0.3.0`. **Gradle Groovy:** ```groovy @@ -18,7 +18,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-complex:0.3.0-dev-20' + implementation 'space.kscience:kmath-complex:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-complex:0.3.0-dev-20") + implementation("space.kscience:kmath-complex:0.3.0") } ``` diff --git a/kmath-core/README.md b/kmath-core/README.md index 31965ef92..4fddd327c 100644 --- a/kmath-core/README.md +++ b/kmath-core/README.md @@ -15,7 +15,7 @@ performance calculations to code generation. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-core:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-core:0.3.0`. **Gradle Groovy:** ```groovy @@ -25,7 +25,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-core:0.3.0-dev-20' + implementation 'space.kscience:kmath-core:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -36,6 +36,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-core:0.3.0-dev-20") + implementation("space.kscience:kmath-core:0.3.0") } ``` diff --git a/kmath-core/api/kmath-core.api b/kmath-core/api/kmath-core.api index b424b59ff..737d33f1c 100644 --- a/kmath-core/api/kmath-core.api +++ b/kmath-core/api/kmath-core.api @@ -1,17 +1,29 @@ public final class space/kscience/kmath/data/ColumnarDataKt { + public static final fun getIndices (Lspace/kscience/kmath/data/ColumnarData;)Lkotlin/ranges/IntRange; +} + +public final class space/kscience/kmath/data/XYColumnarData$Companion { } public final class space/kscience/kmath/data/XYColumnarDataKt { public static synthetic fun asXYData$default (Lspace/kscience/kmath/nd/Structure2D;IIILjava/lang/Object;)Lspace/kscience/kmath/data/XYColumnarData; } +public final class space/kscience/kmath/data/XYErrorColumnarData$Companion { + public final fun of (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/data/XYErrorColumnarData; +} + public abstract interface class space/kscience/kmath/domains/Domain { public abstract fun contains (Lspace/kscience/kmath/structures/Buffer;)Z public abstract fun getDimension ()I } +public final class space/kscience/kmath/domains/Domain1DKt { + public static final fun getCenter (Lspace/kscience/kmath/domains/Domain1D;)D +} + public abstract interface class space/kscience/kmath/expressions/AutoDiffProcessor { - public abstract fun process (Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/DifferentiableExpression; + public abstract fun differentiate (Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/DifferentiableExpression; } public class space/kscience/kmath/expressions/AutoDiffValue { @@ -35,6 +47,9 @@ public final class space/kscience/kmath/expressions/DifferentiableExpressionKt { public static final fun derivative (Lspace/kscience/kmath/expressions/DifferentiableExpression;Ljava/lang/String;)Lspace/kscience/kmath/expressions/Expression; public static final fun derivative (Lspace/kscience/kmath/expressions/DifferentiableExpression;Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; public static final fun derivative (Lspace/kscience/kmath/expressions/DifferentiableExpression;[Lspace/kscience/kmath/expressions/Symbol;)Lspace/kscience/kmath/expressions/Expression; + public static final fun derivative (Lspace/kscience/kmath/expressions/SpecialDifferentiableExpression;Ljava/lang/String;)Lspace/kscience/kmath/expressions/Expression; + public static final fun derivative (Lspace/kscience/kmath/expressions/SpecialDifferentiableExpression;Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; + public static final fun derivative (Lspace/kscience/kmath/expressions/SpecialDifferentiableExpression;[Lspace/kscience/kmath/expressions/Symbol;)Lspace/kscience/kmath/expressions/Expression; } public abstract interface class space/kscience/kmath/expressions/Expression { @@ -46,9 +61,9 @@ public abstract interface class space/kscience/kmath/expressions/ExpressionAlgeb } public final class space/kscience/kmath/expressions/ExpressionKt { - public static final fun binding (Lspace/kscience/kmath/expressions/ExpressionAlgebra;)Lkotlin/properties/ReadOnlyProperty; public static final fun callByString (Lspace/kscience/kmath/expressions/Expression;[Lkotlin/Pair;)Ljava/lang/Object; public static final fun callBySymbol (Lspace/kscience/kmath/expressions/Expression;[Lkotlin/Pair;)Ljava/lang/Object; + public static final fun getBinding (Lspace/kscience/kmath/expressions/ExpressionAlgebra;)Lkotlin/properties/ReadOnlyProperty; public static final fun invoke (Lspace/kscience/kmath/expressions/Expression;)Ljava/lang/Object; } @@ -70,10 +85,11 @@ public abstract class space/kscience/kmath/expressions/FunctionalExpressionAlgeb } public final class space/kscience/kmath/expressions/FunctionalExpressionAlgebraKt { + public static final fun expression (Lspace/kscience/kmath/operations/DoubleField;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; public static final fun expressionInExtendedField (Lspace/kscience/kmath/operations/ExtendedField;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; public static final fun expressionInField (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; + public static final fun expressionInGroup (Lspace/kscience/kmath/operations/Group;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; public static final fun expressionInRing (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; - public static final fun expressionInSpace (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/Expression; } public class space/kscience/kmath/expressions/FunctionalExpressionExtendedField : space/kscience/kmath/expressions/FunctionalExpressionField, space/kscience/kmath/operations/ExtendedField { @@ -85,8 +101,6 @@ public class space/kscience/kmath/expressions/FunctionalExpressionExtendedField public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; public fun atan (Lspace/kscience/kmath/expressions/Expression;)Lspace/kscience/kmath/expressions/Expression; public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; - public synthetic fun bindSymbol (Ljava/lang/String;)Ljava/lang/Object; - public fun bindSymbol (Ljava/lang/String;)Lspace/kscience/kmath/expressions/Expression; public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; public fun cos (Lspace/kscience/kmath/expressions/Expression;)Lspace/kscience/kmath/expressions/Expression; public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; @@ -189,7 +203,6 @@ public final class space/kscience/kmath/expressions/MST$Unary : space/kscience/k } public final class space/kscience/kmath/expressions/MSTKt { - public static final fun evaluate (Lspace/kscience/kmath/operations/Algebra;Lspace/kscience/kmath/expressions/MST;)Ljava/lang/Object; public static final fun interpret (Lspace/kscience/kmath/expressions/MST;Lspace/kscience/kmath/operations/Algebra;Ljava/util/Map;)Ljava/lang/Object; public static final fun interpret (Lspace/kscience/kmath/expressions/MST;Lspace/kscience/kmath/operations/Algebra;[Lkotlin/Pair;)Ljava/lang/Object; public static final fun toExpression (Lspace/kscience/kmath/expressions/MST;Lspace/kscience/kmath/operations/Algebra;)Lspace/kscience/kmath/expressions/Expression; @@ -255,7 +268,7 @@ public final class space/kscience/kmath/expressions/MstExtendedField : space/ksc public fun unaryPlus (Lspace/kscience/kmath/expressions/MST;)Lspace/kscience/kmath/expressions/MST$Unary; } -public final class space/kscience/kmath/expressions/MstField : space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOperations, space/kscience/kmath/operations/ScaleOperations { +public final class space/kscience/kmath/expressions/MstField : space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOps, space/kscience/kmath/operations/ScaleOperations { public static final field INSTANCE Lspace/kscience/kmath/expressions/MstField; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (Lspace/kscience/kmath/expressions/MST;Lspace/kscience/kmath/expressions/MST;)Lspace/kscience/kmath/expressions/MST$Binary; @@ -317,7 +330,7 @@ public final class space/kscience/kmath/expressions/MstNumericAlgebra : space/ks public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } -public final class space/kscience/kmath/expressions/MstRing : space/kscience/kmath/operations/NumbersAddOperations, space/kscience/kmath/operations/Ring, space/kscience/kmath/operations/ScaleOperations { +public final class space/kscience/kmath/expressions/MstRing : space/kscience/kmath/operations/NumbersAddOps, space/kscience/kmath/operations/Ring, space/kscience/kmath/operations/ScaleOperations { public static final field INSTANCE Lspace/kscience/kmath/expressions/MstRing; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (Lspace/kscience/kmath/expressions/MST;Lspace/kscience/kmath/expressions/MST;)Lspace/kscience/kmath/expressions/MST$Binary; @@ -365,8 +378,6 @@ public final class space/kscience/kmath/expressions/SimpleAutoDiffExtendedField public fun atan (Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; public fun atanh (Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; - public synthetic fun bindSymbol (Ljava/lang/String;)Ljava/lang/Object; - public fun bindSymbol (Ljava/lang/String;)Lspace/kscience/kmath/expressions/AutoDiffValue; public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; public fun cos (Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; @@ -395,7 +406,7 @@ public final class space/kscience/kmath/expressions/SimpleAutoDiffExtendedField public fun tanh (Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; } -public class space/kscience/kmath/expressions/SimpleAutoDiffField : space/kscience/kmath/expressions/ExpressionAlgebra, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOperations { +public class space/kscience/kmath/expressions/SimpleAutoDiffField : space/kscience/kmath/expressions/ExpressionAlgebra, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOps { public fun (Lspace/kscience/kmath/operations/Field;Ljava/util/Map;)V public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (Lspace/kscience/kmath/expressions/AutoDiffValue;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; @@ -403,7 +414,6 @@ public class space/kscience/kmath/expressions/SimpleAutoDiffField : space/kscien public fun bindSymbolOrNull (Ljava/lang/String;)Lspace/kscience/kmath/expressions/AutoDiffValue; public synthetic fun const (Ljava/lang/Object;)Ljava/lang/Object; public fun const (Ljava/lang/Object;)Lspace/kscience/kmath/expressions/AutoDiffValue; - public final fun const (Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/AutoDiffValue; public final fun derive (Ljava/lang/Object;Lkotlin/jvm/functions/Function2;)Ljava/lang/Object; public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun divide (Lspace/kscience/kmath/expressions/AutoDiffValue;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; @@ -431,6 +441,7 @@ public final class space/kscience/kmath/expressions/SimpleAutoDiffKt { public static final fun asinh (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public static final fun atan (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public static final fun atanh (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; + public static final fun const (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/expressions/AutoDiffValue; public static final fun cos (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public static final fun cosh (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; public static final fun exp (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; @@ -450,18 +461,13 @@ public final class space/kscience/kmath/expressions/SimpleAutoDiffKt { public static final fun tanh (Lspace/kscience/kmath/expressions/SimpleAutoDiffField;Lspace/kscience/kmath/expressions/AutoDiffValue;)Lspace/kscience/kmath/expressions/AutoDiffValue; } -public final class space/kscience/kmath/expressions/StringSymbol : space/kscience/kmath/expressions/Symbol { - public static final synthetic fun box-impl (Ljava/lang/String;)Lspace/kscience/kmath/expressions/StringSymbol; - public static fun constructor-impl (Ljava/lang/String;)Ljava/lang/String; - public fun equals (Ljava/lang/Object;)Z - public static fun equals-impl (Ljava/lang/String;Ljava/lang/Object;)Z - public static final fun equals-impl0 (Ljava/lang/String;Ljava/lang/String;)Z - public fun getIdentity ()Ljava/lang/String; - public fun hashCode ()I - public static fun hashCode-impl (Ljava/lang/String;)I - public fun toString ()Ljava/lang/String; - public static fun toString-impl (Ljava/lang/String;)Ljava/lang/String; - public final synthetic fun unbox-impl ()Ljava/lang/String; +public abstract interface class space/kscience/kmath/expressions/SpecialDifferentiableExpression : space/kscience/kmath/expressions/DifferentiableExpression { + public abstract fun derivativeOrNull (Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; +} + +public final class space/kscience/kmath/expressions/SpecialExpressionsKt { + public static final fun chiSquaredExpression (Lspace/kscience/kmath/expressions/AutoDiffProcessor;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/expressions/DifferentiableExpression; + public static final fun genericChiSquaredExpression (Lspace/kscience/kmath/expressions/AutoDiffProcessor;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/expressions/DifferentiableExpression; } public abstract interface class space/kscience/kmath/expressions/Symbol : space/kscience/kmath/expressions/MST { @@ -470,15 +476,19 @@ public abstract interface class space/kscience/kmath/expressions/Symbol : space/ } public final class space/kscience/kmath/expressions/Symbol$Companion { - public final fun getX-uKgCeAI ()Ljava/lang/String; - public final fun getY-uKgCeAI ()Ljava/lang/String; - public final fun getZ-uKgCeAI ()Ljava/lang/String; + public final fun getX ()Lspace/kscience/kmath/expressions/Symbol; + public final fun getXError ()Lspace/kscience/kmath/expressions/Symbol; + public final fun getY ()Lspace/kscience/kmath/expressions/Symbol; + public final fun getYError ()Lspace/kscience/kmath/expressions/Symbol; + public final fun getZ ()Lspace/kscience/kmath/expressions/Symbol; + public final fun getZError ()Lspace/kscience/kmath/expressions/Symbol; } public final class space/kscience/kmath/expressions/SymbolIndexerKt { } public final class space/kscience/kmath/expressions/SymbolKt { + public static final fun Symbol (Ljava/lang/String;)Lspace/kscience/kmath/expressions/Symbol; public static final fun get (Ljava/util/Map;Ljava/lang/String;)Ljava/lang/Object; public static final fun get (Ljava/util/Map;Lspace/kscience/kmath/expressions/Symbol;)Ljava/lang/Object; public static final fun getSymbol ()Lkotlin/properties/ReadOnlyProperty; @@ -487,7 +497,7 @@ public final class space/kscience/kmath/expressions/SymbolKt { } public final class space/kscience/kmath/linear/BufferedLinearSpace : space/kscience/kmath/linear/LinearSpace { - public fun (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;)V + public fun (Lspace/kscience/kmath/operations/BufferAlgebra;)V public fun buildMatrix (IILkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/Structure2D; public fun buildVector (ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/structures/Buffer; public fun dot (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; @@ -499,6 +509,10 @@ public final class space/kscience/kmath/linear/BufferedLinearSpace : space/kscie public fun unaryMinus (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; } +public final class space/kscience/kmath/linear/BufferedLinearSpaceKt { + public static final fun linearSpace (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/linear/BufferedLinearSpace; +} + public abstract interface class space/kscience/kmath/linear/CholeskyDecompositionFeature : space/kscience/kmath/linear/MatrixFeature { public abstract fun getL ()Lspace/kscience/kmath/nd/Structure2D; } @@ -514,6 +528,36 @@ public abstract interface class space/kscience/kmath/linear/DiagonalFeature : sp public final class space/kscience/kmath/linear/DiagonalFeature$Companion : space/kscience/kmath/linear/DiagonalFeature { } +public final class space/kscience/kmath/linear/DoubleLinearSpace : space/kscience/kmath/linear/LinearSpace { + public static final field INSTANCE Lspace/kscience/kmath/linear/DoubleLinearSpace; + public fun buildMatrix (IILkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun buildVector (ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/structures/Buffer; + public fun buildVector-CZ9oacQ (ILkotlin/jvm/functions/Function2;)[D + public final fun div-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;D)[D + public fun dot (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun dot (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun dot-CZ9oacQ (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/structures/Buffer;)[D + public fun getElementAlgebra ()Lspace/kscience/kmath/operations/DoubleField; + public synthetic fun getElementAlgebra ()Lspace/kscience/kmath/operations/Ring; + public fun minus (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun minus (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun minus-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public fun plus (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun plus (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun plus-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun times (Ljava/lang/Object;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun times (Lspace/kscience/kmath/nd/Structure2D;D)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun times (Lspace/kscience/kmath/nd/Structure2D;Ljava/lang/Object;)Lspace/kscience/kmath/nd/Structure2D; + public synthetic fun times (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;)Lspace/kscience/kmath/structures/Buffer; + public fun times-CZ9oacQ (DLspace/kscience/kmath/structures/Buffer;)[D + public fun times-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;D)[D + public fun unaryMinus (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; +} + +public final class space/kscience/kmath/linear/DoubleLinearSpaceKt { + public static final fun getLinearSpace (Lspace/kscience/kmath/operations/DoubleField;)Lspace/kscience/kmath/linear/DoubleLinearSpace; +} + public abstract interface class space/kscience/kmath/linear/InverseMatrixFeature : space/kscience/kmath/linear/MatrixFeature { public abstract fun getInverse ()Lspace/kscience/kmath/nd/Structure2D; } @@ -533,11 +577,6 @@ public abstract interface class space/kscience/kmath/linear/LinearSolver { public fun solve (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; } -public final class space/kscience/kmath/linear/LinearSolverKt { - public static final fun asMatrix (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/linear/VirtualMatrix; - public static final fun asVector (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/structures/Buffer; -} - public abstract interface class space/kscience/kmath/linear/LinearSpace { public static final field Companion Lspace/kscience/kmath/linear/LinearSpace$Companion; public abstract fun buildMatrix (IILkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/Structure2D; @@ -560,10 +599,12 @@ public abstract interface class space/kscience/kmath/linear/LinearSpace { public final class space/kscience/kmath/linear/LinearSpace$Companion { public final fun buffered (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/linear/LinearSpace; public static synthetic fun buffered$default (Lspace/kscience/kmath/linear/LinearSpace$Companion;Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;ILjava/lang/Object;)Lspace/kscience/kmath/linear/LinearSpace; - public final fun getReal ()Lspace/kscience/kmath/linear/LinearSpace; + public final fun getDouble ()Lspace/kscience/kmath/linear/LinearSpace; } public final class space/kscience/kmath/linear/LinearSpaceKt { + public static final fun asMatrix (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/linear/VirtualMatrix; + public static final fun asVector (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/structures/Buffer; public static final fun invoke (Lspace/kscience/kmath/linear/LinearSpace;Lkotlin/jvm/functions/Function1;)Ljava/lang/Object; } @@ -587,11 +628,12 @@ public abstract interface class space/kscience/kmath/linear/LupDecompositionFeat public final class space/kscience/kmath/linear/LupDecompositionKt { public static final fun abs (Lspace/kscience/kmath/linear/LinearSpace;Ljava/lang/Comparable;)Ljava/lang/Comparable; - public static final fun inverseWithLup (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; public static final fun lup (Lspace/kscience/kmath/linear/LinearSpace;Lkotlin/jvm/functions/Function2;Lspace/kscience/kmath/nd/Structure2D;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/linear/LupDecomposition; - public static final fun lup (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/linear/LupDecomposition; - public static final fun solveWithLup (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; - public static final fun solveWithLup (Lspace/kscience/kmath/linear/LupDecomposition;Lkotlin/jvm/functions/Function2;Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; + public static final fun lup (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/Structure2D;D)Lspace/kscience/kmath/linear/LupDecomposition; + public static synthetic fun lup$default (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/Structure2D;DILjava/lang/Object;)Lspace/kscience/kmath/linear/LupDecomposition; + public static final fun lupSolver (Lspace/kscience/kmath/linear/LinearSpace;D)Lspace/kscience/kmath/linear/LinearSolver; + public static final fun lupSolver (Lspace/kscience/kmath/linear/LinearSpace;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/linear/LinearSolver; + public static synthetic fun lupSolver$default (Lspace/kscience/kmath/linear/LinearSpace;DILjava/lang/Object;)Lspace/kscience/kmath/linear/LinearSolver; } public final class space/kscience/kmath/linear/MatrixBuilder { @@ -607,6 +649,7 @@ public final class space/kscience/kmath/linear/MatrixBuilderKt { public static final fun column (Lspace/kscience/kmath/linear/LinearSpace;[Ljava/lang/Object;)Lspace/kscience/kmath/nd/Structure2D; public static final fun row (Lspace/kscience/kmath/linear/LinearSpace;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/Structure2D; public static final fun row (Lspace/kscience/kmath/linear/LinearSpace;[Ljava/lang/Object;)Lspace/kscience/kmath/nd/Structure2D; + public static final fun symmetric (Lspace/kscience/kmath/linear/MatrixBuilder;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/Structure2D; } public abstract interface class space/kscience/kmath/linear/MatrixFeature : space/kscience/kmath/nd/StructureFeature { @@ -623,7 +666,10 @@ public final class space/kscience/kmath/linear/MatrixWrapper : space/kscience/km public fun getColNum ()I public fun getColumns ()Ljava/util/List; public fun getDimension ()I - public final fun getFeatures ()Ljava/util/Set; + public synthetic fun getFeature (Lkotlin/reflect/KClass;)Ljava/lang/Object; + public fun getFeature (Lkotlin/reflect/KClass;)Lspace/kscience/kmath/nd/StructureFeature; + public final fun getFeatures-En6fw3w ()Ljava/util/Map; + public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; public final fun getOrigin ()Lspace/kscience/kmath/nd/Structure2D; public fun getRowNum ()I public fun getRows ()Ljava/util/List; @@ -634,9 +680,10 @@ public final class space/kscience/kmath/linear/MatrixWrapper : space/kscience/km public final class space/kscience/kmath/linear/MatrixWrapperKt { public static final fun getOrigin (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; public static final fun one (Lspace/kscience/kmath/linear/LinearSpace;II)Lspace/kscience/kmath/nd/Structure2D; - public static final fun plus (Lspace/kscience/kmath/nd/Structure2D;Ljava/util/Collection;)Lspace/kscience/kmath/linear/MatrixWrapper; public static final fun plus (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/linear/MatrixFeature;)Lspace/kscience/kmath/linear/MatrixWrapper; public static final fun transpose (Lspace/kscience/kmath/nd/Structure2D;)Lspace/kscience/kmath/nd/Structure2D; + public static final fun withFeature (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/linear/MatrixFeature;)Lspace/kscience/kmath/linear/MatrixWrapper; + public static final fun withFeatures (Lspace/kscience/kmath/nd/Structure2D;Ljava/lang/Iterable;)Lspace/kscience/kmath/linear/MatrixWrapper; public static final fun zero (Lspace/kscience/kmath/linear/LinearSpace;II)Lspace/kscience/kmath/nd/Structure2D; } @@ -656,6 +703,10 @@ public abstract interface class space/kscience/kmath/linear/SingularValueDecompo public abstract fun getV ()Lspace/kscience/kmath/nd/Structure2D; } +public final class space/kscience/kmath/linear/SymmetricMatrixFeature : space/kscience/kmath/linear/MatrixFeature { + public static final field INSTANCE Lspace/kscience/kmath/linear/SymmetricMatrixFeature; +} + public final class space/kscience/kmath/linear/TransposedFeature : space/kscience/kmath/linear/MatrixFeature { public fun (Lspace/kscience/kmath/nd/Structure2D;)V public final fun getOriginal ()Lspace/kscience/kmath/nd/Structure2D; @@ -678,6 +729,10 @@ public final class space/kscience/kmath/linear/VirtualMatrix : space/kscience/km public fun getShape ()[I } +public final class space/kscience/kmath/linear/VirtualMatrixKt { + public static final fun virtual (Lspace/kscience/kmath/linear/MatrixBuilder;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/linear/VirtualMatrix; +} + public final class space/kscience/kmath/linear/ZeroFeature : space/kscience/kmath/linear/DiagonalFeature { public static final field INSTANCE Lspace/kscience/kmath/linear/ZeroFeature; } @@ -701,82 +756,164 @@ public final class space/kscience/kmath/misc/CumulativeKt { public static final fun cumulativeSumOfLong (Lkotlin/sequences/Sequence;)Lkotlin/sequences/Sequence; } +public abstract interface class space/kscience/kmath/misc/Feature { + public fun getKey ()Lkotlin/reflect/KClass; +} + +public final class space/kscience/kmath/misc/FeatureSet : space/kscience/kmath/misc/Featured { + public static final field Companion Lspace/kscience/kmath/misc/FeatureSet$Companion; + public static final synthetic fun box-impl (Ljava/util/Map;)Lspace/kscience/kmath/misc/FeatureSet; + public fun equals (Ljava/lang/Object;)Z + public static fun equals-impl (Ljava/util/Map;Ljava/lang/Object;)Z + public static final fun equals-impl0 (Ljava/util/Map;Ljava/util/Map;)Z + public synthetic fun getFeature (Lkotlin/reflect/KClass;)Ljava/lang/Object; + public fun getFeature (Lkotlin/reflect/KClass;)Lspace/kscience/kmath/misc/Feature; + public static fun getFeature-impl (Ljava/util/Map;Lkotlin/reflect/KClass;)Lspace/kscience/kmath/misc/Feature; + public final fun getFeatures ()Ljava/util/Map; + public fun hashCode ()I + public static fun hashCode-impl (Ljava/util/Map;)I + public static final fun iterator-impl (Ljava/util/Map;)Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; + public static fun toString-impl (Ljava/util/Map;)Ljava/lang/String; + public final synthetic fun unbox-impl ()Ljava/util/Map; + public static final fun with-JVE9-Rk (Ljava/util/Map;Ljava/lang/Iterable;)Ljava/util/Map; + public static final fun with-JVE9-Rk (Ljava/util/Map;[Lspace/kscience/kmath/misc/Feature;)Ljava/util/Map; + public static final fun with-YU1a0hQ (Ljava/util/Map;Ljava/util/Map;)Ljava/util/Map; + public static final fun with-h58Sd8I (Ljava/util/Map;Lspace/kscience/kmath/misc/Feature;Lkotlin/reflect/KClass;)Ljava/util/Map; + public static synthetic fun with-h58Sd8I$default (Ljava/util/Map;Lspace/kscience/kmath/misc/Feature;Lkotlin/reflect/KClass;ILjava/lang/Object;)Ljava/util/Map; +} + +public final class space/kscience/kmath/misc/FeatureSet$Companion { + public final fun of-JVE9-Rk (Ljava/lang/Iterable;)Ljava/util/Map; + public final fun of-JVE9-Rk ([Lspace/kscience/kmath/misc/Feature;)Ljava/util/Map; +} + +public abstract interface class space/kscience/kmath/misc/Featured { + public abstract fun getFeature (Lkotlin/reflect/KClass;)Ljava/lang/Object; +} + +public abstract interface class space/kscience/kmath/misc/Loggable { + public static final field Companion Lspace/kscience/kmath/misc/Loggable$Companion; + public static final field INFO Ljava/lang/String; + public abstract fun log (Ljava/lang/String;Lkotlin/jvm/functions/Function0;)V +} + +public final class space/kscience/kmath/misc/Loggable$Companion { + public static final field INFO Ljava/lang/String; + public final fun getConsole ()Lspace/kscience/kmath/misc/Loggable; +} + +public final class space/kscience/kmath/misc/LoggingKt { + public static final fun log (Lspace/kscience/kmath/misc/Loggable;Lkotlin/jvm/functions/Function0;)V +} + +public final class space/kscience/kmath/misc/NumbersJVMKt { + public static final fun toIntExact (J)I +} + public abstract interface annotation class space/kscience/kmath/misc/PerformancePitfall : java/lang/annotation/Annotation { + public abstract fun message ()Ljava/lang/String; +} + +public final class space/kscience/kmath/misc/SortingKt { + public static final fun requireSorted (Lspace/kscience/kmath/structures/Buffer;)V + public static final fun sorted (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun sortedBy (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun sortedByDescending (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun sortedDescending (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; } public abstract interface annotation class space/kscience/kmath/misc/UnstableKMathAPI : java/lang/annotation/Annotation { } -public abstract interface class space/kscience/kmath/nd/AlgebraND { +public abstract interface class space/kscience/kmath/nd/AlgebraND : space/kscience/kmath/operations/Algebra { public static final field Companion Lspace/kscience/kmath/nd/AlgebraND$Companion; - public abstract fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public abstract fun getElementContext ()Lspace/kscience/kmath/operations/Algebra; - public abstract fun getShape ()[I + public abstract fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; public fun invoke (Lkotlin/jvm/functions/Function1;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; - public abstract fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; - public abstract fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public abstract fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; + public abstract fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; } public final class space/kscience/kmath/nd/AlgebraND$Companion { } +public final class space/kscience/kmath/nd/AlgebraNDExtentionsKt { + public static final fun one (Lspace/kscience/kmath/nd/AlgebraND;[I)Lspace/kscience/kmath/nd/StructureND; + public static final fun oneVarArg (Lspace/kscience/kmath/nd/AlgebraND;I[I)Lspace/kscience/kmath/nd/StructureND; + public static final fun structureND (Lspace/kscience/kmath/nd/AlgebraND;I[ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public static final fun zero (Lspace/kscience/kmath/nd/AlgebraND;[I)Lspace/kscience/kmath/nd/StructureND; + public static final fun zeroVarArg (Lspace/kscience/kmath/nd/AlgebraND;I[I)Lspace/kscience/kmath/nd/StructureND; +} + +public final class space/kscience/kmath/nd/AlgebraNDKt { + public static final fun Shape (I[I)[I +} + public abstract interface class space/kscience/kmath/nd/BufferAlgebraND : space/kscience/kmath/nd/AlgebraND { - public fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public fun getBuffer (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/structures/Buffer; - public abstract fun getBufferFactory ()Lkotlin/jvm/functions/Function2; - public abstract fun getStrides ()Lspace/kscience/kmath/nd/Strides; + public static final field Companion Lspace/kscience/kmath/nd/BufferAlgebraND$Companion; + public abstract fun getBufferAlgebra ()Lspace/kscience/kmath/operations/BufferAlgebra; + public fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public abstract fun getIndexerBuilder ()Lkotlin/jvm/functions/Function1; public fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; public synthetic fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; public fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; public synthetic fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public synthetic fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun toBufferND (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; + public synthetic fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; +} + +public final class space/kscience/kmath/nd/BufferAlgebraND$Companion { + public final fun getDefaultIndexerBuilder ()Lkotlin/jvm/functions/Function1; } public final class space/kscience/kmath/nd/BufferAlgebraNDKt { - public static final fun field (Lspace/kscience/kmath/nd/AlgebraND$Companion;Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;[I)Lspace/kscience/kmath/nd/BufferedFieldND; - public static final fun group (Lspace/kscience/kmath/nd/AlgebraND$Companion;Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;[I)Lspace/kscience/kmath/nd/BufferedGroupND; - public static final fun ndField (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun ndGroup (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun ndRing (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun ring (Lspace/kscience/kmath/nd/AlgebraND$Companion;Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;[I)Lspace/kscience/kmath/nd/BufferedRingND; + public static final fun getNd (Lspace/kscience/kmath/operations/BufferAlgebra;)Lspace/kscience/kmath/nd/BufferedFieldOpsND; + public static final fun getNd (Lspace/kscience/kmath/operations/BufferAlgebra;)Lspace/kscience/kmath/nd/BufferedGroupNDOps; + public static final fun getNd (Lspace/kscience/kmath/operations/BufferAlgebra;)Lspace/kscience/kmath/nd/BufferedRingOpsND; + public static final fun mapInline (Lspace/kscience/kmath/nd/BufferAlgebraND;Lspace/kscience/kmath/nd/BufferND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public static final fun structureND (Lspace/kscience/kmath/nd/BufferAlgebraND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public static final fun structureND (Lspace/kscience/kmath/nd/BufferAlgebraND;[ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; } public class space/kscience/kmath/nd/BufferND : space/kscience/kmath/nd/StructureND { - public fun (Lspace/kscience/kmath/nd/Strides;Lspace/kscience/kmath/structures/Buffer;)V - public fun elements ()Lkotlin/sequences/Sequence; + public fun (Lspace/kscience/kmath/nd/ShapeIndexer;Lspace/kscience/kmath/structures/Buffer;)V public fun get ([I)Ljava/lang/Object; - public final fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; public fun getShape ()[I - public final fun getStrides ()Lspace/kscience/kmath/nd/Strides; public fun toString ()Ljava/lang/String; } -public class space/kscience/kmath/nd/BufferedFieldND : space/kscience/kmath/nd/BufferedRingND, space/kscience/kmath/nd/FieldND { - public fun ([ILspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;)V +public final class space/kscience/kmath/nd/BufferNDKt { + public static final fun mapToBuffer (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; +} + +public class space/kscience/kmath/nd/BufferedFieldOpsND : space/kscience/kmath/nd/BufferedRingOpsND, space/kscience/kmath/nd/FieldOpsND { + public fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; public fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; } -public class space/kscience/kmath/nd/BufferedGroupND : space/kscience/kmath/nd/BufferAlgebraND, space/kscience/kmath/nd/GroupND { - public fun ([ILspace/kscience/kmath/operations/Group;Lkotlin/jvm/functions/Function2;)V - public final fun getBufferFactory ()Lkotlin/jvm/functions/Function2; - public synthetic fun getElementContext ()Lspace/kscience/kmath/operations/Algebra; - public final fun getElementContext ()Lspace/kscience/kmath/operations/Group; - public final fun getShape ()[I - public fun getStrides ()Lspace/kscience/kmath/nd/Strides; - public synthetic fun getZero ()Ljava/lang/Object; - public fun getZero ()Lspace/kscience/kmath/nd/BufferND; +public class space/kscience/kmath/nd/BufferedGroupNDOps : space/kscience/kmath/nd/BufferAlgebraND, space/kscience/kmath/nd/GroupOpsND { + public fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun getBufferAlgebra ()Lspace/kscience/kmath/operations/BufferAlgebra; + public fun getIndexerBuilder ()Lkotlin/jvm/functions/Function1; public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; public fun unaryMinus (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; } -public class space/kscience/kmath/nd/BufferedRingND : space/kscience/kmath/nd/BufferedGroupND, space/kscience/kmath/nd/RingND { - public fun ([ILspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;)V - public synthetic fun getOne ()Ljava/lang/Object; - public fun getOne ()Lspace/kscience/kmath/nd/BufferND; +public class space/kscience/kmath/nd/BufferedRingOpsND : space/kscience/kmath/nd/BufferedGroupNDOps, space/kscience/kmath/nd/RingOpsND { + public fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V } public final class space/kscience/kmath/nd/DefaultStrides : space/kscience/kmath/nd/Strides { @@ -794,72 +931,151 @@ public final class space/kscience/kmath/nd/DefaultStrides$Companion { public final fun invoke ([I)Lspace/kscience/kmath/nd/Strides; } -public final class space/kscience/kmath/nd/DoubleFieldND : space/kscience/kmath/nd/BufferedFieldND, space/kscience/kmath/operations/ExtendedField, space/kscience/kmath/operations/NumbersAddOperations, space/kscience/kmath/operations/ScaleOperations { +public final class space/kscience/kmath/nd/DoubleBufferND : space/kscience/kmath/nd/BufferND { + public synthetic fun (Lspace/kscience/kmath/nd/ShapeIndexer;[DLkotlin/jvm/internal/DefaultConstructorMarker;)V + public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public fun getBuffer-Dv3HvWU ()[D +} + +public final class space/kscience/kmath/nd/DoubleFieldND : space/kscience/kmath/nd/DoubleFieldOpsND, space/kscience/kmath/nd/FieldND, space/kscience/kmath/operations/ExtendedField, space/kscience/kmath/operations/NumbersAddOps { public fun ([I)V - public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; - public fun acos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun acosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; - public fun asin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun acosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun asinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; - public fun atan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun asinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun atanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; - public fun cos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun atanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun cosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; - public fun exp (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun getBuffer (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/structures/Buffer; - public fun getBuffer-Udx-57Q (Lspace/kscience/kmath/nd/StructureND;)[D - public synthetic fun getOne ()Ljava/lang/Object; - public fun getOne ()Lspace/kscience/kmath/nd/BufferND; - public synthetic fun getZero ()Ljava/lang/Object; - public fun getZero ()Lspace/kscience/kmath/nd/BufferND; - public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; - public fun ln (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; - public fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; + public fun cosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun getShape ()[I public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; - public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/nd/BufferND; + public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun power (Ljava/lang/Object;I)Ljava/lang/Object; public synthetic fun power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; - public fun power (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/nd/BufferND; - public fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; - public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; - public fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; - public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; - public fun sin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun power (Lspace/kscience/kmath/nd/StructureND;I)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun power (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun power-Qn1smSk (Ljava/lang/Object;I)Ljava/lang/Object; + public fun power-Qn1smSk (Lspace/kscience/kmath/nd/StructureND;I)Lspace/kscience/kmath/nd/DoubleBufferND; public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun sinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; - public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; - public fun tan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun sinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun tanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun tanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; } public final class space/kscience/kmath/nd/DoubleFieldNDKt { - public static final fun nd (Lspace/kscience/kmath/operations/DoubleField;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun real (Lspace/kscience/kmath/nd/AlgebraND$Companion;[I)Lspace/kscience/kmath/nd/DoubleFieldND; + public static final fun getNdAlgebra (Lspace/kscience/kmath/operations/DoubleField;)Lspace/kscience/kmath/nd/DoubleFieldOpsND; + public static final fun ndAlgebra (Lspace/kscience/kmath/operations/DoubleField;[I)Lspace/kscience/kmath/nd/DoubleFieldND; } -public abstract interface class space/kscience/kmath/nd/FieldND : space/kscience/kmath/nd/RingND, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/ScaleOperations { +public abstract class space/kscience/kmath/nd/DoubleFieldOpsND : space/kscience/kmath/nd/BufferedFieldOpsND, space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/ScaleOperations { + public static final field Companion Lspace/kscience/kmath/nd/DoubleFieldOpsND$Companion; + public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; + public fun acos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun acosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun add (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun add (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; + public fun asin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun asinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; + public fun atan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun atanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; + public fun cos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun cosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun div (DLspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun div (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; + public synthetic fun div (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public synthetic fun div (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public fun div (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun div (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun div (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; + public fun div (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun divide (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun divide (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; + public fun exp (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; + public fun ln (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public synthetic fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + protected final fun mapInline (Lspace/kscience/kmath/nd/DoubleBufferND;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun minus (DLspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun minus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public synthetic fun minus (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public fun minus (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun minus (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; + public fun minus (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun multiply (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun multiply (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public fun plus (DLspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun plus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public synthetic fun plus (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public fun plus (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun plus (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; + public fun plus (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; + public fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; + public fun sin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; + public fun tan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun tanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun times (Ljava/lang/Number;Ljava/lang/Object;)Ljava/lang/Object; + public fun times (Ljava/lang/Number;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun times (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; + public synthetic fun times (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun times (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun times (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun toBufferND (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/BufferND; + public fun toBufferND (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryMinus (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun unaryMinus (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun unaryPlus (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryPlus (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/DoubleBufferND; + public fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/BufferND; + public synthetic fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; +} + +public final class space/kscience/kmath/nd/DoubleFieldOpsND$Companion : space/kscience/kmath/nd/DoubleFieldOpsND { +} + +public abstract interface class space/kscience/kmath/nd/FieldND : space/kscience/kmath/nd/FieldOpsND, space/kscience/kmath/nd/RingND, space/kscience/kmath/nd/WithShape, space/kscience/kmath/operations/Field { + public synthetic fun getOne ()Ljava/lang/Object; + public fun getOne ()Lspace/kscience/kmath/nd/StructureND; +} + +public abstract interface class space/kscience/kmath/nd/FieldOpsND : space/kscience/kmath/nd/RingOpsND, space/kscience/kmath/operations/FieldOps, space/kscience/kmath/operations/ScaleOperations { public fun div (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; public fun div (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun divide (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; + public fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; } -public abstract interface class space/kscience/kmath/nd/GroupND : space/kscience/kmath/nd/AlgebraND, space/kscience/kmath/operations/Group { - public static final field Companion Lspace/kscience/kmath/nd/GroupND$Companion; +public abstract interface class space/kscience/kmath/nd/GroupND : space/kscience/kmath/nd/GroupOpsND, space/kscience/kmath/nd/WithShape, space/kscience/kmath/operations/Group { + public synthetic fun getZero ()Ljava/lang/Object; + public fun getZero ()Lspace/kscience/kmath/nd/StructureND; +} + +public abstract interface class space/kscience/kmath/nd/GroupOpsND : space/kscience/kmath/nd/AlgebraND, space/kscience/kmath/operations/GroupOps { + public static final field Companion Lspace/kscience/kmath/nd/GroupOpsND$Companion; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; public fun minus (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; @@ -868,12 +1084,13 @@ public abstract interface class space/kscience/kmath/nd/GroupND : space/kscience public fun plus (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; } -public final class space/kscience/kmath/nd/GroupND$Companion { +public final class space/kscience/kmath/nd/GroupOpsND$Companion { } public final class space/kscience/kmath/nd/MutableBufferND : space/kscience/kmath/nd/BufferND, space/kscience/kmath/nd/MutableStructureND { - public fun (Lspace/kscience/kmath/nd/Strides;Lspace/kscience/kmath/structures/MutableBuffer;)V - public final fun getMutableBuffer ()Lspace/kscience/kmath/structures/MutableBuffer; + public fun (Lspace/kscience/kmath/nd/ShapeIndexer;Lspace/kscience/kmath/structures/MutableBuffer;)V + public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public fun getBuffer ()Lspace/kscience/kmath/structures/MutableBuffer; public fun set ([ILjava/lang/Object;)V } @@ -891,15 +1108,31 @@ public abstract interface class space/kscience/kmath/nd/MutableStructureND : spa public abstract fun set ([ILjava/lang/Object;)V } -public abstract interface class space/kscience/kmath/nd/RingND : space/kscience/kmath/nd/GroupND, space/kscience/kmath/operations/Ring { - public static final field Companion Lspace/kscience/kmath/nd/RingND$Companion; +public abstract interface class space/kscience/kmath/nd/RingND : space/kscience/kmath/nd/GroupND, space/kscience/kmath/nd/RingOpsND, space/kscience/kmath/nd/WithShape, space/kscience/kmath/operations/Ring { + public synthetic fun getOne ()Ljava/lang/Object; + public fun getOne ()Lspace/kscience/kmath/nd/StructureND; +} + +public abstract interface class space/kscience/kmath/nd/RingOpsND : space/kscience/kmath/nd/GroupOpsND, space/kscience/kmath/operations/RingOps { + public static final field Companion Lspace/kscience/kmath/nd/RingOpsND$Companion; public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun multiply (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; public fun times (Ljava/lang/Object;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; public fun times (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; } -public final class space/kscience/kmath/nd/RingND$Companion { +public final class space/kscience/kmath/nd/RingOpsND$Companion { +} + +public abstract interface class space/kscience/kmath/nd/ShapeIndexer : java/lang/Iterable, kotlin/jvm/internal/markers/KMappedMarker { + public abstract fun asSequence ()Lkotlin/sequences/Sequence; + public abstract fun equals (Ljava/lang/Object;)Z + public abstract fun getLinearSize ()I + public abstract fun getShape ()[I + public abstract fun hashCode ()I + public abstract fun index (I)[I + public fun iterator ()Ljava/util/Iterator; + public abstract fun offset ([I)I } public final class space/kscience/kmath/nd/ShapeMismatchException : java/lang/RuntimeException { @@ -908,27 +1141,28 @@ public final class space/kscience/kmath/nd/ShapeMismatchException : java/lang/Ru public final fun getExpected ()[I } -public final class space/kscience/kmath/nd/ShortRingND : space/kscience/kmath/nd/BufferedRingND, space/kscience/kmath/operations/NumbersAddOperations { +public final class space/kscience/kmath/nd/ShortRingND : space/kscience/kmath/nd/ShortRingOpsND, space/kscience/kmath/nd/RingND, space/kscience/kmath/operations/NumbersAddOps { public fun ([I)V - public synthetic fun getOne ()Ljava/lang/Object; - public fun getOne ()Lspace/kscience/kmath/nd/BufferND; - public synthetic fun getZero ()Ljava/lang/Object; - public fun getZero ()Lspace/kscience/kmath/nd/BufferND; + public fun getShape ()[I public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/nd/BufferND; } public final class space/kscience/kmath/nd/ShortRingNDKt { - public static final fun nd (Lspace/kscience/kmath/operations/ShortRing;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun produceInline (Lspace/kscience/kmath/nd/BufferedRingND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public static final fun withNdAlgebra (Lspace/kscience/kmath/operations/ShortRing;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; } -public abstract interface class space/kscience/kmath/nd/Strides { - public abstract fun getLinearSize ()I - public abstract fun getShape ()[I +public abstract class space/kscience/kmath/nd/ShortRingOpsND : space/kscience/kmath/nd/BufferedRingOpsND { + public static final field Companion Lspace/kscience/kmath/nd/ShortRingOpsND$Companion; +} + +public final class space/kscience/kmath/nd/ShortRingOpsND$Companion : space/kscience/kmath/nd/ShortRingOpsND { +} + +public abstract class space/kscience/kmath/nd/Strides : space/kscience/kmath/nd/ShapeIndexer { + public fun ()V + public fun asSequence ()Lkotlin/sequences/Sequence; public abstract fun getStrides ()[I - public abstract fun index (I)[I - public fun indices ()Lkotlin/sequences/Sequence; public fun offset ([I)I } @@ -968,14 +1202,16 @@ public final class space/kscience/kmath/nd/Structure2DKt { public static final fun as2D (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/Structure2D; } -public abstract interface class space/kscience/kmath/nd/StructureFeature { +public abstract interface class space/kscience/kmath/nd/StructureFeature : space/kscience/kmath/misc/Feature { } -public abstract interface class space/kscience/kmath/nd/StructureND { +public abstract interface class space/kscience/kmath/nd/StructureND : space/kscience/kmath/misc/Featured, space/kscience/kmath/nd/WithShape { public static final field Companion Lspace/kscience/kmath/nd/StructureND$Companion; - public abstract fun elements ()Lkotlin/sequences/Sequence; + public fun elements ()Lkotlin/sequences/Sequence; public abstract fun get ([I)Ljava/lang/Object; public fun getDimension ()I + public synthetic fun getFeature (Lkotlin/reflect/KClass;)Ljava/lang/Object; + public fun getFeature (Lkotlin/reflect/KClass;)Lspace/kscience/kmath/nd/StructureFeature; public abstract fun getShape ()[I } @@ -987,14 +1223,25 @@ public final class space/kscience/kmath/nd/StructureND$Companion { public static synthetic fun buffered$default (Lspace/kscience/kmath/nd/StructureND$Companion;Lspace/kscience/kmath/nd/Strides;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/BufferND; public static synthetic fun buffered$default (Lspace/kscience/kmath/nd/StructureND$Companion;[ILkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/BufferND; public final fun contentEquals (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Z + public final fun contentEquals (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;D)Z + public static synthetic fun contentEquals$default (Lspace/kscience/kmath/nd/StructureND$Companion;Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;DILjava/lang/Object;)Z public final fun toString (Lspace/kscience/kmath/nd/StructureND;)Ljava/lang/String; } public final class space/kscience/kmath/nd/StructureNDKt { + public static final fun contentEquals (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Z + public static final fun contentEquals (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Comparable;)Z + public static final fun contentEquals (Lspace/kscience/kmath/nd/AlgebraND;Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Z + public static final fun contentEquals (Lspace/kscience/kmath/nd/GroupOpsND;Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Comparable;)Z public static final fun get (Lspace/kscience/kmath/nd/StructureND;[I)Ljava/lang/Object; public static final fun mapInPlace (Lspace/kscience/kmath/nd/MutableStructureND;Lkotlin/jvm/functions/Function2;)V } +public abstract interface class space/kscience/kmath/nd/WithShape { + public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; + public abstract fun getShape ()[I +} + public abstract interface class space/kscience/kmath/operations/Algebra { public fun binaryOperation (Ljava/lang/String;Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; @@ -1004,21 +1251,16 @@ public abstract interface class space/kscience/kmath/operations/Algebra { public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } -public final class space/kscience/kmath/operations/AlgebraElementsKt { -} - public final class space/kscience/kmath/operations/AlgebraExtensionsKt { - public static final fun abs (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Comparable;)Ljava/lang/Comparable; - public static final fun average (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Iterable;)Ljava/lang/Object; - public static final fun average (Lspace/kscience/kmath/operations/Ring;Lkotlin/sequences/Sequence;)Ljava/lang/Object; - public static final fun averageWith (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Ring;)Ljava/lang/Object; - public static final fun averageWith (Lkotlin/sequences/Sequence;Lspace/kscience/kmath/operations/Ring;)Ljava/lang/Object; - public static final fun power (Lspace/kscience/kmath/operations/Field;Ljava/lang/Object;I)Ljava/lang/Object; - public static final fun power-jXDDuk8 (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Object;I)Ljava/lang/Object; - public static final fun sum (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Iterable;)Ljava/lang/Object; - public static final fun sum (Lspace/kscience/kmath/operations/Ring;Lkotlin/sequences/Sequence;)Ljava/lang/Object; - public static final fun sumWith (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Ring;)Ljava/lang/Object; - public static final fun sumWith (Lkotlin/sequences/Sequence;Lspace/kscience/kmath/operations/Ring;)Ljava/lang/Object; + public static final fun abs (Lspace/kscience/kmath/operations/Group;Ljava/lang/Comparable;)Ljava/lang/Comparable; + public static final fun average (Lspace/kscience/kmath/operations/Group;Ljava/lang/Iterable;)Ljava/lang/Object; + public static final fun average (Lspace/kscience/kmath/operations/Group;Lkotlin/sequences/Sequence;)Ljava/lang/Object; + public static final fun averageWith (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Group;)Ljava/lang/Object; + public static final fun averageWith (Lkotlin/sequences/Sequence;Lspace/kscience/kmath/operations/Group;)Ljava/lang/Object; + public static final fun sum (Lspace/kscience/kmath/operations/Group;Ljava/lang/Iterable;)Ljava/lang/Object; + public static final fun sum (Lspace/kscience/kmath/operations/Group;Lkotlin/sequences/Sequence;)Ljava/lang/Object; + public static final fun sumWith (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Group;)Ljava/lang/Object; + public static final fun sumWith (Lkotlin/sequences/Sequence;Lspace/kscience/kmath/operations/Group;)Ljava/lang/Object; } public final class space/kscience/kmath/operations/AlgebraKt { @@ -1061,7 +1303,7 @@ public final class space/kscience/kmath/operations/BigInt$Companion { public final fun getZERO ()Lspace/kscience/kmath/operations/BigInt; } -public final class space/kscience/kmath/operations/BigIntField : space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOperations, space/kscience/kmath/operations/ScaleOperations { +public final class space/kscience/kmath/operations/BigIntField : space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumbersAddOps, space/kscience/kmath/operations/ScaleOperations { public static final field INSTANCE Lspace/kscience/kmath/operations/BigIntField; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (Lspace/kscience/kmath/operations/BigInt;Lspace/kscience/kmath/operations/BigInt;)Lspace/kscience/kmath/operations/BigInt; @@ -1085,9 +1327,12 @@ public final class space/kscience/kmath/operations/BigIntField : space/kscience/ public final class space/kscience/kmath/operations/BigIntKt { public static final fun abs (Lspace/kscience/kmath/operations/BigInt;)Lspace/kscience/kmath/operations/BigInt; - public static final fun bigInt (Lspace/kscience/kmath/nd/AlgebraND$Companion;[I)Lspace/kscience/kmath/nd/BufferedRingND; public static final fun bigInt (Lspace/kscience/kmath/structures/Buffer$Companion;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; public static final fun bigInt (Lspace/kscience/kmath/structures/MutableBuffer$Companion;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/MutableBuffer; + public static final fun buffer (Lspace/kscience/kmath/operations/BigInt$Companion;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun getAlgebra (Lspace/kscience/kmath/operations/BigInt;)Lspace/kscience/kmath/operations/BigIntField; + public static final fun getNd (Lspace/kscience/kmath/operations/BigIntField;)Lspace/kscience/kmath/nd/BufferedRingOpsND; + public static final fun mutableBuffer (Lspace/kscience/kmath/operations/BigInt;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; public static final fun parseBigInteger (Ljava/lang/String;)Lspace/kscience/kmath/operations/BigInt; public static final fun toBigInt (I)Lspace/kscience/kmath/operations/BigInt; public static final fun toBigInt (J)Lspace/kscience/kmath/operations/BigInt; @@ -1096,6 +1341,85 @@ public final class space/kscience/kmath/operations/BigIntKt { public static final fun toBigInt-WZ4Q5Ns (I)Lspace/kscience/kmath/operations/BigInt; } +public abstract interface class space/kscience/kmath/operations/BufferAlgebra : space/kscience/kmath/operations/Algebra { + public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; + public fun buffer (I[Ljava/lang/Object;)Lspace/kscience/kmath/structures/Buffer; + public abstract fun getBufferFactory ()Lkotlin/jvm/functions/Function2; + public abstract fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public fun map (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/structures/Buffer; + public fun mapIndexed (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/structures/Buffer; + public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; + public fun zip (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/structures/Buffer; +} + +public final class space/kscience/kmath/operations/BufferAlgebraKt { + public static final fun acos (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun acosh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun asin (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun asinh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun atan (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun atanh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun buffer (Lspace/kscience/kmath/operations/BufferAlgebra;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun buffer (Lspace/kscience/kmath/operations/BufferAlgebra;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun buffer (Lspace/kscience/kmath/operations/BufferField;[Ljava/lang/Number;)Lspace/kscience/kmath/structures/Buffer; + public static final fun bufferAlgebra (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/operations/BufferFieldOps; + public static final fun cos (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun cosh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun exp (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun getBufferAlgebra (Lspace/kscience/kmath/operations/DoubleField;)Lspace/kscience/kmath/operations/BufferFieldOps; + public static final fun getBufferAlgebra (Lspace/kscience/kmath/operations/ShortRing;)Lspace/kscience/kmath/operations/BufferRingOps; + public static final fun ln (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun pow (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)Lspace/kscience/kmath/structures/Buffer; + public static final fun sin (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun sinh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun tan (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun tanh (Lspace/kscience/kmath/operations/BufferAlgebra;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun withSize (Lspace/kscience/kmath/operations/BufferFieldOps;I)Lspace/kscience/kmath/operations/BufferField; +} + +public final class space/kscience/kmath/operations/BufferField : space/kscience/kmath/operations/BufferFieldOps, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/WithSize { + public fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;I)V + public synthetic fun getOne ()Ljava/lang/Object; + public fun getOne ()Lspace/kscience/kmath/structures/Buffer; + public fun getSize ()I + public synthetic fun getZero ()Ljava/lang/Object; + public fun getZero ()Lspace/kscience/kmath/structures/Buffer; +} + +public class space/kscience/kmath/operations/BufferFieldOps : space/kscience/kmath/operations/BufferRingOps, space/kscience/kmath/operations/BufferAlgebra, space/kscience/kmath/operations/FieldOps, space/kscience/kmath/operations/ScaleOperations { + public fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function2;)V + public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; + public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun divide (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; + public fun scale (Lspace/kscience/kmath/structures/Buffer;D)Lspace/kscience/kmath/structures/Buffer; + public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryMinus (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; +} + +public final class space/kscience/kmath/operations/BufferOperationKt { + public static final fun asIterable (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Iterable; + public static final fun asSequence (Lspace/kscience/kmath/structures/Buffer;)Lkotlin/sequences/Sequence; + public static final fun fold (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;Lkotlin/jvm/functions/Function2;)Ljava/lang/Object; + public static final fun map (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun toList (Lspace/kscience/kmath/structures/Buffer;)Ljava/util/List; +} + +public class space/kscience/kmath/operations/BufferRingOps : space/kscience/kmath/operations/BufferAlgebra, space/kscience/kmath/operations/RingOps { + public fun (Lspace/kscience/kmath/operations/Ring;Lkotlin/jvm/functions/Function2;)V + public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun add (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; + public fun getBufferFactory ()Lkotlin/jvm/functions/Function2; + public synthetic fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public fun getElementAlgebra ()Lspace/kscience/kmath/operations/Ring; + public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun multiply (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryMinus (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; +} + public final class space/kscience/kmath/operations/ByteRing : space/kscience/kmath/operations/Norm, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/Ring { public static final field INSTANCE Lspace/kscience/kmath/operations/ByteRing; public fun add (BB)Ljava/lang/Byte; @@ -1120,6 +1444,90 @@ public final class space/kscience/kmath/operations/ByteRing : space/kscience/kma public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; } +public final class space/kscience/kmath/operations/DoubleBufferField : space/kscience/kmath/operations/DoubleBufferOps, space/kscience/kmath/operations/ExtendedField { + public fun (I)V + public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun acosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun asinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun atanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun cosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun getOne ()Ljava/lang/Object; + public fun getOne ()Lspace/kscience/kmath/structures/Buffer; + public final fun getSize ()I + public synthetic fun getZero ()Ljava/lang/Object; + public fun getZero ()Lspace/kscience/kmath/structures/Buffer; + public synthetic fun power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; + public fun power-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)[D + public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun tanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; +} + +public abstract class space/kscience/kmath/operations/DoubleBufferOps : space/kscience/kmath/operations/BufferAlgebra, space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/Norm { + public static final field Companion Lspace/kscience/kmath/operations/DoubleBufferOps$Companion; + public fun ()V + public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; + public fun acos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun acosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun add-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; + public fun asin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun asinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; + public fun atan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun atanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; + public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; + public fun cos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun cosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun divide-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; + public fun exp-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public fun getBufferFactory ()Lkotlin/jvm/functions/Function2; + public synthetic fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public fun getElementAlgebra ()Lspace/kscience/kmath/operations/DoubleField; + public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; + public fun ln-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun map (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/structures/Buffer; + public fun map-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)[D + public synthetic fun minus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun minus-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun multiply-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun norm (Ljava/lang/Object;)Ljava/lang/Object; + public fun norm (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Double; + public synthetic fun plus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun plus-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; + public fun scale-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;D)[D + public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; + public fun sin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; + public fun tan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun tanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryMinus-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D + public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; +} + +public final class space/kscience/kmath/operations/DoubleBufferOps$Companion : space/kscience/kmath/operations/DoubleBufferOps { + public final fun mapInline-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function1;)[D +} + public final class space/kscience/kmath/operations/DoubleField : space/kscience/kmath/operations/ExtendedField, space/kscience/kmath/operations/Norm, space/kscience/kmath/operations/ScaleOperations { public static final field INSTANCE Lspace/kscience/kmath/operations/DoubleField; public fun acos (D)Ljava/lang/Double; @@ -1171,6 +1579,8 @@ public final class space/kscience/kmath/operations/DoubleField : space/kscience/ public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; public fun sinh (D)Ljava/lang/Double; public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sqrt (D)Ljava/lang/Double; + public synthetic fun sqrt (Ljava/lang/Object;)Ljava/lang/Object; public fun tan (D)Ljava/lang/Double; public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; public fun tanh (D)Ljava/lang/Double; @@ -1181,6 +1591,12 @@ public final class space/kscience/kmath/operations/DoubleField : space/kscience/ public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; } +public final class space/kscience/kmath/operations/DoubleL2Norm : space/kscience/kmath/operations/Norm { + public static final field INSTANCE Lspace/kscience/kmath/operations/DoubleL2Norm; + public synthetic fun norm (Ljava/lang/Object;)Ljava/lang/Object; + public fun norm (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Double; +} + public abstract interface class space/kscience/kmath/operations/ExponentialOperations : space/kscience/kmath/operations/Algebra { public static final field ACOSH_OPERATION Ljava/lang/String; public static final field ASINH_OPERATION Ljava/lang/String; @@ -1212,7 +1628,7 @@ public final class space/kscience/kmath/operations/ExponentialOperations$Compani public static final field TANH_OPERATION Ljava/lang/String; } -public abstract interface class space/kscience/kmath/operations/ExtendedField : space/kscience/kmath/operations/ExtendedFieldOperations, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/ScaleOperations { +public abstract interface class space/kscience/kmath/operations/ExtendedField : space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/PowerOperations { public fun acosh (Ljava/lang/Object;)Ljava/lang/Object; public fun asinh (Ljava/lang/Object;)Ljava/lang/Object; public fun atanh (Ljava/lang/Object;)Ljava/lang/Object; @@ -1220,27 +1636,33 @@ public abstract interface class space/kscience/kmath/operations/ExtendedField : public fun rightSideNumberOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; public fun sinh (Ljava/lang/Object;)Ljava/lang/Object; public fun tanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } -public abstract interface class space/kscience/kmath/operations/ExtendedFieldOperations : space/kscience/kmath/operations/ExponentialOperations, space/kscience/kmath/operations/FieldOperations, space/kscience/kmath/operations/PowerOperations, space/kscience/kmath/operations/TrigonometricOperations { +public abstract interface class space/kscience/kmath/operations/ExtendedFieldOps : space/kscience/kmath/operations/ExponentialOperations, space/kscience/kmath/operations/FieldOps, space/kscience/kmath/operations/ScaleOperations, space/kscience/kmath/operations/TrigonometricOperations { public fun tan (Ljava/lang/Object;)Ljava/lang/Object; public fun tanh (Ljava/lang/Object;)Ljava/lang/Object; public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } -public abstract interface class space/kscience/kmath/operations/Field : space/kscience/kmath/operations/FieldOperations, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/Ring, space/kscience/kmath/operations/ScaleOperations { +public abstract interface class space/kscience/kmath/operations/Field : space/kscience/kmath/operations/FieldOps, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/Ring, space/kscience/kmath/operations/ScaleOperations { + public static final field Companion Lspace/kscience/kmath/operations/Field$Companion; public fun number (Ljava/lang/Number;)Ljava/lang/Object; + public fun power (Ljava/lang/Object;I)Ljava/lang/Object; } -public abstract interface class space/kscience/kmath/operations/FieldOperations : space/kscience/kmath/operations/RingOperations { - public static final field Companion Lspace/kscience/kmath/operations/FieldOperations$Companion; +public final class space/kscience/kmath/operations/Field$Companion { +} + +public abstract interface class space/kscience/kmath/operations/FieldOps : space/kscience/kmath/operations/RingOps { + public static final field Companion Lspace/kscience/kmath/operations/FieldOps$Companion; public static final field DIV_OPERATION Ljava/lang/String; public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; public fun div (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public abstract fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; } -public final class space/kscience/kmath/operations/FieldOperations$Companion { +public final class space/kscience/kmath/operations/FieldOps$Companion { public static final field DIV_OPERATION Ljava/lang/String; } @@ -1295,6 +1717,8 @@ public final class space/kscience/kmath/operations/FloatField : space/kscience/k public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; public fun sinh (F)Ljava/lang/Float; public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sqrt (F)Ljava/lang/Float; + public synthetic fun sqrt (Ljava/lang/Object;)Ljava/lang/Object; public fun tan (F)Ljava/lang/Float; public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; public fun tanh (F)Ljava/lang/Float; @@ -1305,12 +1729,12 @@ public final class space/kscience/kmath/operations/FloatField : space/kscience/k public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; } -public abstract interface class space/kscience/kmath/operations/Group : space/kscience/kmath/operations/GroupOperations { +public abstract interface class space/kscience/kmath/operations/Group : space/kscience/kmath/operations/GroupOps { public abstract fun getZero ()Ljava/lang/Object; } -public abstract interface class space/kscience/kmath/operations/GroupOperations : space/kscience/kmath/operations/Algebra { - public static final field Companion Lspace/kscience/kmath/operations/GroupOperations$Companion; +public abstract interface class space/kscience/kmath/operations/GroupOps : space/kscience/kmath/operations/Algebra { + public static final field Companion Lspace/kscience/kmath/operations/GroupOps$Companion; public static final field MINUS_OPERATION Ljava/lang/String; public static final field PLUS_OPERATION Ljava/lang/String; public abstract fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; @@ -1322,7 +1746,7 @@ public abstract interface class space/kscience/kmath/operations/GroupOperations public fun unaryPlus (Ljava/lang/Object;)Ljava/lang/Object; } -public final class space/kscience/kmath/operations/GroupOperations$Companion { +public final class space/kscience/kmath/operations/GroupOps$Companion { public static final field MINUS_OPERATION Ljava/lang/String; public static final field PLUS_OPERATION Ljava/lang/String; } @@ -1351,6 +1775,10 @@ public final class space/kscience/kmath/operations/IntRing : space/kscience/kmat public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; } +public final class space/kscience/kmath/operations/IsIntegerKt { + public static final fun isInteger (Ljava/lang/Number;)Z +} + public final class space/kscience/kmath/operations/JBigDecimalField : space/kscience/kmath/operations/JBigDecimalFieldBase { public static final field Companion Lspace/kscience/kmath/operations/JBigDecimalField$Companion; public fun ()V @@ -1441,6 +1869,15 @@ public abstract interface class space/kscience/kmath/operations/Norm { public abstract fun norm (Ljava/lang/Object;)Ljava/lang/Object; } +public final class space/kscience/kmath/operations/NumbersKt { + public static final fun getAlgebra (Lkotlin/jvm/internal/ByteCompanionObject;)Lspace/kscience/kmath/operations/ByteRing; + public static final fun getAlgebra (Lkotlin/jvm/internal/DoubleCompanionObject;)Lspace/kscience/kmath/operations/DoubleField; + public static final fun getAlgebra (Lkotlin/jvm/internal/FloatCompanionObject;)Lspace/kscience/kmath/operations/FloatField; + public static final fun getAlgebra (Lkotlin/jvm/internal/IntCompanionObject;)Lspace/kscience/kmath/operations/IntRing; + public static final fun getAlgebra (Lkotlin/jvm/internal/LongCompanionObject;)Lspace/kscience/kmath/operations/LongRing; + public static final fun getAlgebra (Lkotlin/jvm/internal/ShortCompanionObject;)Lspace/kscience/kmath/operations/ShortRing; +} + public abstract interface class space/kscience/kmath/operations/NumericAlgebra : space/kscience/kmath/operations/Algebra { public fun bindSymbolOrNull (Ljava/lang/String;)Ljava/lang/Object; public fun leftSideNumberOperation (Ljava/lang/String;Ljava/lang/Number;Ljava/lang/Object;)Ljava/lang/Object; @@ -1455,10 +1892,7 @@ public final class space/kscience/kmath/operations/NumericAlgebraKt { public static final fun getPi (Lspace/kscience/kmath/operations/NumericAlgebra;)Ljava/lang/Object; } -public final class space/kscience/kmath/operations/OptionalOperationsKt { -} - -public abstract interface class space/kscience/kmath/operations/PowerOperations : space/kscience/kmath/operations/Algebra { +public abstract interface class space/kscience/kmath/operations/PowerOperations : space/kscience/kmath/operations/FieldOps { public static final field Companion Lspace/kscience/kmath/operations/PowerOperations$Companion; public static final field POW_OPERATION Ljava/lang/String; public static final field SQRT_OPERATION Ljava/lang/String; @@ -1472,19 +1906,24 @@ public final class space/kscience/kmath/operations/PowerOperations$Companion { public static final field SQRT_OPERATION Ljava/lang/String; } -public abstract interface class space/kscience/kmath/operations/Ring : space/kscience/kmath/operations/Group, space/kscience/kmath/operations/RingOperations { +public abstract interface class space/kscience/kmath/operations/Ring : space/kscience/kmath/operations/Group, space/kscience/kmath/operations/RingOps { + public static final field Companion Lspace/kscience/kmath/operations/Ring$Companion; public abstract fun getOne ()Ljava/lang/Object; + public fun power-Qn1smSk (Ljava/lang/Object;I)Ljava/lang/Object; } -public abstract interface class space/kscience/kmath/operations/RingOperations : space/kscience/kmath/operations/GroupOperations { - public static final field Companion Lspace/kscience/kmath/operations/RingOperations$Companion; +public final class space/kscience/kmath/operations/Ring$Companion { +} + +public abstract interface class space/kscience/kmath/operations/RingOps : space/kscience/kmath/operations/GroupOps { + public static final field Companion Lspace/kscience/kmath/operations/RingOps$Companion; public static final field TIMES_OPERATION Ljava/lang/String; public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; public abstract fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun times (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; } -public final class space/kscience/kmath/operations/RingOperations$Companion { +public final class space/kscience/kmath/operations/RingOps$Companion { public static final field TIMES_OPERATION Ljava/lang/String; } @@ -1544,6 +1983,10 @@ public final class space/kscience/kmath/operations/TrigonometricOperations$Compa public static final field TAN_OPERATION Ljava/lang/String; } +public abstract interface class space/kscience/kmath/operations/WithSize { + public abstract fun getSize ()I +} + public final class space/kscience/kmath/structures/ArrayBuffer : space/kscience/kmath/structures/MutableBuffer { public fun ([Ljava/lang/Object;)V public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; @@ -1551,6 +1994,11 @@ public final class space/kscience/kmath/structures/ArrayBuffer : space/kscience/ public fun getSize ()I public fun iterator ()Ljava/util/Iterator; public fun set (ILjava/lang/Object;)V + public fun toString ()Ljava/lang/String; +} + +public final class space/kscience/kmath/structures/ArrayBufferKt { + public static final fun asBuffer ([Ljava/lang/Object;)Lspace/kscience/kmath/structures/ArrayBuffer; } public abstract interface class space/kscience/kmath/structures/Buffer { @@ -1558,31 +2006,25 @@ public abstract interface class space/kscience/kmath/structures/Buffer { public abstract fun get (I)Ljava/lang/Object; public abstract fun getSize ()I public abstract fun iterator ()Ljava/util/Iterator; + public abstract fun toString ()Ljava/lang/String; } public final class space/kscience/kmath/structures/Buffer$Companion { public final fun auto (Lkotlin/reflect/KClass;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; public final fun boxing (ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; public final fun contentEquals (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)Z + public final fun toString (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/String; } public final class space/kscience/kmath/structures/BufferKt { - public static final fun asBuffer (Ljava/util/List;)Lspace/kscience/kmath/structures/ListBuffer; - public static final fun asBuffer ([Ljava/lang/Object;)Lspace/kscience/kmath/structures/ArrayBuffer; - public static final fun asMutableBuffer (Ljava/util/List;)Ljava/util/List; public static final fun asReadOnly (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public static final fun first (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Object; public static final fun getIndices (Lspace/kscience/kmath/structures/Buffer;)Lkotlin/ranges/IntRange; -} - -public final class space/kscience/kmath/structures/BufferOperationKt { - public static final fun asIterable (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Iterable; - public static final fun asSequence (Lspace/kscience/kmath/structures/Buffer;)Lkotlin/sequences/Sequence; - public static final fun fold (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;Lkotlin/jvm/functions/Function2;)Ljava/lang/Object; - public static final fun map (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; - public static final fun toList (Lspace/kscience/kmath/structures/Buffer;)Ljava/util/List; + public static final fun last (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/Object; } public final class space/kscience/kmath/structures/DoubleBuffer : space/kscience/kmath/structures/MutableBuffer { + public static final field Companion Lspace/kscience/kmath/structures/DoubleBuffer$Companion; public static final synthetic fun box-impl ([D)Lspace/kscience/kmath/structures/DoubleBuffer; public static fun constructor-impl ([D)[D public synthetic fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; @@ -1610,97 +2052,8 @@ public final class space/kscience/kmath/structures/DoubleBuffer : space/kscience public final synthetic fun unbox-impl ()[D } -public final class space/kscience/kmath/structures/DoubleBufferField : space/kscience/kmath/operations/ExtendedField { - public fun (I)V - public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; - public fun acos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun acosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun add-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; - public fun asin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun asinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; - public fun atan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun atanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; - public fun cos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun cosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun divide-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; - public fun exp-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun getOne ()Ljava/lang/Object; - public fun getOne ()Lspace/kscience/kmath/structures/Buffer; - public final fun getSize ()I - public synthetic fun getZero ()Ljava/lang/Object; - public fun getZero ()Lspace/kscience/kmath/structures/Buffer; - public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; - public fun ln-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun multiply-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; - public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/structures/Buffer; - public synthetic fun power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; - public fun power-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)[D - public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; - public fun scale-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;D)[D - public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; - public fun sin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun sinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; - public fun tan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun tanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; - public fun unaryMinus (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; -} - -public final class space/kscience/kmath/structures/DoubleBufferFieldOperations : space/kscience/kmath/operations/ExtendedFieldOperations { - public static final field INSTANCE Lspace/kscience/kmath/structures/DoubleBufferFieldOperations; - public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; - public fun acos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun acosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun add-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; - public fun asin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun asinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; - public fun atan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun atanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; - public fun cos-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; - public fun cosh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun divide-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; - public fun exp-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; - public fun ln-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun multiply (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; - public fun multiply-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; - public fun power-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)[D - public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; - public fun sin-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; - public fun sinh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; - public fun tan-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun tanh (Ljava/lang/Object;)Ljava/lang/Object; - public fun tanh-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D - public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; - public fun unaryMinus-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D +public final class space/kscience/kmath/structures/DoubleBuffer$Companion { + public final fun zero-Udx-57Q (I)[D } public final class space/kscience/kmath/structures/DoubleBufferKt { @@ -1731,6 +2084,7 @@ public final class space/kscience/kmath/structures/FlaggedDoubleBuffer : space/k public fun getSize ()I public final fun getValues ()[D public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; } public final class space/kscience/kmath/structures/FloatBuffer : space/kscience/kmath/structures/MutableBuffer { @@ -1808,6 +2162,12 @@ public final class space/kscience/kmath/structures/ListBuffer : space/kscience/k public final fun getList ()Ljava/util/List; public fun getSize ()I public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; +} + +public final class space/kscience/kmath/structures/ListBufferKt { + public static final fun asBuffer (Ljava/util/List;)Lspace/kscience/kmath/structures/ListBuffer; + public static final fun asMutableBuffer (Ljava/util/List;)Ljava/util/List; } public final class space/kscience/kmath/structures/LongBuffer : space/kscience/kmath/structures/MutableBuffer { @@ -1852,6 +2212,7 @@ public class space/kscience/kmath/structures/MemoryBuffer : space/kscience/kmath public fun getSize ()I protected final fun getSpec ()Lspace/kscience/kmath/memory/MemorySpec; public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; } public final class space/kscience/kmath/structures/MemoryBuffer$Companion { @@ -1981,5 +2342,6 @@ public final class space/kscience/kmath/structures/VirtualBuffer : space/kscienc public fun get (I)Ljava/lang/Object; public fun getSize ()I public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; } diff --git a/kmath-coroutines/README.md b/kmath-coroutines/README.md index 0d83a6c60..d0fef6e0f 100644 --- a/kmath-coroutines/README.md +++ b/kmath-coroutines/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-coroutines:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-coroutines:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-coroutines:0.3.0-dev-20' + implementation 'space.kscience:kmath-coroutines:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-coroutines:0.3.0-dev-20") + implementation("space.kscience:kmath-coroutines:0.3.0") } ``` diff --git a/kmath-dimensions/README.md b/kmath-dimensions/README.md index 52097cf40..650bcafde 100644 --- a/kmath-dimensions/README.md +++ b/kmath-dimensions/README.md @@ -6,7 +6,7 @@ A proof of concept module for adding type-safe dimensions to structures ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-dimensions:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-dimensions:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-dimensions:0.3.0-dev-20' + implementation 'space.kscience:kmath-dimensions:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-dimensions:0.3.0-dev-20") + implementation("space.kscience:kmath-dimensions:0.3.0") } ``` diff --git a/kmath-ejml/README.md b/kmath-ejml/README.md index 3fe6d9e1a..eaa90120f 100644 --- a/kmath-ejml/README.md +++ b/kmath-ejml/README.md @@ -9,7 +9,7 @@ EJML based linear algebra implementation. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-ejml:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-ejml:0.3.0`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-ejml:0.3.0-dev-20' + implementation 'space.kscience:kmath-ejml:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ejml:0.3.0-dev-20") + implementation("space.kscience:kmath-ejml:0.3.0") } ``` diff --git a/kmath-for-real/README.md b/kmath-for-real/README.md index 197190dcd..9e8f95a16 100644 --- a/kmath-for-real/README.md +++ b/kmath-for-real/README.md @@ -9,7 +9,7 @@ Specialization of KMath APIs for Double numbers. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-for-real:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-for-real:0.3.0`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-for-real:0.3.0-dev-20' + implementation 'space.kscience:kmath-for-real:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-for-real:0.3.0-dev-20") + implementation("space.kscience:kmath-for-real:0.3.0") } ``` diff --git a/kmath-functions/README.md b/kmath-functions/README.md index 6379ad0b5..3f44bd3f9 100644 --- a/kmath-functions/README.md +++ b/kmath-functions/README.md @@ -11,7 +11,7 @@ Functions and interpolations. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-functions:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-functions:0.3.0`. **Gradle Groovy:** ```groovy @@ -21,7 +21,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-functions:0.3.0-dev-20' + implementation 'space.kscience:kmath-functions:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -32,6 +32,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-functions:0.3.0-dev-20") + implementation("space.kscience:kmath-functions:0.3.0") } ``` diff --git a/kmath-geometry/README.md b/kmath-geometry/README.md index 6b8fb25a0..6602f5510 100644 --- a/kmath-geometry/README.md +++ b/kmath-geometry/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-geometry:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-geometry:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-geometry:0.3.0-dev-20' + implementation 'space.kscience:kmath-geometry:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-geometry:0.3.0-dev-20") + implementation("space.kscience:kmath-geometry:0.3.0") } ``` diff --git a/kmath-histograms/README.md b/kmath-histograms/README.md index 0b8a632d6..27f1b43ec 100644 --- a/kmath-histograms/README.md +++ b/kmath-histograms/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-histograms:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-histograms:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-histograms:0.3.0-dev-20' + implementation 'space.kscience:kmath-histograms:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-histograms:0.3.0-dev-20") + implementation("space.kscience:kmath-histograms:0.3.0") } ``` diff --git a/kmath-jafama/README.md b/kmath-jafama/README.md index a274b3d88..fe6afb835 100644 --- a/kmath-jafama/README.md +++ b/kmath-jafama/README.md @@ -7,7 +7,7 @@ Integration with [Jafama](https://github.com/jeffhain/jafama). ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-jafama:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-jafama:0.3.0`. **Gradle Groovy:** ```groovy @@ -17,7 +17,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-jafama:0.3.0-dev-20' + implementation 'space.kscience:kmath-jafama:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -28,7 +28,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-jafama:0.3.0-dev-20") + implementation("space.kscience:kmath-jafama:0.3.0") } ``` diff --git a/kmath-jupyter/README.md b/kmath-jupyter/README.md index 8014b969d..db58ad840 100644 --- a/kmath-jupyter/README.md +++ b/kmath-jupyter/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-jupyter:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-jupyter:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-jupyter:0.3.0-dev-20' + implementation 'space.kscience:kmath-jupyter:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-jupyter:0.3.0-dev-20") + implementation("space.kscience:kmath-jupyter:0.3.0") } ``` diff --git a/kmath-kotlingrad/README.md b/kmath-kotlingrad/README.md index 08c913090..52e8b3116 100644 --- a/kmath-kotlingrad/README.md +++ b/kmath-kotlingrad/README.md @@ -8,7 +8,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-kotlingrad:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-kotlingrad:0.3.0`. **Gradle Groovy:** ```groovy @@ -18,7 +18,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-kotlingrad:0.3.0-dev-20' + implementation 'space.kscience:kmath-kotlingrad:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-kotlingrad:0.3.0-dev-20") + implementation("space.kscience:kmath-kotlingrad:0.3.0") } ``` diff --git a/kmath-memory/README.md b/kmath-memory/README.md index d37087a66..9f4520bd8 100644 --- a/kmath-memory/README.md +++ b/kmath-memory/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-memory:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-memory:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-memory:0.3.0-dev-20' + implementation 'space.kscience:kmath-memory:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-memory:0.3.0-dev-20") + implementation("space.kscience:kmath-memory:0.3.0") } ``` diff --git a/kmath-multik/README.md b/kmath-multik/README.md index 167445f52..edfce6f79 100644 --- a/kmath-multik/README.md +++ b/kmath-multik/README.md @@ -6,7 +6,7 @@ JetBrains Multik connector ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-multik:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-multik:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-multik:0.3.0-dev-20' + implementation 'space.kscience:kmath-multik:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-multik:0.3.0-dev-20") + implementation("space.kscience:kmath-multik:0.3.0") } ``` diff --git a/kmath-nd4j/README.md b/kmath-nd4j/README.md index 225de18e9..0bcae138e 100644 --- a/kmath-nd4j/README.md +++ b/kmath-nd4j/README.md @@ -9,7 +9,7 @@ ND4J based implementations of KMath abstractions. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-nd4j:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-nd4j:0.3.0`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-nd4j:0.3.0-dev-20' + implementation 'space.kscience:kmath-nd4j:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -30,7 +30,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-nd4j:0.3.0-dev-20") + implementation("space.kscience:kmath-nd4j:0.3.0") } ``` diff --git a/kmath-optimization/README.md b/kmath-optimization/README.md index 137975c90..63e0f43e3 100644 --- a/kmath-optimization/README.md +++ b/kmath-optimization/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-optimization:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-optimization:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-optimization:0.3.0-dev-20' + implementation 'space.kscience:kmath-optimization:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-optimization:0.3.0-dev-20") + implementation("space.kscience:kmath-optimization:0.3.0") } ``` diff --git a/kmath-stat/README.md b/kmath-stat/README.md index 762e61237..80c6e0fcd 100644 --- a/kmath-stat/README.md +++ b/kmath-stat/README.md @@ -6,7 +6,7 @@ ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-stat:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-stat:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-stat:0.3.0-dev-20' + implementation 'space.kscience:kmath-stat:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-stat:0.3.0-dev-20") + implementation("space.kscience:kmath-stat:0.3.0") } ``` diff --git a/kmath-symja/README.md b/kmath-symja/README.md index e3c717cff..ea2d5d68f 100644 --- a/kmath-symja/README.md +++ b/kmath-symja/README.md @@ -6,7 +6,7 @@ Symja integration module ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-symja:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-symja:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-symja:0.3.0-dev-20' + implementation 'space.kscience:kmath-symja:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-symja:0.3.0-dev-20") + implementation("space.kscience:kmath-symja:0.3.0") } ``` diff --git a/kmath-tensorflow/README.md b/kmath-tensorflow/README.md index f1dfa0202..7852c07be 100644 --- a/kmath-tensorflow/README.md +++ b/kmath-tensorflow/README.md @@ -6,7 +6,7 @@ Google tensorflow connector ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-tensorflow:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-tensorflow:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-tensorflow:0.3.0-dev-20' + implementation 'space.kscience:kmath-tensorflow:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-tensorflow:0.3.0-dev-20") + implementation("space.kscience:kmath-tensorflow:0.3.0") } ``` diff --git a/kmath-tensors/README.md b/kmath-tensors/README.md index 3d7dfd1fb..44ee47675 100644 --- a/kmath-tensors/README.md +++ b/kmath-tensors/README.md @@ -9,7 +9,7 @@ Common linear algebra operations on tensors. ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-tensors:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-tensors:0.3.0`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-tensors:0.3.0-dev-20' + implementation 'space.kscience:kmath-tensors:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-tensors:0.3.0-dev-20") + implementation("space.kscience:kmath-tensors:0.3.0") } ``` diff --git a/kmath-viktor/README.md b/kmath-viktor/README.md index 229d4dcd4..5d7c2dea1 100644 --- a/kmath-viktor/README.md +++ b/kmath-viktor/README.md @@ -6,7 +6,7 @@ Binding for https://github.com/JetBrains-Research/viktor ## Artifact: -The Maven coordinates of this project are `space.kscience:kmath-viktor:0.3.0-dev-20`. +The Maven coordinates of this project are `space.kscience:kmath-viktor:0.3.0`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-viktor:0.3.0-dev-20' + implementation 'space.kscience:kmath-viktor:0.3.0' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-viktor:0.3.0-dev-20") + implementation("space.kscience:kmath-viktor:0.3.0") } ``` diff --git a/kmath-viktor/api/kmath-viktor.api b/kmath-viktor/api/kmath-viktor.api index 59882627b..3bb7c3b21 100644 --- a/kmath-viktor/api/kmath-viktor.api +++ b/kmath-viktor/api/kmath-viktor.api @@ -1,40 +1,69 @@ public final class space/kscience/kmath/viktor/ViktorBuffer : space/kscience/kmath/structures/MutableBuffer { - public fun (Lorg/jetbrains/bio/viktor/F64FlatArray;)V + public static final synthetic fun box-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)Lspace/kscience/kmath/viktor/ViktorBuffer; + public static fun constructor-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)Lorg/jetbrains/bio/viktor/F64FlatArray; public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; + public static fun copy-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)Lspace/kscience/kmath/structures/MutableBuffer; + public fun equals (Ljava/lang/Object;)Z + public static fun equals-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;Ljava/lang/Object;)Z + public static final fun equals-impl0 (Lorg/jetbrains/bio/viktor/F64FlatArray;Lorg/jetbrains/bio/viktor/F64FlatArray;)Z public fun get (I)Ljava/lang/Double; public synthetic fun get (I)Ljava/lang/Object; + public static fun get-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;I)Ljava/lang/Double; public final fun getFlatArray ()Lorg/jetbrains/bio/viktor/F64FlatArray; public fun getSize ()I + public static fun getSize-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)I + public fun hashCode ()I + public static fun hashCode-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)I public fun iterator ()Ljava/util/Iterator; + public static fun iterator-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)Ljava/util/Iterator; public fun set (ID)V public synthetic fun set (ILjava/lang/Object;)V + public static fun set-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;ID)V + public fun toString ()Ljava/lang/String; + public static fun toString-impl (Lorg/jetbrains/bio/viktor/F64FlatArray;)Ljava/lang/String; + public final synthetic fun unbox-impl ()Lorg/jetbrains/bio/viktor/F64FlatArray; } -public final class space/kscience/kmath/viktor/ViktorFieldND : space/kscience/kmath/nd/FieldND, space/kscience/kmath/operations/ExtendedField, space/kscience/kmath/operations/NumbersAddOperations, space/kscience/kmath/operations/ScaleOperations { +public class space/kscience/kmath/viktor/ViktorFieldND : space/kscience/kmath/viktor/ViktorFieldOpsND, space/kscience/kmath/nd/FieldND, space/kscience/kmath/operations/NumbersAddOps { public fun ([I)V + public synthetic fun getOne ()Ljava/lang/Object; + public synthetic fun getOne ()Lspace/kscience/kmath/nd/StructureND; + public fun getOne ()Lspace/kscience/kmath/viktor/ViktorStructureND; + public fun getShape ()[I + public synthetic fun getZero ()Ljava/lang/Object; + public synthetic fun getZero ()Lspace/kscience/kmath/nd/StructureND; + public fun getZero ()Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; + public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/viktor/ViktorStructureND; +} + +public class space/kscience/kmath/viktor/ViktorFieldOpsND : space/kscience/kmath/nd/FieldOpsND, space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/PowerOperations { + public static final field Companion Lspace/kscience/kmath/viktor/ViktorFieldOpsND$Companion; + public fun ()V public synthetic fun acos (Ljava/lang/Object;)Ljava/lang/Object; public fun acos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun acosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun acosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public synthetic fun add (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; public fun add (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun asin (Ljava/lang/Object;)Ljava/lang/Object; public fun asin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun asinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun asinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun atan (Ljava/lang/Object;)Ljava/lang/Object; public fun atan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; - public synthetic fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; - public fun combine (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun atanh (Ljava/lang/Object;)Ljava/lang/Object; + public fun atanh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun cos (Ljava/lang/Object;)Ljava/lang/Object; public fun cos (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun cosh (Ljava/lang/Object;)Ljava/lang/Object; + public fun cosh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; public fun exp (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; - public synthetic fun getElementContext ()Lspace/kscience/kmath/operations/Algebra; - public fun getElementContext ()Lspace/kscience/kmath/operations/DoubleField; + public synthetic fun getElementAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public fun getElementAlgebra ()Lspace/kscience/kmath/operations/DoubleField; public final fun getF64Buffer (Lspace/kscience/kmath/nd/StructureND;)Lorg/jetbrains/bio/viktor/F64Array; - public synthetic fun getOne ()Ljava/lang/Object; - public fun getOne ()Lspace/kscience/kmath/viktor/ViktorStructureND; - public fun getShape ()[I - public synthetic fun getZero ()Ljava/lang/Object; - public fun getZero ()Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun ln (Ljava/lang/Object;)Ljava/lang/Object; public fun ln (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun map (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; @@ -43,26 +72,38 @@ public final class space/kscience/kmath/viktor/ViktorFieldND : space/kscience/km public fun mapIndexed (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun minus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun minus (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; - public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; - public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun plus (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun plus (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun plus (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; public fun plus (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; public fun power (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/viktor/ViktorStructureND; - public synthetic fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; - public fun produce (Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun scale (Ljava/lang/Object;D)Ljava/lang/Object; + public synthetic fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; public fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun sin (Ljava/lang/Object;)Ljava/lang/Object; public fun sin (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun sinh (Ljava/lang/Object;)Ljava/lang/Object; + public fun sinh (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; + public synthetic fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun structureND ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun tan (Ljava/lang/Object;)Ljava/lang/Object; public fun tan (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun times (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; public fun times (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/viktor/ViktorStructureND; public synthetic fun unaryMinus (Ljava/lang/Object;)Ljava/lang/Object; public fun unaryMinus (Lspace/kscience/kmath/nd/StructureND;)Lspace/kscience/kmath/nd/StructureND; + public synthetic fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/nd/StructureND; + public fun zip (Lspace/kscience/kmath/nd/StructureND;Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/viktor/ViktorStructureND; +} + +public final class space/kscience/kmath/viktor/ViktorFieldOpsND$Companion : space/kscience/kmath/viktor/ViktorFieldOpsND { +} + +public final class space/kscience/kmath/viktor/ViktorFieldOpsNDKt { + public static final fun ViktorFieldND ([I)Lspace/kscience/kmath/viktor/ViktorFieldND; + public static final fun getViktorAlgebra (Lspace/kscience/kmath/operations/DoubleField;)Lspace/kscience/kmath/viktor/ViktorFieldOpsND; + public static final fun viktorAlgebra (Lspace/kscience/kmath/operations/DoubleField;[I)Lspace/kscience/kmath/viktor/ViktorFieldND; } public final class space/kscience/kmath/viktor/ViktorStructureND : space/kscience/kmath/nd/MutableStructureND { @@ -77,7 +118,6 @@ public final class space/kscience/kmath/viktor/ViktorStructureND : space/kscienc } public final class space/kscience/kmath/viktor/ViktorStructureNDKt { - public static final fun ViktorNDField ([I)Lspace/kscience/kmath/viktor/ViktorFieldND; public static final fun asStructure (Lorg/jetbrains/bio/viktor/F64Array;)Lspace/kscience/kmath/viktor/ViktorStructureND; } -- 2.34.1 From d862a0a8960703f25a4fbd050ea5890fa3c9b150 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 11 Apr 2022 20:08:13 +0300 Subject: [PATCH 37/59] 0.3.0 release --- kmath-jupyter/api/kmath-jupyter.api | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 kmath-jupyter/api/kmath-jupyter.api diff --git a/kmath-jupyter/api/kmath-jupyter.api b/kmath-jupyter/api/kmath-jupyter.api new file mode 100644 index 000000000..e625e22f7 --- /dev/null +++ b/kmath-jupyter/api/kmath-jupyter.api @@ -0,0 +1,4 @@ +public final class space/kscience/kmath/jupyter/KMathJupyterKt { + public static final fun toMst (Ljava/lang/Number;)Lspace/kscience/kmath/expressions/MST$Numeric; +} + -- 2.34.1 From 358d750226881956b8c8ce4de3f08d24ae2dca4f Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 12 Apr 2022 09:49:35 +0300 Subject: [PATCH 38/59] Add missing @CommanderTvis contributions to changelog --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 28240dc68..75833602c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -33,6 +33,10 @@ - Separate methods for UInt, Int and Number powers. NaN safety. - Tensorflow prototype - `ValueAndErrorField` +- MST compilation to WASM: #286 +- Jafama integration: #176 +- `contentEquals` with tolerance: #364 +- Compilation to TeX for MST: #254 ### Changed -- 2.34.1 From 19cd74013b1ab0f38332292d32f36e45101baee3 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 12 Apr 2022 11:06:18 +0300 Subject: [PATCH 39/59] Update pages.yml --- .github/workflows/pages.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 9b76fd16e..2308d00fc 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -24,7 +24,7 @@ jobs: - uses: gradle/gradle-build-action@v2.1.5 with: arguments: dokkaHtmlMultiModule --no-parallel - - uses: JamesIves/github-pages-deploy-action@4.2.5 + - uses: JamesIves/github-pages-deploy-action@4.3.0 with: branch: gh-pages folder: build/dokka/htmlMultiModule -- 2.34.1 From b698f2d613cdf20cdfb03cb7185ca7c04318b786 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 12 Apr 2022 11:10:14 +0300 Subject: [PATCH 40/59] Update pages.yml --- .github/workflows/pages.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 2308d00fc..1ac0bbdfe 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -24,7 +24,7 @@ jobs: - uses: gradle/gradle-build-action@v2.1.5 with: arguments: dokkaHtmlMultiModule --no-parallel - - uses: JamesIves/github-pages-deploy-action@4.3.0 + - uses: JamesIves/github-pages-deploy-action@v4.3.0 with: branch: gh-pages folder: build/dokka/htmlMultiModule -- 2.34.1 From 7e4ece8dbc6e49cb8f224a3793301047de20f83f Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 12 Apr 2022 11:56:12 +0300 Subject: [PATCH 41/59] Update publish.yml --- .github/workflows/publish.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 8e9b98dcb..794881b09 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -34,6 +34,7 @@ jobs: arguments: | releaseAll -Ppublishing.enabled=true + -Ppublishing.sonatype=false -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} - name: Publish Mac Artifacts @@ -45,5 +46,6 @@ jobs: releaseIosArm64 releaseIosX64 -Ppublishing.enabled=true + -Ppublishing.sonatype=false -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} -- 2.34.1 From 2144c6382cce2eae27c4cd55bab693cfeda7e54d Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 12 Apr 2022 12:02:11 +0300 Subject: [PATCH 42/59] Update pages.yml --- .github/workflows/pages.yml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 1ac0bbdfe..2abaf0b9f 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -1,8 +1,9 @@ name: Dokka publication on: - push: - branches: [ master ] + workflow_dispatch: + release: + types: [ created ] jobs: build: -- 2.34.1 From 5a36c3e03c60ffe02b7e7ea5609843b6f3a4155d Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Wed, 13 Apr 2022 11:20:11 +0300 Subject: [PATCH 43/59] Remove metaspace memory allocation key --- gradle.properties | 1 - 1 file changed, 1 deletion(-) diff --git a/gradle.properties b/gradle.properties index 80108737e..4923364d8 100644 --- a/gradle.properties +++ b/gradle.properties @@ -9,5 +9,4 @@ kotlin.native.ignoreDisabledTargets=true #kotlin.incremental.js.ir=true org.gradle.configureondemand=true -org.gradle.jvmargs=-XX:MaxMetaspaceSize=1G org.gradle.parallel=true -- 2.34.1 From c28be8322697c72237544522d8a8c143f688979d Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Wed, 8 Jun 2022 09:00:37 +0300 Subject: [PATCH 44/59] LazyStructire::deferred -> async --- CHANGELOG.md | 2 ++ build.gradle.kts | 2 +- buildSrc/build.gradle.kts | 1 + buildSrc/gradle.properties | 2 +- .../kscience/kmath/nd/VirtualStructureND.kt | 16 ++++++++++++++++ .../kscience/kmath/structures/LazyStructureND.kt | 10 +++++----- 6 files changed, 26 insertions(+), 7 deletions(-) create mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index 75833602c..c4b8c06cf 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,8 @@ ### Added ### Changed +- Kotlin 1.7 +- `LazyStructure` `deffered` -> `async` to comply with coroutines code style ### Deprecated diff --git a/build.gradle.kts b/build.gradle.kts index 10f2385f5..9fa012fb2 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -11,7 +11,7 @@ allprojects { } group = "space.kscience" - version = "0.3.0" + version = "0.3.1" } subprojects { diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts index fa5142538..dcb39d448 100644 --- a/buildSrc/build.gradle.kts +++ b/buildSrc/build.gradle.kts @@ -1,4 +1,5 @@ plugins { + kotlin("jvm") version "1.7.0-RC" `kotlin-dsl` `version-catalog` alias(miptNpmLibs.plugins.kotlin.plugin.serialization) diff --git a/buildSrc/gradle.properties b/buildSrc/gradle.properties index a0b05e812..751caec36 100644 --- a/buildSrc/gradle.properties +++ b/buildSrc/gradle.properties @@ -4,4 +4,4 @@ # kotlin.code.style=official -toolsVersion=0.11.2-kotlin-1.6.10 +toolsVersion=0.11.5-kotlin-1.7.0-RC diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt new file mode 100644 index 000000000..799d14b3d --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt @@ -0,0 +1,16 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.nd + +public open class VirtualStructureND( + override val shape: Shape, + public val producer: (IntArray) -> T, +) : StructureND { + override fun get(index: IntArray): T { + require(check that index is in the shape boundaries) + return producer(index) + } +} \ No newline at end of file diff --git a/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/structures/LazyStructureND.kt b/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/structures/LazyStructureND.kt index ac9eb773a..2b9265843 100644 --- a/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/structures/LazyStructureND.kt +++ b/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/structures/LazyStructureND.kt @@ -18,12 +18,12 @@ public class LazyStructureND( ) : StructureND { private val cache: MutableMap> = HashMap() - public fun deferred(index: IntArray): Deferred = cache.getOrPut(index) { + public fun async(index: IntArray): Deferred = cache.getOrPut(index) { scope.async(context = Dispatchers.Math) { function(index) } } - public suspend fun await(index: IntArray): T = deferred(index).await() - override operator fun get(index: IntArray): T = runBlocking { deferred(index).await() } + public suspend fun await(index: IntArray): T = async(index).await() + override operator fun get(index: IntArray): T = runBlocking { async(index).await() } @OptIn(PerformancePitfall::class) override fun elements(): Sequence> { @@ -33,8 +33,8 @@ public class LazyStructureND( } } -public fun StructureND.deferred(index: IntArray): Deferred = - if (this is LazyStructureND) deferred(index) else CompletableDeferred(get(index)) +public fun StructureND.async(index: IntArray): Deferred = + if (this is LazyStructureND) this@async.async(index) else CompletableDeferred(get(index)) public suspend fun StructureND.await(index: IntArray): T = if (this is LazyStructureND) await(index) else get(index) -- 2.34.1 From de9f3cc8df4ebb0c05ee81d6a77922174e8d532c Mon Sep 17 00:00:00 2001 From: Gleb Minaev <43728100+lounres@users.noreply.github.com> Date: Fri, 10 Jun 2022 23:37:50 +0300 Subject: [PATCH 45/59] Inlined LaTeX formula. Now GitHub supports MathJax! --- kmath-ast/README.md | 5 +---- kmath-ast/docs/README-TEMPLATE.md | 5 +---- 2 files changed, 2 insertions(+), 8 deletions(-) diff --git a/kmath-ast/README.md b/kmath-ast/README.md index 5d5630f46..cc5f5b764 100644 --- a/kmath-ast/README.md +++ b/kmath-ast/README.md @@ -199,10 +199,7 @@ public fun main() { Result LaTeX: -
- -![](https://latex.codecogs.com/gif.latex?%5Coperatorname{exp}%5C,%5Cleft(%5Csqrt{x}%5Cright)-%5Cfrac{%5Cfrac{%5Coperatorname{arcsin}%5C,%5Cleft(2%5C,x%5Cright)}{2%5Ctimes10^{10}%2Bx^{3}}}{12}+x^{2/3}) -
+$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\,x\right)}{2\times10^{10}%2Bx^{3}}}{12}+x^{2/3}$$ Result MathML (can be used with MathJax or other renderers): diff --git a/kmath-ast/docs/README-TEMPLATE.md b/kmath-ast/docs/README-TEMPLATE.md index e9e22f4d4..1f14deaba 100644 --- a/kmath-ast/docs/README-TEMPLATE.md +++ b/kmath-ast/docs/README-TEMPLATE.md @@ -170,10 +170,7 @@ public fun main() { Result LaTeX: -
- -![](https://latex.codecogs.com/gif.latex?%5Coperatorname{exp}%5C,%5Cleft(%5Csqrt{x}%5Cright)-%5Cfrac{%5Cfrac{%5Coperatorname{arcsin}%5C,%5Cleft(2%5C,x%5Cright)}{2%5Ctimes10^{10}%2Bx^{3}}}{12}+x^{2/3}) -
+$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\,x\right)}{2\times10^{10}%2Bx^{3}}}{12}+x^{2/3}$$ Result MathML (can be used with MathJax or other renderers): -- 2.34.1 From b92ef23f5d3ec2c2578abc6f8734a12cd837bbf9 Mon Sep 17 00:00:00 2001 From: Gleb Minaev <43728100+lounres@users.noreply.github.com> Date: Sat, 11 Jun 2022 00:06:45 +0300 Subject: [PATCH 46/59] Some fixes --- kmath-ast/README.md | 2 +- kmath-ast/docs/README-TEMPLATE.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/kmath-ast/README.md b/kmath-ast/README.md index cc5f5b764..553c60bb3 100644 --- a/kmath-ast/README.md +++ b/kmath-ast/README.md @@ -199,7 +199,7 @@ public fun main() { Result LaTeX: -$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\,x\right)}{2\times10^{10}%2Bx^{3}}}{12}+x^{2/3}$$ +$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\\,x\right)}{2\times10^{10}+x^{3}}}{12}+x^{2/3}$$ Result MathML (can be used with MathJax or other renderers): diff --git a/kmath-ast/docs/README-TEMPLATE.md b/kmath-ast/docs/README-TEMPLATE.md index 1f14deaba..96bbfbf5a 100644 --- a/kmath-ast/docs/README-TEMPLATE.md +++ b/kmath-ast/docs/README-TEMPLATE.md @@ -170,7 +170,7 @@ public fun main() { Result LaTeX: -$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\,x\right)}{2\times10^{10}%2Bx^{3}}}{12}+x^{2/3}$$ +$$\operatorname{exp}\\,\left(\sqrt{x}\right)-\frac{\frac{\operatorname{arcsin}\\,\left(2\\,x\right)}{2\times10^{10}+x^{3}}}{12}+x^{2/3}$$ Result MathML (can be used with MathJax or other renderers): -- 2.34.1 From 569e01fce13f890e8c938d90ac4285e99f3b3e93 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 12 Jun 2022 15:16:40 +0300 Subject: [PATCH 47/59] Migration to kotlin 1.7 --- build.gradle.kts | 2 +- buildSrc/build.gradle.kts | 13 +++---- buildSrc/gradle.properties | 7 ---- buildSrc/settings.gradle.kts | 14 ++++++-- .../kmath/ejml/codegen/ejmlCodegen.kt | 4 ++- gradle.properties | 5 ++- kmath-ast/build.gradle.kts | 2 +- kmath-core/build.gradle.kts | 4 +-- .../space/kscience/kmath/nd/AlgebraND.kt | 19 ---------- .../kscience/kmath/nd/BufferAlgebraND.kt | 2 +- .../kotlin/space/kscience/kmath/nd/Shape.kt | 35 +++++++++++++++++++ .../space/kscience/kmath/nd/ShapeIndexer.kt | 14 +++++--- .../space/kscience/kmath/nd/StructureND.kt | 4 +-- .../kscience/kmath/nd/VirtualStructureND.kt | 18 ++++++++-- .../space/kscience/kmath/nd/operationsND.kt | 32 +++++++++++++++++ .../kscience/kmath/nd/NdOperationsTest.kt | 28 +++++++++++++++ .../space/kscience/kmath/ejml/_generated.kt | 16 ++++++--- .../kscience/kmath/ejml/EjmlMatrixTest.kt | 6 ++-- kmath-histograms/build.gradle.kts | 8 ++--- .../kmath/histogram/TreeHistogramTest.kt | 2 ++ kmath-memory/build.gradle.kts | 3 +- kmath-optimization/build.gradle.kts | 5 +-- kmath-stat/build.gradle.kts | 5 +-- .../space/kscience/kmath/stat/Sampler.kt | 2 ++ .../space/kscience/kmath/stat/MCScopeTest.kt | 2 +- .../kscience/kmath/viktor/ViktorFieldOpsND.kt | 1 + settings.gradle.kts | 20 ++++++++++- 27 files changed, 200 insertions(+), 73 deletions(-) delete mode 100644 buildSrc/gradle.properties create mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Shape.kt create mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt create mode 100644 kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt diff --git a/build.gradle.kts b/build.gradle.kts index 9fa012fb2..ab136bfbc 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -11,7 +11,7 @@ allprojects { } group = "space.kscience" - version = "0.3.1" + version = "0.3.1-dev-1" } subprojects { diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts index dcb39d448..20611e92d 100644 --- a/buildSrc/build.gradle.kts +++ b/buildSrc/build.gradle.kts @@ -1,8 +1,8 @@ plugins { - kotlin("jvm") version "1.7.0-RC" + kotlin("jvm") version "1.7.0" `kotlin-dsl` `version-catalog` - alias(miptNpmLibs.plugins.kotlin.plugin.serialization) + alias(npmlibs.plugins.kotlin.plugin.serialization) } java.targetCompatibility = JavaVersion.VERSION_11 @@ -14,17 +14,18 @@ repositories { gradlePluginPortal() } -val toolsVersion: String by extra -val kotlinVersion = miptNpmLibs.versions.kotlin.asProvider().get() -val benchmarksVersion = miptNpmLibs.versions.kotlinx.benchmark.get() +val toolsVersion = npmlibs.versions.tools.get() +val kotlinVersion = npmlibs.versions.kotlin.asProvider().get() +val benchmarksVersion = npmlibs.versions.kotlinx.benchmark.get() dependencies { api("ru.mipt.npm:gradle-tools:$toolsVersion") + api(npmlibs.atomicfu.gradle) //plugins form benchmarks api("org.jetbrains.kotlinx:kotlinx-benchmark-plugin:$benchmarksVersion") api("org.jetbrains.kotlin:kotlin-allopen:$kotlinVersion") //to be used inside build-script only - implementation(miptNpmLibs.kotlinx.serialization.json) + implementation(npmlibs.kotlinx.serialization.json) } kotlin.sourceSets.all { diff --git a/buildSrc/gradle.properties b/buildSrc/gradle.properties deleted file mode 100644 index 751caec36..000000000 --- a/buildSrc/gradle.properties +++ /dev/null @@ -1,7 +0,0 @@ -# -# Copyright 2018-2021 KMath contributors. -# Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. -# - -kotlin.code.style=official -toolsVersion=0.11.5-kotlin-1.7.0-RC diff --git a/buildSrc/settings.gradle.kts b/buildSrc/settings.gradle.kts index 7c1df133d..bce265510 100644 --- a/buildSrc/settings.gradle.kts +++ b/buildSrc/settings.gradle.kts @@ -6,7 +6,17 @@ enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") dependencyResolutionManagement { - val toolsVersion: String by extra + val projectProperties = java.util.Properties() + file("../gradle.properties").inputStream().use { + projectProperties.load(it) + } + + projectProperties.forEach { key, value -> + extra.set(key.toString(), value) + } + + + val toolsVersion: String = projectProperties["toolsVersion"].toString() repositories { mavenLocal() @@ -16,7 +26,7 @@ dependencyResolutionManagement { } versionCatalogs { - create("miptNpmLibs") { + create("npmlibs") { from("ru.mipt.npm:version-catalog:$toolsVersion") } } diff --git a/buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt b/buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt index 7f8cb35b3..7c23d8ea0 100644 --- a/buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt +++ b/buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt @@ -319,7 +319,9 @@ public object EjmlLinearSpace${ops} : EjmlLinearSpace<${type}, ${kmathAlgebra}, } else -> null - }?.let(type::cast) + }?.let{ + type.cast(it) + } } /** diff --git a/gradle.properties b/gradle.properties index 4923364d8..9cdd7801c 100644 --- a/gradle.properties +++ b/gradle.properties @@ -6,7 +6,10 @@ kotlin.code.style=official kotlin.jupyter.add.scanner=false kotlin.mpp.stability.nowarn=true kotlin.native.ignoreDisabledTargets=true -#kotlin.incremental.js.ir=true +//kotlin.incremental.js.ir=true org.gradle.configureondemand=true org.gradle.parallel=true +org.gradle.jvmargs=-Xmx4096m + +toolsVersion=0.11.6-kotlin-1.7.0 diff --git a/kmath-ast/build.gradle.kts b/kmath-ast/build.gradle.kts index 15b1d0900..0dd625ef1 100644 --- a/kmath-ast/build.gradle.kts +++ b/kmath-ast/build.gradle.kts @@ -57,7 +57,7 @@ tasks.dokkaHtml { if (System.getProperty("space.kscience.kmath.ast.dump.generated.classes") == "1") tasks.jvmTest { - jvmArgs = (jvmArgs ?: emptyList()) + listOf("-Dspace.kscience.kmath.ast.dump.generated.classes=1") + jvmArgs("-Dspace.kscience.kmath.ast.dump.generated.classes=1") } readme { diff --git a/kmath-core/build.gradle.kts b/kmath-core/build.gradle.kts index 4a35a54fb..052924ce8 100644 --- a/kmath-core/build.gradle.kts +++ b/kmath-core/build.gradle.kts @@ -1,8 +1,6 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") + id("ru.mipt.npm.gradle.mpp") id("ru.mipt.npm.gradle.native") -// id("com.xcporter.metaview") version "0.0.5" } kotlin.sourceSets { diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt index a9712e870..ad291cf7f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/AlgebraND.kt @@ -10,25 +10,6 @@ import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import kotlin.reflect.KClass -/** - * An exception is thrown when the expected and actual shape of NDArray differ. - * - * @property expected the expected shape. - * @property actual the actual shape. - */ -public class ShapeMismatchException(public val expected: IntArray, public val actual: IntArray) : - RuntimeException("Shape ${actual.contentToString()} doesn't fit in expected shape ${expected.contentToString()}.") - -public typealias Shape = IntArray - -public fun Shape(shapeFirst: Int, vararg shapeRest: Int): Shape = intArrayOf(shapeFirst, *shapeRest) - -public interface WithShape { - public val shape: Shape - - public val indices: ShapeIndexer get() = DefaultStrides(shape) -} - /** * The base interface for all ND-algebra implementations. * diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferAlgebraND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferAlgebraND.kt index b09344d12..68e8ebe90 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferAlgebraND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferAlgebraND.kt @@ -47,7 +47,7 @@ public interface BufferAlgebraND> : AlgebraND { zipInline(left.toBufferND(), right.toBufferND(), transform) public companion object { - public val defaultIndexerBuilder: (IntArray) -> ShapeIndexer = DefaultStrides.Companion::invoke + public val defaultIndexerBuilder: (IntArray) -> ShapeIndexer = ::Strides } } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Shape.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Shape.kt new file mode 100644 index 000000000..d682d5e69 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Shape.kt @@ -0,0 +1,35 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.nd + +/** + * An exception is thrown when the expected and actual shape of NDArray differ. + * + * @property expected the expected shape. + * @property actual the actual shape. + */ +public class ShapeMismatchException(public val expected: IntArray, public val actual: IntArray) : + RuntimeException("Shape ${actual.contentToString()} doesn't fit in expected shape ${expected.contentToString()}.") + +public class IndexOutOfShapeException(public val shape: Shape, public val index: IntArray) : + RuntimeException("Index ${index.contentToString()} is out of shape ${shape.contentToString()}") + +public typealias Shape = IntArray + +public fun Shape(shapeFirst: Int, vararg shapeRest: Int): Shape = intArrayOf(shapeFirst, *shapeRest) + +public interface WithShape { + public val shape: Shape + + public val indices: ShapeIndexer get() = DefaultStrides(shape) +} + +internal fun requireIndexInShape(index: IntArray, shape: Shape) { + if (index.size != shape.size) throw IndexOutOfShapeException(index, shape) + shape.forEachIndexed { axis, axisShape -> + if (index[axis] !in 0 until axisShape) throw IndexOutOfShapeException(index, shape) + } +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndexer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndexer.kt index c6ff79587..29701425f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndexer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndexer.kt @@ -10,7 +10,7 @@ import kotlin.native.concurrent.ThreadLocal /** * A converter from linear index to multivariate index */ -public interface ShapeIndexer: Iterable{ +public interface ShapeIndexer : Iterable { public val shape: Shape /** @@ -44,7 +44,7 @@ public interface ShapeIndexer: Iterable{ /** * Linear transformation of indexes */ -public abstract class Strides: ShapeIndexer { +public abstract class Strides : ShapeIndexer { /** * Array strides */ @@ -66,7 +66,7 @@ public abstract class Strides: ShapeIndexer { /** * Simple implementation of [Strides]. */ -public class DefaultStrides private constructor(override val shape: IntArray) : Strides() { +public class DefaultStrides(override val shape: IntArray) : Strides() { override val linearSize: Int get() = strides[shape.size] /** @@ -112,10 +112,16 @@ public class DefaultStrides private constructor(override val shape: IntArray) : /** * Cached builder for default strides */ + @Deprecated("Replace by Strides(shape)") public operator fun invoke(shape: IntArray): Strides = defaultStridesCache.getOrPut(shape) { DefaultStrides(shape) } } } @ThreadLocal -private val defaultStridesCache = HashMap() \ No newline at end of file +private val defaultStridesCache = HashMap() + +/** + * Cached builder for default strides + */ +public fun Strides(shape: IntArray): Strides = defaultStridesCache.getOrPut(shape) { DefaultStrides(shape) } \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt index d948cf36f..e934c6370 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt @@ -101,8 +101,8 @@ public interface StructureND : Featured, WithShape { val bufferRepr: String = when (structure.shape.size) { 1 -> (0 until structure.shape[0]).map { structure[it] } .joinToString(prefix = "[", postfix = "]", separator = ", ") - 2 -> (0 until structure.shape[0]).joinToString(prefix = "[", postfix = "]", separator = ", ") { i -> - (0 until structure.shape[1]).joinToString(prefix = "[", postfix = "]", separator = ", ") { j -> + 2 -> (0 until structure.shape[0]).joinToString(prefix = "[\n", postfix = "\n]", separator = ",\n") { i -> + (0 until structure.shape[1]).joinToString(prefix = " [", postfix = "]", separator = ", ") { j -> structure[i, j].toString() } } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt index 799d14b3d..7e86ea73d 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/VirtualStructureND.kt @@ -5,12 +5,26 @@ package space.kscience.kmath.nd +import space.kscience.kmath.misc.UnstableKMathAPI + public open class VirtualStructureND( override val shape: Shape, public val producer: (IntArray) -> T, ) : StructureND { override fun get(index: IntArray): T { - require(check that index is in the shape boundaries) + requireIndexInShape(index, shape) return producer(index) } -} \ No newline at end of file +} + +@UnstableKMathAPI +public class VirtualDoubleStructureND( + shape: Shape, + producer: (IntArray) -> Double, +) : VirtualStructureND(shape, producer) + +@UnstableKMathAPI +public class VirtualIntStructureND( + shape: Shape, + producer: (IntArray) -> Int, +) : VirtualStructureND(shape, producer) \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt new file mode 100644 index 000000000..c9624dc4e --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt @@ -0,0 +1,32 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.nd + +public fun StructureND.roll(axis: Int, step: Int = 1): StructureND { + require(axis in shape.indices) { "Axis $axis is outside of shape dimensions: [0, ${shape.size})" } + return VirtualStructureND(shape) { index -> + val newIndex: IntArray = IntArray(index.size) { indexAxis -> + if (indexAxis == axis) { + (index[indexAxis] + step).mod(shape[indexAxis]) + } else { + index[indexAxis] + } + } + get(newIndex) + } +} + +public fun StructureND.roll(pair: Pair, vararg others: Pair): StructureND { + val axisMap: Map = mapOf(pair, *others) + require(axisMap.keys.all { it in shape.indices }) { "Some of axes ${axisMap.keys} is outside of shape dimensions: [0, ${shape.size})" } + return VirtualStructureND(shape) { index -> + val newIndex: IntArray = IntArray(index.size) { indexAxis -> + val offset = axisMap[indexAxis] ?: 0 + (index[indexAxis] + offset).mod(shape[indexAxis]) + } + get(newIndex) + } +} \ No newline at end of file diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt new file mode 100644 index 000000000..25b062b44 --- /dev/null +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt @@ -0,0 +1,28 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.nd + +import space.kscience.kmath.operations.DoubleField +import kotlin.test.Test +import kotlin.test.assertEquals + +class NdOperationsTest { + @Test + fun roll() { + val structure = DoubleField.ndAlgebra.structureND(5, 5) { index -> + index.sumOf { it.toDouble() } + } + + println(StructureND.toString(structure)) + + val rolled = structure.roll(0,-1) + + println(StructureND.toString(rolled)) + + assertEquals(4.0, rolled[0, 0]) + } + +} \ No newline at end of file diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt index dce739dc2..aac327a84 100644 --- a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt +++ b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt @@ -271,7 +271,9 @@ public object EjmlLinearSpaceDDRM : EjmlLinearSpace null - }?.let(type::cast) + }?.let{ + type.cast(it) + } } /** @@ -505,7 +507,9 @@ public object EjmlLinearSpaceFDRM : EjmlLinearSpace null - }?.let(type::cast) + }?.let{ + type.cast(it) + } } /** @@ -734,7 +738,9 @@ public object EjmlLinearSpaceDSCC : EjmlLinearSpace null - }?.let(type::cast) + }?.let{ + type.cast(it) + } } /** @@ -963,7 +969,9 @@ public object EjmlLinearSpaceFSCC : EjmlLinearSpace null - }?.let(type::cast) + }?.let{ + type.cast(it) + } } /** diff --git a/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlMatrixTest.kt b/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlMatrixTest.kt index 209bb5b27..af6284e5e 100644 --- a/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlMatrixTest.kt +++ b/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlMatrixTest.kt @@ -3,6 +3,8 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:OptIn(PerformancePitfall::class) + package space.kscience.kmath.ejml import org.ejml.data.DMatrixRMaj @@ -18,11 +20,11 @@ import kotlin.random.Random import kotlin.random.asJavaRandom import kotlin.test.* -@OptIn(PerformancePitfall::class) -fun assertMatrixEquals(expected: StructureND, actual: StructureND) { +internal fun assertMatrixEquals(expected: StructureND, actual: StructureND) { assertTrue { StructureND.contentEquals(expected, actual) } } +@OptIn(UnstableKMathAPI::class) internal class EjmlMatrixTest { private val random = Random(0) diff --git a/kmath-histograms/build.gradle.kts b/kmath-histograms/build.gradle.kts index 51271bb0a..786086c9f 100644 --- a/kmath-histograms/build.gradle.kts +++ b/kmath-histograms/build.gradle.kts @@ -1,17 +1,15 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") + id("ru.mipt.npm.gradle.mpp") id("ru.mipt.npm.gradle.native") } -kscience { - useAtomic() -} +//apply(plugin = "kotlinx-atomicfu") kotlin.sourceSets { commonMain { dependencies { api(project(":kmath-core")) + api(npmlibs.atomicfu) } } commonTest { diff --git a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt index c4eeb53cc..2c56a88a7 100644 --- a/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt +++ b/kmath-histograms/src/jvmTest/kotlin/space/kscience/kmath/histogram/TreeHistogramTest.kt @@ -6,12 +6,14 @@ package space.kscience.kmath.histogram import org.junit.jupiter.api.Test +import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.real.step import kotlin.random.Random import kotlin.test.assertEquals import kotlin.test.assertTrue +@OptIn(UnstableKMathAPI::class) class TreeHistogramTest { @Test diff --git a/kmath-memory/build.gradle.kts b/kmath-memory/build.gradle.kts index 4478e5b80..2bd6dd723 100644 --- a/kmath-memory/build.gradle.kts +++ b/kmath-memory/build.gradle.kts @@ -1,6 +1,5 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") + id("ru.mipt.npm.gradle.mpp") id("ru.mipt.npm.gradle.native") } diff --git a/kmath-optimization/build.gradle.kts b/kmath-optimization/build.gradle.kts index b920b9267..2e5bf6005 100644 --- a/kmath-optimization/build.gradle.kts +++ b/kmath-optimization/build.gradle.kts @@ -3,10 +3,6 @@ plugins { id("ru.mipt.npm.gradle.native") } -kscience { - useAtomic() -} - kotlin.sourceSets { all { languageSettings.optIn("space.kscience.kmath.misc.UnstableKMathAPI") @@ -15,6 +11,7 @@ kotlin.sourceSets { commonMain { dependencies { api(project(":kmath-coroutines")) + api(npmlibs.atomicfu) } } } diff --git a/kmath-stat/build.gradle.kts b/kmath-stat/build.gradle.kts index 41a1666f8..b458135b3 100644 --- a/kmath-stat/build.gradle.kts +++ b/kmath-stat/build.gradle.kts @@ -3,14 +3,11 @@ plugins { id("ru.mipt.npm.gradle.native") } -kscience { - useAtomic() -} - kotlin.sourceSets { commonMain { dependencies { api(project(":kmath-coroutines")) + implementation(npmlibs.atomicfu) } } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt index c96ecdc8c..a88f3e437 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt @@ -8,6 +8,7 @@ package space.kscience.kmath.stat import kotlinx.coroutines.flow.first import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.combine +import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.DoubleBuffer @@ -30,6 +31,7 @@ public fun interface Sampler { /** * Sample a bunch of values */ +@OptIn(UnstableKMathAPI::class) public fun Sampler.sampleBuffer( generator: RandomGenerator, size: Int, diff --git a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/MCScopeTest.kt b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/MCScopeTest.kt index 075d7f3e5..cca645809 100644 --- a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/MCScopeTest.kt +++ b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/MCScopeTest.kt @@ -66,7 +66,7 @@ class MCScopeTest { } - @OptIn(ObsoleteCoroutinesApi::class) + @OptIn(DelicateCoroutinesApi::class) fun compareResult(test: ATest) { val res1 = runBlocking(Dispatchers.Default) { test() } val res2 = runBlocking(newSingleThreadContext("test")) { test() } diff --git a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorFieldOpsND.kt b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorFieldOpsND.kt index 1d4d6cebd..cecbc35b8 100644 --- a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorFieldOpsND.kt +++ b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorFieldOpsND.kt @@ -117,6 +117,7 @@ public open class ViktorFieldOpsND : public val DoubleField.viktorAlgebra: ViktorFieldOpsND get() = ViktorFieldOpsND +@OptIn(UnstableKMathAPI::class) public open class ViktorFieldND( override val shape: Shape, ) : ViktorFieldOpsND(), FieldND, NumbersAddOps> { diff --git a/settings.gradle.kts b/settings.gradle.kts index b3c275810..b14c594b4 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -1,6 +1,24 @@ rootProject.name = "kmath" enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") + +dependencyResolutionManagement { + val toolsVersion: String by extra + + repositories { + mavenLocal() + maven("https://repo.kotlin.link") + mavenCentral() + gradlePluginPortal() + } + + versionCatalogs { + create("npmlibs") { + from("ru.mipt.npm:version-catalog:$toolsVersion") + } + } +} + include( ":kmath-memory", ":kmath-complex", @@ -27,4 +45,4 @@ include( ":kmath-jafama", ":examples", ":benchmarks", -) +) \ No newline at end of file -- 2.34.1 From e1276b684f5b4220b01842f325a0407d14a1415f Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 12 Jun 2022 15:19:59 +0300 Subject: [PATCH 48/59] Update better-parse --- kmath-ast/build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kmath-ast/build.gradle.kts b/kmath-ast/build.gradle.kts index 0dd625ef1..f49c2767a 100644 --- a/kmath-ast/build.gradle.kts +++ b/kmath-ast/build.gradle.kts @@ -24,7 +24,7 @@ kotlin.sourceSets { commonMain { dependencies { - api("com.github.h0tk3y.betterParse:better-parse:0.4.2") + api("com.github.h0tk3y.betterParse:better-parse:0.4.4") api(project(":kmath-core")) } } -- 2.34.1 From fabad733f4cb9436fd3dd34ea0dbb3871e0348ea Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Sun, 12 Jun 2022 15:30:10 +0300 Subject: [PATCH 49/59] Fix binaryen module creation --- .../kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt index aacb62f36..878919d8d 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/WasmBuilder.kt @@ -71,7 +71,7 @@ internal sealed class WasmBuilder>( protected open fun visitBinary(mst: TypedMst.Binary): ExpressionRef = error("Binary operation ${mst.operation} not defined in $this") - protected open fun createModule(): BinaryenModule = js("new \$module\$binaryen.Module()") + protected open fun createModule(): BinaryenModule = space.kscience.kmath.internal.binaryen.Module() protected fun visit(node: TypedMst): ExpressionRef = when (node) { is TypedMst.Constant -> visitNumber( -- 2.34.1 From 1fd8dfd7b826718df16017dc7e2960ac85dbc98d Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Mon, 13 Jun 2022 11:17:41 +0300 Subject: [PATCH 50/59] refactor Quaternions --- .../kmath/estree/internal/ESTreeBuilder.kt | 7 +- .../kscience/kmath/asm/internal/AsmBuilder.kt | 2 + kmath-complex/build.gradle.kts | 10 +- .../kscience/kmath/complex/Quaternion.kt | 133 ++++++++---------- kmath-geometry/build.gradle.kts | 2 +- .../kmath/geometry/Euclidean2DSpace.kt | 3 - .../kmath/geometry/Euclidean3DSpace.kt | 2 - 7 files changed, 68 insertions(+), 91 deletions(-) diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt index 10a6c4a16..40c446da0 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt @@ -14,11 +14,12 @@ internal class ESTreeBuilder(val bodyCallback: ESTreeBuilder.() -> BaseExp private class GeneratedExpression(val executable: dynamic, val constants: Array) : Expression { @Suppress("UNUSED_VARIABLE") override fun invoke(arguments: Map): T { - val e = executable - val c = constants + //val e = executable + //val c = constants val a = js("{}") arguments.forEach { (key, value) -> a[key.identity] = value } - return js("e(c, a)").unsafeCast() + return executable.call(constants, a).unsafeCast() + //return js("e(c, a)").unsafeCast() } } diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/AsmBuilder.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/AsmBuilder.kt index a85079fc8..a76b47ecc 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/AsmBuilder.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/AsmBuilder.kt @@ -49,5 +49,7 @@ internal abstract class AsmBuilder { * ASM Type for [space.kscience.kmath.expressions.Symbol]. */ val SYMBOL_TYPE: Type = getObjectType("space/kscience/kmath/expressions/Symbol") + + const val ARGUMENTS_NAME = "args" } } diff --git a/kmath-complex/build.gradle.kts b/kmath-complex/build.gradle.kts index ea74df646..f0ce631a5 100644 --- a/kmath-complex/build.gradle.kts +++ b/kmath-complex/build.gradle.kts @@ -19,13 +19,15 @@ readme { feature( id = "complex", - description = "Complex Numbers", ref = "src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt" - ) + ){ + "Complex numbers operations" + } feature( id = "quaternion", - description = "Quaternions", ref = "src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt" - ) + ){ + "Quaternions and their composition" + } } diff --git a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt index 3ef3428c6..85c945faf 100644 --- a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt +++ b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt @@ -16,6 +16,52 @@ import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.structures.MutableMemoryBuffer import kotlin.math.* +/** + * Represents `double`-based quaternion. + * + * @property w The first component. + * @property x The second component. + * @property y The third component. + * @property z The fourth component. + */ +public data class Quaternion( + val w: Double, val x: Double, val y: Double, val z: Double, +) { + init { + require(!w.isNaN()) { "w-component of quaternion is not-a-number" } + require(!x.isNaN()) { "x-component of quaternion is not-a-number" } + require(!y.isNaN()) { "y-component of quaternion is not-a-number" } + require(!z.isNaN()) { "z-component of quaternion is not-a-number" } + } + + /** + * Returns a string representation of this quaternion. + */ + override fun toString(): String = "($w + $x * i + $y * j + $z * k)" + + public companion object : MemorySpec { + override val objectSize: Int + get() = 32 + + override fun MemoryReader.read(offset: Int): Quaternion = + Quaternion(readDouble(offset), readDouble(offset + 8), readDouble(offset + 16), readDouble(offset + 24)) + + override fun MemoryWriter.write(offset: Int, value: Quaternion) { + writeDouble(offset, value.w) + writeDouble(offset + 8, value.x) + writeDouble(offset + 16, value.y) + writeDouble(offset + 24, value.z) + } + } +} + +public fun Quaternion(w: Number, x: Number = 0.0, y: Number = 0.0, z: Number = 0.0): Quaternion = Quaternion( + w.toDouble(), + x.toDouble(), + y.toDouble(), + z.toDouble(), +) + /** * This quaternion's conjugate. */ @@ -45,23 +91,23 @@ public val Quaternion.r: Double @OptIn(UnstableKMathAPI::class) public object QuaternionField : Field, Norm, PowerOperations, ExponentialOperations, NumbersAddOps, ScaleOperations { - override val zero: Quaternion = 0.toQuaternion() - override val one: Quaternion = 1.toQuaternion() + override val zero: Quaternion = Quaternion(0.0) + override val one: Quaternion = Quaternion(1.0) /** * The `i` quaternion unit. */ - public val i: Quaternion = Quaternion(0, 1) + public val i: Quaternion = Quaternion(0.0, 1.0, 0.0, 0.0) /** * The `j` quaternion unit. */ - public val j: Quaternion = Quaternion(0, 0, 1) + public val j: Quaternion = Quaternion(0.0, 0.0, 1.0, 0.0) /** * The `k` quaternion unit. */ - public val k: Quaternion = Quaternion(0, 0, 0, 1) + public val k: Quaternion = Quaternion(0.0, 0.0, 0.0, 1.0) override fun add(left: Quaternion, right: Quaternion): Quaternion = Quaternion(left.w + right.w, left.x + right.x, left.y + right.y, left.z + right.z) @@ -133,7 +179,7 @@ public object QuaternionField : Field, Norm, override fun exp(arg: Quaternion): Quaternion { val un = arg.x * arg.x + arg.y * arg.y + arg.z * arg.z - if (un == 0.0) return exp(arg.w).toQuaternion() + if (un == 0.0) return Quaternion(exp(arg.w)) val n1 = sqrt(un) val ea = exp(arg.w) val n2 = ea * sin(n1) / n1 @@ -158,7 +204,8 @@ public object QuaternionField : Field, Norm, return Quaternion(ln(n), th * arg.x, th * arg.y, th * arg.z) } - override operator fun Number.plus(other: Quaternion): Quaternion = Quaternion(toDouble() + other.w, other.x, other.y, other.z) + override operator fun Number.plus(other: Quaternion): Quaternion = + Quaternion(toDouble() + other.w, other.x, other.y, other.z) override operator fun Number.minus(other: Quaternion): Quaternion = Quaternion(toDouble() - other.w, -other.x, -other.y, -other.z) @@ -179,7 +226,7 @@ public object QuaternionField : Field, Norm, else -> null } - override fun number(value: Number): Quaternion = value.toQuaternion() + override fun number(value: Number): Quaternion = Quaternion(value) override fun sinh(arg: Quaternion): Quaternion = (exp(arg) - exp(-arg)) / 2.0 override fun cosh(arg: Quaternion): Quaternion = (exp(arg) + exp(-arg)) / 2.0 @@ -189,76 +236,6 @@ public object QuaternionField : Field, Norm, override fun atanh(arg: Quaternion): Quaternion = (ln(arg + one) - ln(one - arg)) / 2.0 } -/** - * Represents `double`-based quaternion. - * - * @property w The first component. - * @property x The second component. - * @property y The third component. - * @property z The fourth component. - */ -@OptIn(UnstableKMathAPI::class) -public data class Quaternion( - val w: Double, val x: Double, val y: Double, val z: Double, -) { - public constructor(w: Number, x: Number, y: Number, z: Number) : this( - w.toDouble(), - x.toDouble(), - y.toDouble(), - z.toDouble(), - ) - - public constructor(w: Number, x: Number, y: Number) : this(w.toDouble(), x.toDouble(), y.toDouble(), 0.0) - public constructor(w: Number, x: Number) : this(w.toDouble(), x.toDouble(), 0.0, 0.0) - public constructor(w: Number) : this(w.toDouble(), 0.0, 0.0, 0.0) - public constructor(wx: Complex, yz: Complex) : this(wx.re, wx.im, yz.re, yz.im) - public constructor(wx: Complex) : this(wx.re, wx.im, 0, 0) - - init { - require(!w.isNaN()) { "w-component of quaternion is not-a-number" } - require(!x.isNaN()) { "x-component of quaternion is not-a-number" } - require(!y.isNaN()) { "x-component of quaternion is not-a-number" } - require(!z.isNaN()) { "x-component of quaternion is not-a-number" } - } - - /** - * Returns a string representation of this quaternion. - */ - override fun toString(): String = "($w + $x * i + $y * j + $z * k)" - - public companion object : MemorySpec { - override val objectSize: Int - get() = 32 - - override fun MemoryReader.read(offset: Int): Quaternion = - Quaternion(readDouble(offset), readDouble(offset + 8), readDouble(offset + 16), readDouble(offset + 24)) - - override fun MemoryWriter.write(offset: Int, value: Quaternion) { - writeDouble(offset, value.w) - writeDouble(offset + 8, value.x) - writeDouble(offset + 16, value.y) - writeDouble(offset + 24, value.z) - } - } -} - -/** - * Creates a quaternion with real part equal to this real. - * - * @receiver the real part. - * @return a new quaternion. - */ -public fun Number.toQuaternion(): Quaternion = Quaternion(this) - -/** - * Creates a quaternion with `w`-component equal to `re`-component of given complex and `x`-component equal to - * `im`-component of given complex. - * - * @receiver the complex number. - * @return a new quaternion. - */ -public fun Complex.toQuaternion(): Quaternion = Quaternion(this) - /** * Creates a new buffer of quaternions with the specified [size], where each element is calculated by calling the * specified [init] function. diff --git a/kmath-geometry/build.gradle.kts b/kmath-geometry/build.gradle.kts index 7eb814683..bfe2e32a2 100644 --- a/kmath-geometry/build.gradle.kts +++ b/kmath-geometry/build.gradle.kts @@ -6,7 +6,7 @@ plugins { kotlin.sourceSets.commonMain { dependencies { - api(project(":kmath-core")) + api(projects.kmath.kmathComplex) } } diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean2DSpace.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean2DSpace.kt index d00575bcc..a83cb3ac7 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean2DSpace.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean2DSpace.kt @@ -6,12 +6,10 @@ package space.kscience.kmath.geometry import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.ScaleOperations import space.kscience.kmath.operations.invoke import kotlin.math.sqrt -@OptIn(UnstableKMathAPI::class) public interface Vector2D : Point, Vector { public val x: Double public val y: Double @@ -29,7 +27,6 @@ public interface Vector2D : Point, Vector { public val Vector2D.r: Double get() = Euclidean2DSpace { norm() } -@Suppress("FunctionName") public fun Vector2D(x: Double, y: Double): Vector2D = Vector2DImpl(x, y) private data class Vector2DImpl( diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt index e12563b46..d3b3fb15e 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt @@ -6,12 +6,10 @@ package space.kscience.kmath.geometry import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.ScaleOperations import space.kscience.kmath.operations.invoke import kotlin.math.sqrt -@OptIn(UnstableKMathAPI::class) public interface Vector3D : Point, Vector { public val x: Double public val y: Double -- 2.34.1 From 85a1e8b33f3ed3683d1e68e722ef0cf89fc43cc5 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 14 Jun 2022 16:27:32 +0300 Subject: [PATCH 51/59] New common test infrastructure --- build.gradle.kts | 14 ++- .../kscience/kmath/complex/Quaternion.kt | 79 ++++++++++---- ...aternionFieldTest.kt => QuaternionTest.kt} | 15 ++- .../kmath/geometry/Euclidean3DSpace.kt | 14 +++ .../{Projections.kt => projections.kt} | 2 + .../kscience/kmath/geometry/rotations3D.kt | 100 ++++++++++++++++++ .../kscience/kmath/geometry/RotationTest.kt | 35 ++++++ .../tensorflow/DoubleTensorFlowAlgebra.kt | 2 + settings.gradle.kts | 1 + test-utils/build.gradle.kts | 13 +++ .../commonMain/kotlin}/AlgebraicVerifier.kt | 0 .../src/commonMain/kotlin}/FieldVerifier.kt | 2 +- .../src/commonMain/kotlin}/RingVerifier.kt | 2 +- .../src/commonMain/kotlin}/SpaceVerifier.kt | 10 +- test-utils/src/commonMain/kotlin/asserts.kt | 20 ++++ 15 files changed, 279 insertions(+), 30 deletions(-) rename kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/{QuaternionFieldTest.kt => QuaternionTest.kt} (84%) rename kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/{Projections.kt => projections.kt} (97%) create mode 100644 kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt create mode 100644 kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt create mode 100644 test-utils/build.gradle.kts rename {kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils => test-utils/src/commonMain/kotlin}/AlgebraicVerifier.kt (100%) rename {kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils => test-utils/src/commonMain/kotlin}/FieldVerifier.kt (96%) rename {kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils => test-utils/src/commonMain/kotlin}/RingVerifier.kt (95%) rename {kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils => test-utils/src/commonMain/kotlin}/SpaceVerifier.kt (93%) create mode 100644 test-utils/src/commonMain/kotlin/asserts.kt diff --git a/build.gradle.kts b/build.gradle.kts index ab136bfbc..d8c591799 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -17,7 +17,7 @@ allprojects { subprojects { if (name.startsWith("kmath")) apply() - plugins.withId("org.jetbrains.dokka"){ + plugins.withId("org.jetbrains.dokka") { tasks.withType { dependsOn(tasks["assemble"]) @@ -51,6 +51,18 @@ subprojects { } } } + + plugins.withId("org.jetbrains.kotlin.multiplatform") { + configure { + sourceSets { + val commonTest by getting { + dependencies { + implementation(projects.testUtils) + } + } + } + } + } } readme.readmeTemplate = file("docs/templates/README-TEMPLATE.md") diff --git a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt index 85c945faf..359b66b20 100644 --- a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt +++ b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt @@ -24,9 +24,12 @@ import kotlin.math.* * @property y The third component. * @property z The fourth component. */ -public data class Quaternion( - val w: Double, val x: Double, val y: Double, val z: Double, -) { +public class Quaternion( + public val w: Double, + public val x: Double, + public val y: Double, + public val z: Double, +) : Buffer { init { require(!w.isNaN()) { "w-component of quaternion is not-a-number" } require(!x.isNaN()) { "x-component of quaternion is not-a-number" } @@ -39,12 +42,49 @@ public data class Quaternion( */ override fun toString(): String = "($w + $x * i + $y * j + $z * k)" - public companion object : MemorySpec { - override val objectSize: Int - get() = 32 + override val size: Int get() = 4 - override fun MemoryReader.read(offset: Int): Quaternion = - Quaternion(readDouble(offset), readDouble(offset + 8), readDouble(offset + 16), readDouble(offset + 24)) + override fun get(index: Int): Double = when (index) { + 0 -> w + 1 -> x + 2 -> y + 3 -> z + else -> error("Index $index out of bounds [0,3]") + } + + override fun iterator(): Iterator = listOf(w, x, y, z).iterator() + + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other == null || this::class != other::class) return false + + other as Quaternion + + if (w != other.w) return false + if (x != other.x) return false + if (y != other.y) return false + if (z != other.z) return false + + return true + } + + override fun hashCode(): Int { + var result = w.hashCode() + result = 31 * result + x.hashCode() + result = 31 * result + y.hashCode() + result = 31 * result + z.hashCode() + return result + } + + public companion object : MemorySpec { + override val objectSize: Int get() = 32 + + override fun MemoryReader.read(offset: Int): Quaternion = Quaternion( + readDouble(offset), + readDouble(offset + 8), + readDouble(offset + 16), + readDouble(offset + 24) + ) override fun MemoryWriter.write(offset: Int, value: Quaternion) { writeDouble(offset, value.w) @@ -66,30 +106,22 @@ public fun Quaternion(w: Number, x: Number = 0.0, y: Number = 0.0, z: Number = 0 * This quaternion's conjugate. */ public val Quaternion.conjugate: Quaternion - get() = QuaternionField { z - x * i - y * j - z * k } + get() = Quaternion(w, -x, -y, -z) /** * This quaternion's reciprocal. */ public val Quaternion.reciprocal: Quaternion get() { - QuaternionField { - val n = norm(this@reciprocal) - return conjugate / (n * n) - } + val norm2 = (w * w + x * x + y * y + z * z) + return Quaternion(w / norm2, -x / norm2, -y / norm2, -z / norm2) } -/** - * Absolute value of the quaternion. - */ -public val Quaternion.r: Double - get() = sqrt(w * w + x * x + y * y + z * z) - /** * A field of [Quaternion]. */ @OptIn(UnstableKMathAPI::class) -public object QuaternionField : Field, Norm, PowerOperations, +public object QuaternionField : Field, Norm, PowerOperations, ExponentialOperations, NumbersAddOps, ScaleOperations { override val zero: Quaternion = Quaternion(0.0) override val one: Quaternion = Quaternion(1.0) @@ -217,7 +249,12 @@ public object QuaternionField : Field, Norm, Quaternion(toDouble() * arg.w, toDouble() * arg.x, toDouble() * arg.y, toDouble() * arg.z) override fun Quaternion.unaryMinus(): Quaternion = Quaternion(-w, -x, -y, -z) - override fun norm(arg: Quaternion): Quaternion = sqrt(arg.conjugate * arg) + override fun norm(arg: Quaternion): Double = sqrt( + arg.w.pow(2) + + arg.x.pow(2) + + arg.y.pow(2) + + arg.z.pow(2) + ) override fun bindSymbolOrNull(value: String): Quaternion? = when (value) { "i" -> i diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionFieldTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt similarity index 84% rename from kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionFieldTest.kt rename to kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt index 6784f3516..fd4df736c 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionFieldTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt @@ -6,10 +6,23 @@ package space.kscience.kmath.complex import space.kscience.kmath.operations.invoke +import space.kscience.kmath.testutils.assertBufferEquals import kotlin.test.Test import kotlin.test.assertEquals -internal class QuaternionFieldTest { +internal class QuaternionTest { + + @Test + fun testNorm() { + assertEquals(2.0, QuaternionField.norm(Quaternion(1.0, 1.0, 1.0, 1.0))) + } + + @Test + fun testInverse() = QuaternionField { + val q = Quaternion(1.0, 2.0, -3.0, 4.0) + assertBufferEquals(one, q * q.reciprocal, 1e-4) + } + @Test fun testAddition() { assertEquals(Quaternion(42, 42), QuaternionField { Quaternion(16, 16) + Quaternion(26, 26) }) diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt index d3b3fb15e..c1fc74bf1 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Euclidean3DSpace.kt @@ -8,6 +8,7 @@ package space.kscience.kmath.geometry import space.kscience.kmath.linear.Point import space.kscience.kmath.operations.ScaleOperations import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.Buffer import kotlin.math.sqrt public interface Vector3D : Point, Vector { @@ -29,6 +30,19 @@ public interface Vector3D : Point, Vector { @Suppress("FunctionName") public fun Vector3D(x: Double, y: Double, z: Double): Vector3D = Vector3DImpl(x, y, z) +public fun Buffer.asVector3D(): Vector3D = object : Vector3D { + init { + require(this@asVector3D.size == 3) { "Buffer of size 3 is required for Vector3D" } + } + + override val x: Double get() = this@asVector3D[0] + override val y: Double get() = this@asVector3D[1] + override val z: Double get() = this@asVector3D[2] + + override fun toString(): String = this@asVector3D.toString() + +} + public val Vector3D.r: Double get() = Euclidean3DSpace { norm() } private data class Vector3DImpl( diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Projections.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/projections.kt similarity index 97% rename from kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Projections.kt rename to kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/projections.kt index 5e299f450..6ffc43739 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Projections.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/projections.kt @@ -5,6 +5,8 @@ package space.kscience.kmath.geometry +//TODO move vector to receiver + /** * Project vector onto a line. * @param vector to project diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt new file mode 100644 index 000000000..374315610 --- /dev/null +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt @@ -0,0 +1,100 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.geometry + +import space.kscience.kmath.complex.Quaternion +import space.kscience.kmath.complex.QuaternionField +import space.kscience.kmath.complex.reciprocal +import space.kscience.kmath.linear.LinearSpace +import space.kscience.kmath.linear.Matrix +import space.kscience.kmath.linear.linearSpace +import space.kscience.kmath.linear.matrix +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.invoke +import kotlin.math.pow +import kotlin.math.sqrt + +internal fun Vector3D.toQuaternion(): Quaternion = Quaternion(0.0, x, y, z) + +/** + * Angle in radians denoted by this quaternion rotation + */ +public val Quaternion.theta: Double get() = kotlin.math.acos(w) * 2 + +/** + * An axis of quaternion rotation + */ +public val Quaternion.vector: Vector3D + get() { + val sint2 = sqrt(1 - w * w) + + return object : Vector3D { + override val x: Double get() = this@vector.x/sint2 + override val y: Double get() = this@vector.y/sint2 + override val z: Double get() = this@vector.z/sint2 + override fun toString(): String = listOf(x, y, z).toString() + } + } + +/** + * Rotate a vector in a [Euclidean3DSpace] + */ +public fun Euclidean3DSpace.rotate(vector: Vector3D, q: Quaternion): Vector3D = with(QuaternionField) { + val p = vector.toQuaternion() + (q * p * q.reciprocal).vector +} + +/** + * Use a composition of quaternions to create a rotation + */ +public fun Euclidean3DSpace.rotate(vector: Vector3D, composition: QuaternionField.() -> Quaternion): Vector3D = + rotate(vector, QuaternionField.composition()) + +public fun Euclidean3DSpace.rotate(vector: Vector3D, matrix: Matrix): Vector3D { + require(matrix.colNum == 3 && matrix.rowNum == 3) { "Square 3x3 rotation matrix is required" } + return with(DoubleField.linearSpace) { matrix.dot(vector).asVector3D() } +} + +/** + * Convert a [Quaternion] to a rotation matrix + */ +@OptIn(UnstableKMathAPI::class) +public fun Quaternion.toRotationMatrix( + linearSpace: LinearSpace = DoubleField.linearSpace, +): Matrix { + val s = QuaternionField.norm(this).pow(-2) + return linearSpace.matrix(3, 3)( + 1.0 - 2 * s * (y * y + z * z), 2 * s * (x * y - z * w), 2 * s * (x * z + y * w), + 2 * s * (x * y + z * w), 1.0 - 2 * s * (x * x + z * z), 2 * s * (y * z - x * w), + 2 * s * (x * z - y * w), 2 * s * (y * z + x * w), 1.0 - 2 * s * (x * x + y * y) + ) +} + +/** + * taken from https://d3cw3dd2w32x2b.cloudfront.net/wp-content/uploads/2015/01/matrix-to-quat.pdf + */ +public fun Quaternion.Companion.fromRotationMatrix(matrix: Matrix): Quaternion { + val t: Double + val q = if (matrix[2, 2] < 0) { + if (matrix[0, 0] > matrix[1, 1]) { + t = 1 + matrix[0, 0] - matrix[1, 1] - matrix[2, 2] + Quaternion(t, matrix[0, 1] + matrix[1, 0], matrix[2, 0] + matrix[0, 2], matrix[1, 2] - matrix[2, 1]) + } else { + t = 1 - matrix[0, 0] + matrix[1, 1] - matrix[2, 2] + Quaternion(matrix[0, 1] + matrix[1, 0], t, matrix[1, 2] + matrix[2, 1], matrix[2, 0] - matrix[0, 2]) + } + } else { + if (matrix[0, 0] < -matrix[1, 1]) { + t = 1 - matrix[0, 0] - matrix[1, 1] + matrix[2, 2] + Quaternion(matrix[2, 0] + matrix[0, 2], matrix[1, 2] + matrix[2, 1], t, matrix[0, 1] - matrix[1, 0]) + } else { + t = 1 + matrix[0, 0] + matrix[1, 1] + matrix[2, 2] + Quaternion(matrix[1, 2] - matrix[2, 1], matrix[2, 0] - matrix[0, 2], matrix[0, 1] - matrix[1, 0], t) + } + } + return QuaternionField.invoke { q * (0.5 / sqrt(t)) } +} \ No newline at end of file diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt new file mode 100644 index 000000000..ca7226fb6 --- /dev/null +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt @@ -0,0 +1,35 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.geometry + +import space.kscience.kmath.complex.Quaternion +import space.kscience.kmath.testutils.assertBufferEquals +import kotlin.test.Test +import kotlin.test.assertEquals + +class RotationTest { + + @Test + fun rotations() = with(Euclidean3DSpace) { + val vector = Vector3D(1.0, 1.0, 1.0) + val q = Quaternion(1.0, 2.0, -3.0, 4.0) + val rotatedByQ = rotate(vector, q) + val matrix = q.toRotationMatrix() + val rotatedByM = rotate(vector,matrix) + + assertBufferEquals(rotatedByQ, rotatedByM, 1e-4) + } + + @Test + fun rotationConversion() { + + val q = Quaternion(1.0, 2.0, -3.0, 4.0) + + val matrix = q.toRotationMatrix() + + assertEquals(q, Quaternion.fromRotationMatrix(matrix)) + } +} \ No newline at end of file diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowAlgebra.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowAlgebra.kt index ecfd8d098..ad7a978a0 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowAlgebra.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/DoubleTensorFlowAlgebra.kt @@ -7,6 +7,7 @@ import org.tensorflow.op.core.Constant import org.tensorflow.types.TFloat64 import space.kscience.kmath.expressions.Symbol import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.DefaultStrides import space.kscience.kmath.nd.Shape import space.kscience.kmath.nd.StructureND @@ -74,6 +75,7 @@ public class DoubleTensorFlowAlgebra internal constructor( * * The resulting tensor is available outside of scope */ +@UnstableKMathAPI public fun DoubleField.produceWithTF( block: DoubleTensorFlowAlgebra.() -> StructureND, ): StructureND = Graph().use { graph -> diff --git a/settings.gradle.kts b/settings.gradle.kts index b14c594b4..e3c621e9a 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -20,6 +20,7 @@ dependencyResolutionManagement { } include( + ":test-utils", ":kmath-memory", ":kmath-complex", ":kmath-core", diff --git a/test-utils/build.gradle.kts b/test-utils/build.gradle.kts new file mode 100644 index 000000000..88c7ea9d0 --- /dev/null +++ b/test-utils/build.gradle.kts @@ -0,0 +1,13 @@ +plugins { + id("ru.mipt.npm.gradle.mpp") + id("ru.mipt.npm.gradle.native") +} + +kotlin.sourceSets { + commonMain { + dependencies { + api(projects.kmath.kmathCore) + api(kotlin("test")) + } + } +} diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/AlgebraicVerifier.kt b/test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt similarity index 100% rename from kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/AlgebraicVerifier.kt rename to test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/FieldVerifier.kt b/test-utils/src/commonMain/kotlin/FieldVerifier.kt similarity index 96% rename from kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/FieldVerifier.kt rename to test-utils/src/commonMain/kotlin/FieldVerifier.kt index 20a7b6a72..f4ca7506b 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/FieldVerifier.kt +++ b/test-utils/src/commonMain/kotlin/FieldVerifier.kt @@ -10,7 +10,7 @@ import space.kscience.kmath.operations.invoke import kotlin.test.assertEquals import kotlin.test.assertNotEquals -internal class FieldVerifier>( +public class FieldVerifier>( algebra: A, a: T, b: T, c: T, x: Number, ) : RingVerifier(algebra, a, b, c, x) { diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/RingVerifier.kt b/test-utils/src/commonMain/kotlin/RingVerifier.kt similarity index 95% rename from kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/RingVerifier.kt rename to test-utils/src/commonMain/kotlin/RingVerifier.kt index daf18834a..14606cb2c 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/RingVerifier.kt +++ b/test-utils/src/commonMain/kotlin/RingVerifier.kt @@ -10,7 +10,7 @@ import space.kscience.kmath.operations.ScaleOperations import space.kscience.kmath.operations.invoke import kotlin.test.assertEquals -internal open class RingVerifier(algebra: A, a: T, b: T, c: T, x: Number) : +public open class RingVerifier(algebra: A, a: T, b: T, c: T, x: Number) : SpaceVerifier(algebra, a, b, c, x) where A : Ring, A : ScaleOperations { override fun verify() { diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/SpaceVerifier.kt b/test-utils/src/commonMain/kotlin/SpaceVerifier.kt similarity index 93% rename from kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/SpaceVerifier.kt rename to test-utils/src/commonMain/kotlin/SpaceVerifier.kt index 951197fc6..d761a3775 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/testutils/SpaceVerifier.kt +++ b/test-utils/src/commonMain/kotlin/SpaceVerifier.kt @@ -11,12 +11,12 @@ import space.kscience.kmath.operations.invoke import kotlin.test.assertEquals import kotlin.test.assertNotEquals -internal open class SpaceVerifier( +public open class SpaceVerifier( override val algebra: S, - val a: T, - val b: T, - val c: T, - val x: Number, + public val a: T, + public val b: T, + public val c: T, + public val x: Number, ) : AlgebraicVerifier> where S : Ring, S : ScaleOperations { override fun verify() { algebra { diff --git a/test-utils/src/commonMain/kotlin/asserts.kt b/test-utils/src/commonMain/kotlin/asserts.kt new file mode 100644 index 000000000..8e7d1ae23 --- /dev/null +++ b/test-utils/src/commonMain/kotlin/asserts.kt @@ -0,0 +1,20 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package space.kscience.kmath.testutils + +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.indices +import kotlin.test.assertEquals +import kotlin.test.fail + +public fun assertBufferEquals(expected: Buffer, result: Buffer, tolerance: Double = 1e-4) { + if (expected.size != result.size) { + fail("Expected size is ${expected.size}, but the result size is ${result.size}") + } + expected.indices.forEach { + assertEquals(expected[it], result[it], tolerance) + } +} \ No newline at end of file -- 2.34.1 From b09127f090c2b9df283eae2bbf689a38bae9b8f0 Mon Sep 17 00:00:00 2001 From: Iaroslav Postovalov Date: Tue, 14 Jun 2022 22:52:47 +0700 Subject: [PATCH 52/59] Fix name clash in strict mode; replace eval with new Function --- .../space/kscience/kmath/estree/estree.kt | 2 +- .../kmath/estree/internal/ESTreeBuilder.kt | 28 +++++++------------ .../internal/estree/estree.extensions.kt | 5 +++- 3 files changed, 15 insertions(+), 20 deletions(-) diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt index a8b1aa2e1..240acf1d7 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/estree.kt @@ -36,7 +36,7 @@ public fun MST.compileToExpression(algebra: Algebra): Expression ) } - return ESTreeBuilder { visit(typed) }.instance + return ESTreeBuilder { visit(typed) }.instance } /** diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt index 40c446da0..16a59d273 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/ESTreeBuilder.kt @@ -14,37 +14,28 @@ internal class ESTreeBuilder(val bodyCallback: ESTreeBuilder.() -> BaseExp private class GeneratedExpression(val executable: dynamic, val constants: Array) : Expression { @Suppress("UNUSED_VARIABLE") override fun invoke(arguments: Map): T { - //val e = executable - //val c = constants + val e = executable + val c = constants val a = js("{}") arguments.forEach { (key, value) -> a[key.identity] = value } - return executable.call(constants, a).unsafeCast() - //return js("e(c, a)").unsafeCast() + return js("e(c, a)").unsafeCast() } } + @Suppress("UNUSED_VARIABLE") val instance: Expression by lazy { val node = Program( sourceType = "script", - VariableDeclaration( - kind = "var", - VariableDeclarator( - id = Identifier("executable"), - init = FunctionExpression( - params = arrayOf(Identifier("constants"), Identifier("arguments")), - body = BlockStatement(ReturnStatement(bodyCallback())), - ), - ), - ), + ReturnStatement(bodyCallback()) ) - eval(generate(node)) - GeneratedExpression(js("executable"), constants.toTypedArray()) + val code = generate(node) + GeneratedExpression(js("new Function('constants', 'arguments_0', code)"), constants.toTypedArray()) } private val constants = mutableListOf() - fun constant(value: Any?) = when { + fun constant(value: Any?): BaseExpression = when { value == null || jsTypeOf(value) == "number" || jsTypeOf(value) == "string" || jsTypeOf(value) == "boolean" -> SimpleLiteral(value) @@ -62,7 +53,8 @@ internal class ESTreeBuilder(val bodyCallback: ESTreeBuilder.() -> BaseExp } } - fun variable(name: Symbol): BaseExpression = call(getOrFail, Identifier("arguments"), SimpleLiteral(name.identity)) + fun variable(name: Symbol): BaseExpression = + call(getOrFail, Identifier("arguments_0"), SimpleLiteral(name.identity)) fun call(function: Function, vararg args: BaseExpression): BaseExpression = SimpleCallExpression( optional = false, diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.extensions.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.extensions.kt index 3aa31f921..5b1ce914e 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.extensions.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.extensions.kt @@ -3,6 +3,8 @@ * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. */ +@file:Suppress("unused") + package space.kscience.kmath.internal.estree internal fun Program(sourceType: String, vararg body: dynamic) = object : Program { @@ -28,9 +30,10 @@ internal fun Identifier(name: String) = object : Identifier { override var name = name } -internal fun FunctionExpression(params: Array, body: BlockStatement) = object : FunctionExpression { +internal fun FunctionExpression(id: Identifier?, params: Array, body: BlockStatement) = object : FunctionExpression { override var params = params override var type = "FunctionExpression" + override var id: Identifier? = id override var body = body } -- 2.34.1 From b5031121ce9ef7ea0c0aae3796da8e736074a083 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 14 Jun 2022 19:31:13 +0300 Subject: [PATCH 53/59] up build tools --- gradle.properties | 2 +- .../kotlin/space/kscience/kmath/geometry/RotationTest.kt | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/gradle.properties b/gradle.properties index 9cdd7801c..5202289fa 100644 --- a/gradle.properties +++ b/gradle.properties @@ -12,4 +12,4 @@ org.gradle.configureondemand=true org.gradle.parallel=true org.gradle.jvmargs=-Xmx4096m -toolsVersion=0.11.6-kotlin-1.7.0 +toolsVersion=0.11.7-kotlin-1.7.0 diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt index ca7226fb6..abe26d398 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt @@ -7,6 +7,7 @@ package space.kscience.kmath.geometry import space.kscience.kmath.complex.Quaternion import space.kscience.kmath.testutils.assertBufferEquals +import kotlin.test.Ignore import kotlin.test.Test import kotlin.test.assertEquals @@ -24,6 +25,7 @@ class RotationTest { } @Test + @Ignore fun rotationConversion() { val q = Quaternion(1.0, 2.0, -3.0, 4.0) -- 2.34.1 From a1267d84ac43ca18d543c44c81514a73f990d50c Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Tue, 14 Jun 2022 20:58:13 +0300 Subject: [PATCH 54/59] Fix quaternion rotation tests --- .../kscience/kmath/complex/Quaternion.kt | 2 + .../space/kscience/kmath/nd/Structure2D.kt | 4 ++ .../kscience/kmath/geometry/rotations3D.kt | 60 ++++++++++++------- .../kscience/kmath/geometry/RotationTest.kt | 10 ++-- 4 files changed, 48 insertions(+), 28 deletions(-) diff --git a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt index 359b66b20..0305bfc88 100644 --- a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt +++ b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Quaternion.kt @@ -117,6 +117,8 @@ public val Quaternion.reciprocal: Quaternion return Quaternion(w / norm2, -x / norm2, -y / norm2, -z / norm2) } +public fun Quaternion.normalized(): Quaternion = with(QuaternionField){ this@normalized / norm(this@normalized) } + /** * A field of [Quaternion]. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure2D.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure2D.kt index cf8559869..a2fd83474 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure2D.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure2D.kt @@ -138,6 +138,10 @@ private class MutableStructure2DWrapper(val structure: MutableStructureND) override fun equals(other: Any?): Boolean = false override fun hashCode(): Int = 0 + + override fun toString(): String { + return StructureND.toString(structure) + } } /** diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt index 374315610..67c3666ed 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/rotations3D.kt @@ -14,7 +14,6 @@ import space.kscience.kmath.linear.linearSpace import space.kscience.kmath.linear.matrix import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.operations.invoke import kotlin.math.pow import kotlin.math.sqrt @@ -33,9 +32,9 @@ public val Quaternion.vector: Vector3D val sint2 = sqrt(1 - w * w) return object : Vector3D { - override val x: Double get() = this@vector.x/sint2 - override val y: Double get() = this@vector.y/sint2 - override val z: Double get() = this@vector.z/sint2 + override val x: Double get() = this@vector.x / sint2 + override val y: Double get() = this@vector.y / sint2 + override val z: Double get() = this@vector.z / sint2 override fun toString(): String = listOf(x, y, z).toString() } } @@ -75,26 +74,43 @@ public fun Quaternion.toRotationMatrix( } /** - * taken from https://d3cw3dd2w32x2b.cloudfront.net/wp-content/uploads/2015/01/matrix-to-quat.pdf + * taken from https://www.euclideanspace.com/maths/geometry/rotations/conversions/matrixToQuaternion/ */ public fun Quaternion.Companion.fromRotationMatrix(matrix: Matrix): Quaternion { - val t: Double - val q = if (matrix[2, 2] < 0) { - if (matrix[0, 0] > matrix[1, 1]) { - t = 1 + matrix[0, 0] - matrix[1, 1] - matrix[2, 2] - Quaternion(t, matrix[0, 1] + matrix[1, 0], matrix[2, 0] + matrix[0, 2], matrix[1, 2] - matrix[2, 1]) - } else { - t = 1 - matrix[0, 0] + matrix[1, 1] - matrix[2, 2] - Quaternion(matrix[0, 1] + matrix[1, 0], t, matrix[1, 2] + matrix[2, 1], matrix[2, 0] - matrix[0, 2]) - } + require(matrix.colNum == 3 && matrix.rowNum == 3) { "Rotation matrix should be 3x3 but is ${matrix.rowNum}x${matrix.colNum}" } + val trace = matrix[0, 0] + matrix[1, 1] + matrix[2, 2] + + return if (trace > 0) { + val s = sqrt(trace + 1.0) * 2 // S=4*qw + Quaternion( + w = 0.25 * s, + x = (matrix[2, 1] - matrix[1, 2]) / s, + y = (matrix[0, 2] - matrix[2, 0]) / s, + z = (matrix[1, 0] - matrix[0, 1]) / s, + ) + } else if ((matrix[0, 0] > matrix[1, 1]) && (matrix[0, 0] > matrix[2, 2])) { + val s = sqrt(1.0 + matrix[0, 0] - matrix[1, 1] - matrix[2, 2]) * 2 // S=4*qx + Quaternion( + w = (matrix[2, 1] - matrix[1, 2]) / s, + x = 0.25 * s, + y = (matrix[0, 1] + matrix[1, 0]) / s, + z = (matrix[0, 2] + matrix[2, 0]) / s, + ) + } else if (matrix[1, 1] > matrix[2, 2]) { + val s = sqrt(1.0 + matrix[1, 1] - matrix[0, 0] - matrix[2, 2]) * 2 // S=4*qy + Quaternion( + w = (matrix[0, 2] - matrix[2, 0]) / s, + x = (matrix[0, 1] + matrix[1, 0]) / s, + y = 0.25 * s, + z = (matrix[1, 2] + matrix[2, 1]) / s, + ) } else { - if (matrix[0, 0] < -matrix[1, 1]) { - t = 1 - matrix[0, 0] - matrix[1, 1] + matrix[2, 2] - Quaternion(matrix[2, 0] + matrix[0, 2], matrix[1, 2] + matrix[2, 1], t, matrix[0, 1] - matrix[1, 0]) - } else { - t = 1 + matrix[0, 0] + matrix[1, 1] + matrix[2, 2] - Quaternion(matrix[1, 2] - matrix[2, 1], matrix[2, 0] - matrix[0, 2], matrix[0, 1] - matrix[1, 0], t) - } + val s = sqrt(1.0 + matrix[2, 2] - matrix[0, 0] - matrix[1, 1]) * 2 // S=4*qz + Quaternion( + w = (matrix[1, 0] - matrix[0, 1]) / s, + x = (matrix[0, 2] + matrix[2, 0]) / s, + y = (matrix[1, 2] + matrix[2, 1]) / s, + z = 0.25 * s, + ) } - return QuaternionField.invoke { q * (0.5 / sqrt(t)) } } \ No newline at end of file diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt index abe26d398..89b69d0f2 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/RotationTest.kt @@ -6,17 +6,16 @@ package space.kscience.kmath.geometry import space.kscience.kmath.complex.Quaternion +import space.kscience.kmath.complex.normalized import space.kscience.kmath.testutils.assertBufferEquals -import kotlin.test.Ignore import kotlin.test.Test -import kotlin.test.assertEquals class RotationTest { @Test fun rotations() = with(Euclidean3DSpace) { val vector = Vector3D(1.0, 1.0, 1.0) - val q = Quaternion(1.0, 2.0, -3.0, 4.0) + val q = Quaternion(1.0, 2.0, -3.0, 4.0).normalized() val rotatedByQ = rotate(vector, q) val matrix = q.toRotationMatrix() val rotatedByM = rotate(vector,matrix) @@ -25,13 +24,12 @@ class RotationTest { } @Test - @Ignore fun rotationConversion() { - val q = Quaternion(1.0, 2.0, -3.0, 4.0) + val q = Quaternion(1.0, 2.0, -3.0, 4.0).normalized() val matrix = q.toRotationMatrix() - assertEquals(q, Quaternion.fromRotationMatrix(matrix)) + assertBufferEquals(q, Quaternion.fromRotationMatrix(matrix)) } } \ No newline at end of file -- 2.34.1 From 5846f42141a210bef8ba873030f9566ebc14c5e9 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 15 Jul 2022 15:21:49 +0300 Subject: [PATCH 55/59] Grand derivative refactoring. Phase 1 --- .../kscience/kmath/expressions/DSCompiler.kt | 90 +- .../kmath/expressions/DerivativeStructure.kt | 191 ++-- .../DerivativeStructureExpression.kt | 327 +++--- .../kscience/kmath/linear/LinearSpace.kt | 2 +- .../space/kscience/kmath/misc/annotations.kt | 2 +- .../space/kscience/kmath/nd/BufferND.kt | 2 +- .../space/kscience/kmath/nd/StructureND.kt | 4 +- .../kmath/operations/DoubleBufferOps.kt | 4 +- .../kmath/operations/bufferOperation.kt | 26 +- .../space/kscience/kmath/structures/Buffer.kt | 8 +- .../space/kscience/kmath/ejml/_generated.kt | 1003 ----------------- .../histogram/UniformHistogramGroupND.kt | 6 +- .../kmath/multik/MultikDoubleAlgebra.kt | 7 + .../space/kscience/kmath/stat/Sampler.kt | 2 +- 14 files changed, 311 insertions(+), 1363 deletions(-) delete mode 100644 kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt index bb88ce52c..e0050cf03 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt @@ -5,11 +5,11 @@ package space.kscience.kmath.expressions + import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.structures.MutableBufferFactory -import kotlin.math.max import kotlin.math.min internal fun MutableBuffer.fill(element: T, fromIndex: Int = 0, toIndex: Int = size) { @@ -54,7 +54,7 @@ internal fun MutableBuffer.fill(element: T, fromIndex: Int = 0, toIndex: * @property order Derivation order. * @see DerivativeStructure */ -internal class DSCompiler> internal constructor( +class DSCompiler> internal constructor( val algebra: A, val bufferFactory: MutableBufferFactory, val freeParameters: Int, @@ -120,8 +120,7 @@ internal class DSCompiler> internal constructor( * This number includes the single 0 order derivative element, which is * guaranteed to be stored in the first element of the array. */ - val size: Int - get() = sizes[freeParameters][order] + val size: Int get() = sizes[freeParameters][order] /** * Get the index of a partial derivative in the array. @@ -178,7 +177,7 @@ internal fun DSCompiler.ln( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : ExponentialOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -211,7 +210,7 @@ internal fun DSCompiler.pow( operandOffset: Int, n: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : PowerOperations = algebra { if (n == 0) { // special case, x^0 = 1 for all x @@ -267,7 +266,7 @@ internal fun DSCompiler.exp( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Ring, A : ScaleOperations, A : ExponentialOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -290,7 +289,7 @@ internal fun DSCompiler.sqrt( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : PowerOperations = algebra { // create the function value and derivatives // [x^(1/n), (1/n)x^((1/n)-1), (1-n)/n^2x^((1/n)-2), ... ] @@ -351,7 +350,7 @@ internal fun DSCompiler.pow( operandOffset: Int, p: Double, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Ring, A : NumericAlgebra, A : PowerOperations, A : ScaleOperations = algebra { // create the function value and derivatives // [x^p, px^(p-1), p(p-1)x^(p-2), ... ] @@ -387,7 +386,7 @@ internal fun DSCompiler.tan( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Ring, A : TrigonometricOperations, A : ScaleOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -469,7 +468,7 @@ internal fun DSCompiler.sin( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Ring, A : ScaleOperations, A : TrigonometricOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -497,7 +496,7 @@ internal fun DSCompiler.acos( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : TrigonometricOperations, A : PowerOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -559,7 +558,7 @@ internal fun DSCompiler.asin( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : TrigonometricOperations, A : PowerOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -618,7 +617,7 @@ internal fun DSCompiler.atan( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : TrigonometricOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -678,7 +677,7 @@ internal fun DSCompiler.cosh( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Ring, A : ScaleOperations, A : ExponentialOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -708,7 +707,7 @@ internal fun DSCompiler.tanh( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : ExponentialOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -765,7 +764,7 @@ internal fun DSCompiler.acosh( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : ExponentialOperations, A : PowerOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -857,7 +856,7 @@ internal fun DSCompiler.sinh( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : ExponentialOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -964,7 +963,7 @@ internal fun DSCompiler.asinh( operand: Buffer, operandOffset: Int, result: MutableBuffer, - resultOffset: Int + resultOffset: Int, ) where A : Field, A : ExponentialOperations, A : PowerOperations = algebra { // create the function value and derivatives val function = bufferFactory(1 + order) { zero } @@ -1109,59 +1108,6 @@ internal fun DSCompiler.atanh( compose(operand, operandOffset, function, result, resultOffset) } -/** - * Get the compiler for number of free parameters and order. - * - * @param parameters number of free parameters. - * @param order derivation order. - * @return cached rules set. - */ -internal fun > getCompiler( - algebra: A, - bufferFactory: MutableBufferFactory, - parameters: Int, - order: Int -): DSCompiler { - // get the cached compilers - val cache: Array?>>? = null - - // we need to create more compilers - val maxParameters: Int = max(parameters, cache?.size ?: 0) - val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) - val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } - - if (cache != null) { - // preserve the already created compilers - for (i in cache.indices) { - cache[i].copyInto(newCache[i], endIndex = cache[i].size) - } - } - - // create the array in increasing diagonal order - - // create the array in increasing diagonal order - for (diag in 0..parameters + order) { - for (o in max(0, diag - parameters)..min(order, diag)) { - val p: Int = diag - o - if (newCache[p][o] == null) { - val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! - val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! - - newCache[p][o] = DSCompiler( - algebra, - bufferFactory, - p, - o, - valueCompiler, - derivativeCompiler, - ) - } - } - } - - return newCache[parameters][order]!! -} - /** * Compile the sizes array. * diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt index a1a6354f0..01c045cdb 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt @@ -6,10 +6,9 @@ package space.kscience.kmath.expressions import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.NumericAlgebra import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.structures.MutableBuffer +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.asBuffer /** * Class representing both the value and the differentials of a function. @@ -28,128 +27,29 @@ import space.kscience.kmath.structures.MutableBuffer * [Commons Math's `DerivativeStructure`](https://github.com/apache/commons-math/blob/924f6c357465b39beb50e3c916d5eb6662194175/commons-math-legacy/src/main/java/org/apache/commons/math4/legacy/analysis/differentiation/DerivativeStructure.java). */ @UnstableKMathAPI -public open class DerivativeStructure internal constructor( - internal val derivativeAlgebra: DerivativeStructureRing, - internal val compiler: DSCompiler, -) where A : Ring, A : NumericAlgebra, A : ScaleOperations { - /** - * Combined array holding all values. - */ - internal var data: MutableBuffer = - derivativeAlgebra.bufferFactory(compiler.size) { derivativeAlgebra.algebra.zero } +public open class DerivativeStructure> @PublishedApi internal constructor( + private val derivativeAlgebra: DerivativeStructureAlgebra, + @PublishedApi internal val data: Buffer, +) { - /** - * Build an instance with all values and derivatives set to 0. - * - * @param parameters number of free parameters. - * @param order derivation order. - */ - public constructor ( - derivativeAlgebra: DerivativeStructureRing, - parameters: Int, - order: Int, - ) : this( - derivativeAlgebra, - getCompiler(derivativeAlgebra.algebra, derivativeAlgebra.bufferFactory, parameters, order), - ) - - /** - * Build an instance representing a constant value. - * - * @param parameters number of free parameters. - * @param order derivation order. - * @param value value of the constant. - * @see DerivativeStructure - */ - public constructor ( - derivativeAlgebra: DerivativeStructureRing, - parameters: Int, - order: Int, - value: T, - ) : this( - derivativeAlgebra, - parameters, - order, - ) { - data[0] = value - } - - /** - * Build an instance representing a variable. - * - * Instances built using this constructor are considered to be the free variables with respect to which - * differentials are computed. As such, their differential with respect to themselves is +1. - * - * @param parameters number of free parameters. - * @param order derivation order. - * @param index index of the variable (from 0 to `parameters - 1`). - * @param value value of the variable. - */ - public constructor ( - derivativeAlgebra: DerivativeStructureRing, - parameters: Int, - order: Int, - index: Int, - value: T, - ) : this(derivativeAlgebra, parameters, order, value) { - require(index < parameters) { "number is too large: $index >= $parameters" } - - if (order > 0) { - // the derivative of the variable with respect to itself is 1. - data[getCompiler(derivativeAlgebra.algebra, derivativeAlgebra.bufferFactory, index, order).size] = - derivativeAlgebra.algebra.one - } - } - - /** - * Build an instance from all its derivatives. - * - * @param parameters number of free parameters. - * @param order derivation order. - * @param derivatives derivatives sorted according to [DSCompiler.getPartialDerivativeIndex]. - */ - public constructor ( - derivativeAlgebra: DerivativeStructureRing, - parameters: Int, - order: Int, - vararg derivatives: T, - ) : this( - derivativeAlgebra, - parameters, - order, - ) { - require(derivatives.size == data.size) { "dimension mismatch: ${derivatives.size} and ${data.size}" } - data = derivativeAlgebra.bufferFactory(data.size) { derivatives[it] } - } - - /** - * Copy constructor. - * - * @param ds instance to copy. - */ - internal constructor(ds: DerivativeStructure) : this(ds.derivativeAlgebra, ds.compiler) { - this.data = ds.data.copy() - } + public val compiler: DSCompiler get() = derivativeAlgebra.compiler /** * The number of free parameters. */ - public val freeParameters: Int - get() = compiler.freeParameters + public val freeParameters: Int get() = compiler.freeParameters /** * The derivation order. */ - public val order: Int - get() = compiler.order + public val order: Int get() = compiler.order /** * The value part of the derivative structure. * * @see getPartialDerivative */ - public val value: T - get() = data[0] + public val value: T get() = data[0] /** * Get a partial derivative. @@ -183,4 +83,75 @@ public open class DerivativeStructure internal constructor( public override fun hashCode(): Int = 227 + 229 * freeParameters + 233 * order + 239 * data.hashCode() + + public companion object { + + /** + * Build an instance representing a variable. + * + * Instances built using this constructor are considered to be the free variables with respect to which + * differentials are computed. As such, their differential with respect to themselves is +1. + */ + public fun > variable( + derivativeAlgebra: DerivativeStructureAlgebra, + index: Int, + value: T, + ): DerivativeStructure { + val compiler = derivativeAlgebra.compiler + require(index < compiler.freeParameters) { "number is too large: $index >= ${compiler.freeParameters}" } + return DerivativeStructure(derivativeAlgebra, derivativeAlgebra.bufferForVariable(index, value)) + } + + /** + * Build an instance from all its derivatives. + * + * @param derivatives derivatives sorted according to [DSCompiler.getPartialDerivativeIndex]. + */ + public fun > ofDerivatives( + derivativeAlgebra: DerivativeStructureAlgebra, + vararg derivatives: T, + ): DerivativeStructure { + val compiler = derivativeAlgebra.compiler + require(derivatives.size == compiler.size) { "dimension mismatch: ${derivatives.size} and ${compiler.size}" } + val data = derivatives.asBuffer() + + return DerivativeStructure( + derivativeAlgebra, + data + ) + } + } +} + +@OptIn(UnstableKMathAPI::class) +private fun > DerivativeStructureAlgebra.bufferForVariable(index: Int, value: T): Buffer { + val buffer = bufferFactory(compiler.size) { algebra.zero } + buffer[0] = value + if (compiler.order > 0) { + // the derivative of the variable with respect to itself is 1. + + val indexOfDerivative = compiler.getPartialDerivativeIndex(*IntArray(numberOfVariables).apply { + set(index, 1) + }) + + buffer[indexOfDerivative] = algebra.one + } + return buffer +} + +/** + * A class implementing both [DerivativeStructure] and [Symbol]. + */ +@UnstableKMathAPI +public class DerivativeStructureSymbol> internal constructor( + derivativeAlgebra: DerivativeStructureAlgebra, + index: Int, + symbol: Symbol, + value: T, +) : Symbol by symbol, DerivativeStructure( + derivativeAlgebra, derivativeAlgebra.bufferForVariable(index, value) +) { + override fun toString(): String = symbol.toString() + override fun equals(other: Any?): Boolean = (other as? Symbol) == symbol + override fun hashCode(): Int = symbol.hashCode() } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt index f91fb55e8..638057921 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt @@ -7,83 +7,89 @@ package space.kscience.kmath.expressions import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.structures.MutableBufferFactory -import space.kscience.kmath.structures.indices +import kotlin.math.max +import kotlin.math.min -/** - * A class implementing both [DerivativeStructure] and [Symbol]. - */ @UnstableKMathAPI -public class DerivativeStructureSymbol( - derivativeAlgebra: DerivativeStructureRing, - size: Int, - order: Int, - index: Int, - symbol: Symbol, - value: T, -) : Symbol by symbol, DerivativeStructure( - derivativeAlgebra, - size, - order, - index, - value -) where A : Ring, A : NumericAlgebra, A : ScaleOperations { - override fun toString(): String = symbol.toString() - override fun equals(other: Any?): Boolean = (other as? Symbol) == symbol - override fun hashCode(): Int = symbol.hashCode() -} - -/** - * A ring over [DerivativeStructure]. - * - * @property order The derivation order. - * @param bindings The map of bindings values. All bindings are considered free parameters. - */ -@UnstableKMathAPI -public open class DerivativeStructureRing( +public abstract class DerivativeStructureAlgebra>( public val algebra: A, public val bufferFactory: MutableBufferFactory, public val order: Int, bindings: Map, -) : Ring>, ScaleOperations>, - NumericAlgebra>, - ExpressionAlgebra>, - NumbersAddOps> where A : Ring, A : NumericAlgebra, A : ScaleOperations { +) : ExpressionAlgebra> { + public val numberOfVariables: Int = bindings.size - override val zero: DerivativeStructure by lazy { - DerivativeStructure( - this, - numberOfVariables, - order, - ) - } - override val one: DerivativeStructure by lazy { - DerivativeStructure( - this, - numberOfVariables, - order, - algebra.one, - ) - } + /** + * Get the compiler for number of free parameters and order. + * + * @return cached rules set. + */ + @PublishedApi + internal val compiler: DSCompiler by lazy { + // get the cached compilers + val cache: Array?>>? = null - override fun number(value: Number): DerivativeStructure = const(algebra.number(value)) + // we need to create more compilers + val maxParameters: Int = max(numberOfVariables, cache?.size ?: 0) + val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) + val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } + + if (cache != null) { + // preserve the already created compilers + for (i in cache.indices) { + cache[i].copyInto(newCache[i], endIndex = cache[i].size) + } + } + + // create the array in increasing diagonal order + for (diag in 0..numberOfVariables + order) { + for (o in max(0, diag - numberOfVariables)..min(order, diag)) { + val p: Int = diag - o + if (newCache[p][o] == null) { + val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! + val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! + + newCache[p][o] = DSCompiler( + algebra, + bufferFactory, + p, + o, + valueCompiler, + derivativeCompiler, + ) + } + } + } + + return@lazy newCache[numberOfVariables][order]!! + } private val variables: Map> = bindings.entries.mapIndexed { index, (key, value) -> key to DerivativeStructureSymbol( this, - numberOfVariables, - order, index, key, value, ) }.toMap() - public override fun const(value: T): DerivativeStructure = - DerivativeStructure(this, numberOfVariables, order, value) + + + public override fun const(value: T): DerivativeStructure { + val buffer = bufferFactory(compiler.size) { algebra.zero } + buffer[0] = value + + return DerivativeStructure( + this, + buffer + ) + } override fun bindSymbolOrNull(value: String): DerivativeStructureSymbol? = variables[StringSymbol(value)] @@ -103,54 +109,99 @@ public open class DerivativeStructureRing( public fun DerivativeStructure.derivative(vararg symbols: Symbol): T = derivative(symbols.toList()) +} + + +/** + * A ring over [DerivativeStructure]. + * + * @property order The derivation order. + * @param bindings The map of bindings values. All bindings are considered free parameters. + */ +@UnstableKMathAPI +public open class DerivativeStructureRing( + algebra: A, + bufferFactory: MutableBufferFactory, + order: Int, + bindings: Map, +) : DerivativeStructureAlgebra(algebra, bufferFactory, order, bindings), + Ring>, ScaleOperations>, + NumericAlgebra>, + NumbersAddOps> where A : Ring, A : NumericAlgebra, A : ScaleOperations { + + override fun bindSymbolOrNull(value: String): DerivativeStructureSymbol? = + super.bindSymbolOrNull(value) + override fun DerivativeStructure.unaryMinus(): DerivativeStructure { - val ds = DerivativeStructure(this@DerivativeStructureRing, compiler) - for (i in ds.data.indices) { - ds.data[i] = algebra { -data[i] } - } - return ds + val newData = algebra { data.map(bufferFactory) { -it } } + return DerivativeStructure(this@DerivativeStructureRing, newData) } + /** + * Create a copy of given [Buffer] and modify it according to [block] + */ + protected inline fun DerivativeStructure.transformDataBuffer(block: DSCompiler.(MutableBuffer) -> Unit): DerivativeStructure { + val newData = bufferFactory(compiler.size) { data[it] } + compiler.block(newData) + return DerivativeStructure(this@DerivativeStructureRing, newData) + } + + protected fun DerivativeStructure.mapData(block: (T) -> T): DerivativeStructure { + val newData: Buffer = data.map(bufferFactory, block) + return DerivativeStructure(this@DerivativeStructureRing, newData) + } + + protected fun DerivativeStructure.mapDataIndexed(block: (Int, T) -> T): DerivativeStructure { + val newData: Buffer = data.mapIndexed(bufferFactory, block) + return DerivativeStructure(this@DerivativeStructureRing, newData) + } + + override val zero: DerivativeStructure by lazy { + const(algebra.zero) + } + + override val one: DerivativeStructure by lazy { + const(algebra.one) + } + + override fun number(value: Number): DerivativeStructure = const(algebra.number(value)) + override fun add(left: DerivativeStructure, right: DerivativeStructure): DerivativeStructure { left.compiler.checkCompatibility(right.compiler) - val ds = DerivativeStructure(left) - left.compiler.add(left.data, 0, right.data, 0, ds.data, 0) - return ds + return left.transformDataBuffer { result -> + add(left.data, 0, right.data, 0, result, 0) + } } - override fun scale(a: DerivativeStructure, value: Double): DerivativeStructure { - val ds = DerivativeStructure(a) - for (i in ds.data.indices) { - ds.data[i] = algebra { ds.data[i].times(value) } - } - return ds + override fun scale(a: DerivativeStructure, value: Double): DerivativeStructure = algebra { + a.mapData { it.times(value) } } override fun multiply( left: DerivativeStructure, - right: DerivativeStructure + right: DerivativeStructure, ): DerivativeStructure { left.compiler.checkCompatibility(right.compiler) - val result = DerivativeStructure(this, left.compiler) - left.compiler.multiply(left.data, 0, right.data, 0, result.data, 0) - return result + return left.transformDataBuffer { result -> + multiply(left.data, 0, right.data, 0, result, 0) + } } override fun DerivativeStructure.minus(arg: DerivativeStructure): DerivativeStructure { compiler.checkCompatibility(arg.compiler) - val ds = DerivativeStructure(this) - compiler.subtract(data, 0, arg.data, 0, ds.data, 0) - return ds + return transformDataBuffer { result -> + subtract(data, 0, arg.data, 0, result, 0) + } } - override operator fun DerivativeStructure.plus(other: Number): DerivativeStructure { - val ds = DerivativeStructure(this) - ds.data[0] = algebra { ds.data[0] + number(other) } - return ds + override operator fun DerivativeStructure.plus(other: Number): DerivativeStructure = algebra { + transformDataBuffer { + it[0] += number(other) + } } override operator fun DerivativeStructure.minus(other: Number): DerivativeStructure = - this + -other.toDouble() + this + (-other.toDouble()) override operator fun Number.plus(other: DerivativeStructure): DerivativeStructure = other + this override operator fun Number.minus(other: DerivativeStructure): DerivativeStructure = other - this @@ -194,119 +245,85 @@ public class DerivativeStructureField>( override fun divide(left: DerivativeStructure, right: DerivativeStructure): DerivativeStructure { left.compiler.checkCompatibility(right.compiler) - val result = DerivativeStructure(this, left.compiler) - left.compiler.divide(left.data, 0, right.data, 0, result.data, 0) - return result + return left.transformDataBuffer { result -> + left.compiler.divide(left.data, 0, right.data, 0, result, 0) + } } - override fun sin(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.sin(arg.data, 0, result.data, 0) - return result + override fun sin(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + sin(arg.data, 0, result, 0) } - override fun cos(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.cos(arg.data, 0, result.data, 0) - return result + override fun cos(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + cos(arg.data, 0, result, 0) } - override fun tan(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.tan(arg.data, 0, result.data, 0) - return result + override fun tan(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + tan(arg.data, 0, result, 0) } - override fun asin(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.asin(arg.data, 0, result.data, 0) - return result + override fun asin(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + asin(arg.data, 0, result, 0) } - override fun acos(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.acos(arg.data, 0, result.data, 0) - return result + override fun acos(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + acos(arg.data, 0, result, 0) } - override fun atan(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.atan(arg.data, 0, result.data, 0) - return result + override fun atan(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + atan(arg.data, 0, result, 0) } - override fun sinh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.sinh(arg.data, 0, result.data, 0) - return result + override fun sinh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + sinh(arg.data, 0, result, 0) } - override fun cosh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.cosh(arg.data, 0, result.data, 0) - return result + override fun cosh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + cosh(arg.data, 0, result, 0) } - override fun tanh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.tanh(arg.data, 0, result.data, 0) - return result + override fun tanh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + tanh(arg.data, 0, result, 0) } - override fun asinh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.asinh(arg.data, 0, result.data, 0) - return result + override fun asinh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + asinh(arg.data, 0, result, 0) } - override fun acosh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.acosh(arg.data, 0, result.data, 0) - return result + override fun acosh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + acosh(arg.data, 0, result, 0) } - override fun atanh(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.atanh(arg.data, 0, result.data, 0) - return result + override fun atanh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + atanh(arg.data, 0, result, 0) } override fun power(arg: DerivativeStructure, pow: Number): DerivativeStructure = when (pow) { - is Int -> { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.pow(arg.data, 0, pow, result.data, 0) - result + is Int -> arg.transformDataBuffer { result -> + pow(arg.data, 0, pow, result, 0) } - else -> { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.pow(arg.data, 0, pow.toDouble(), result.data, 0) - result + else -> arg.transformDataBuffer { result -> + pow(arg.data, 0, pow.toDouble(), result, 0) } } - override fun sqrt(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.sqrt(arg.data, 0, result.data, 0) - return result + override fun sqrt(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + sqrt(arg.data, 0, result, 0) } public fun power(arg: DerivativeStructure, pow: DerivativeStructure): DerivativeStructure { arg.compiler.checkCompatibility(pow.compiler) - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.pow(arg.data, 0, pow.data, 0, result.data, 0) - return result + return arg.transformDataBuffer { result -> + pow(arg.data, 0, pow.data, 0, result, 0) + } } - override fun exp(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.exp(arg.data, 0, result.data, 0) - return result + override fun exp(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + exp(arg.data, 0, result, 0) } - override fun ln(arg: DerivativeStructure): DerivativeStructure { - val result = DerivativeStructure(this, arg.compiler) - arg.compiler.ln(arg.data, 0, result.data, 0) - return result + override fun ln(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> + ln(arg.data, 0, result, 0) } } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSpace.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSpace.kt index 715fad07b..10438dd02 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSpace.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSpace.kt @@ -188,7 +188,7 @@ public interface LinearSpace> { */ public fun > buffered( algebra: A, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), ): LinearSpace = BufferedLinearSpace(BufferRingOps(algebra, bufferFactory)) @Deprecated("use DoubleField.linearSpace") diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt index 7c612b6a9..60fa81cd8 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt @@ -27,5 +27,5 @@ public annotation class UnstableKMathAPI RequiresOptIn.Level.WARNING, ) public annotation class PerformancePitfall( - val message: String = "Potential performance problem" + val message: String = "Potential performance problem", ) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt index 2401f6319..8175bd65e 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/BufferND.kt @@ -69,7 +69,7 @@ public class MutableBufferND( * Transform structure to a new structure using provided [MutableBufferFactory] and optimizing if argument is [MutableBufferND] */ public inline fun MutableStructureND.mapToMutableBuffer( - factory: MutableBufferFactory = MutableBuffer.Companion::auto, + factory: MutableBufferFactory = MutableBufferFactory(MutableBuffer.Companion::auto), crossinline transform: (T) -> R, ): MutableBufferND { return if (this is MutableBufferND) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt index e934c6370..6e54e1b9d 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/StructureND.kt @@ -120,7 +120,7 @@ public interface StructureND : Featured, WithShape { */ public fun buffered( strides: Strides, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), initializer: (IntArray) -> T, ): BufferND = BufferND(strides, bufferFactory(strides.linearSize) { i -> initializer(strides.index(i)) }) @@ -140,7 +140,7 @@ public interface StructureND : Featured, WithShape { public fun buffered( shape: IntArray, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), initializer: (IntArray) -> T, ): BufferND = buffered(DefaultStrides(shape), bufferFactory, initializer) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferOps.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferOps.kt index 0ee591acc..083892105 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferOps.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferOps.kt @@ -6,12 +6,10 @@ package space.kscience.kmath.operations import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.asBuffer - import kotlin.math.* /** @@ -21,7 +19,7 @@ public abstract class DoubleBufferOps : BufferAlgebra, Exte Norm, Double> { override val elementAlgebra: DoubleField get() = DoubleField - override val bufferFactory: BufferFactory get() = ::DoubleBuffer + override val bufferFactory: BufferFactory get() = BufferFactory(::DoubleBuffer) override fun Buffer.map(block: DoubleField.(Double) -> Double): DoubleBuffer = mapInline { DoubleField.block(it) } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt index 31b0c2841..652472fcf 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt @@ -61,31 +61,39 @@ public inline fun Buffer.toTypedArray(): Array = Array(size, : /** * Create a new buffer from this one with the given mapping function and using [Buffer.Companion.auto] buffer factory. */ -public inline fun Buffer.map(block: (T) -> R): Buffer = +public inline fun Buffer.map(block: (T) -> R): Buffer = Buffer.auto(size) { block(get(it)) } /** * Create a new buffer from this one with the given mapping function. * Provided [bufferFactory] is used to construct the new buffer. */ -public inline fun Buffer.map( +public inline fun Buffer.map( bufferFactory: BufferFactory, crossinline block: (T) -> R, ): Buffer = bufferFactory(size) { block(get(it)) } /** - * Create a new buffer from this one with the given indexed mapping function. - * Provided [BufferFactory] is used to construct the new buffer. + * Create a new buffer from this one with the given mapping (indexed) function. + * Provided [bufferFactory] is used to construct the new buffer. */ -public inline fun Buffer.mapIndexed( - bufferFactory: BufferFactory = Buffer.Companion::auto, +public inline fun Buffer.mapIndexed( + bufferFactory: BufferFactory, crossinline block: (index: Int, value: T) -> R, ): Buffer = bufferFactory(size) { block(it, get(it)) } +/** + * Create a new buffer from this one with the given indexed mapping function. + * Provided [BufferFactory] is used to construct the new buffer. + */ +public inline fun Buffer.mapIndexed( + crossinline block: (index: Int, value: T) -> R, +): Buffer = BufferFactory(Buffer.Companion::auto).invoke(size) { block(it, get(it)) } + /** * Fold given buffer according to [operation] */ -public inline fun Buffer.fold(initial: R, operation: (acc: R, T) -> R): R { +public inline fun Buffer.fold(initial: R, operation: (acc: R, T) -> R): R { var accumulator = initial for (index in this.indices) accumulator = operation(accumulator, get(index)) return accumulator @@ -95,9 +103,9 @@ public inline fun Buffer.fold(initial: R, operation: (acc: R, T) * Zip two buffers using given [transform]. */ @UnstableKMathAPI -public inline fun Buffer.zip( +public inline fun Buffer.zip( other: Buffer, - bufferFactory: BufferFactory = Buffer.Companion::auto, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::auto), crossinline transform: (T1, T2) -> R, ): Buffer { require(size == other.size) { "Buffer size mismatch in zip: expected $size but found ${other.size}" } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt index a1b0307c4..1c79c257a 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/Buffer.kt @@ -14,14 +14,18 @@ import kotlin.reflect.KClass * * @param T the type of buffer. */ -public typealias BufferFactory = (Int, (Int) -> T) -> Buffer +public fun interface BufferFactory { + public operator fun invoke(size: Int, builder: (Int) -> T): Buffer +} /** * Function that produces [MutableBuffer] from its size and function that supplies values. * * @param T the type of buffer. */ -public typealias MutableBufferFactory = (Int, (Int) -> T) -> MutableBuffer +public fun interface MutableBufferFactory: BufferFactory{ + override fun invoke(size: Int, builder: (Int) -> T): MutableBuffer +} /** * A generic read-only random-access structure for both primitives and objects. diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt deleted file mode 100644 index aac327a84..000000000 --- a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt +++ /dev/null @@ -1,1003 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. - */ - -/* This file is generated with buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt */ - -package space.kscience.kmath.ejml - -import org.ejml.data.* -import org.ejml.dense.row.CommonOps_DDRM -import org.ejml.dense.row.CommonOps_FDRM -import org.ejml.dense.row.factory.DecompositionFactory_DDRM -import org.ejml.dense.row.factory.DecompositionFactory_FDRM -import org.ejml.sparse.FillReducing -import org.ejml.sparse.csc.CommonOps_DSCC -import org.ejml.sparse.csc.CommonOps_FSCC -import org.ejml.sparse.csc.factory.DecompositionFactory_DSCC -import org.ejml.sparse.csc.factory.DecompositionFactory_FSCC -import org.ejml.sparse.csc.factory.LinearSolverFactory_DSCC -import org.ejml.sparse.csc.factory.LinearSolverFactory_FSCC -import space.kscience.kmath.linear.* -import space.kscience.kmath.linear.Matrix -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.nd.StructureFeature -import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.operations.FloatField -import space.kscience.kmath.operations.invoke -import space.kscience.kmath.structures.DoubleBuffer -import space.kscience.kmath.structures.FloatBuffer -import kotlin.reflect.KClass -import kotlin.reflect.cast - -/** - * [EjmlVector] specialization for [Double]. - */ -public class EjmlDoubleVector(override val origin: M) : EjmlVector(origin) { - init { - require(origin.numRows == 1) { "The origin matrix must have only one row to form a vector" } - } - - override operator fun get(index: Int): Double = origin[0, index] -} - -/** - * [EjmlVector] specialization for [Float]. - */ -public class EjmlFloatVector(override val origin: M) : EjmlVector(origin) { - init { - require(origin.numRows == 1) { "The origin matrix must have only one row to form a vector" } - } - - override operator fun get(index: Int): Float = origin[0, index] -} - -/** - * [EjmlMatrix] specialization for [Double]. - */ -public class EjmlDoubleMatrix(override val origin: M) : EjmlMatrix(origin) { - override operator fun get(i: Int, j: Int): Double = origin[i, j] -} - -/** - * [EjmlMatrix] specialization for [Float]. - */ -public class EjmlFloatMatrix(override val origin: M) : EjmlMatrix(origin) { - override operator fun get(i: Int, j: Int): Float = origin[i, j] -} - -/** - * [EjmlLinearSpace] implementation based on [CommonOps_DDRM], [DecompositionFactory_DDRM] operations and - * [DMatrixRMaj] matrices. - */ -public object EjmlLinearSpaceDDRM : EjmlLinearSpace() { - /** - * The [DoubleField] reference. - */ - override val elementAlgebra: DoubleField get() = DoubleField - - @Suppress("UNCHECKED_CAST") - override fun Matrix.toEjml(): EjmlDoubleMatrix = when { - this is EjmlDoubleMatrix<*> && origin is DMatrixRMaj -> this as EjmlDoubleMatrix - else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } - } - - @Suppress("UNCHECKED_CAST") - override fun Point.toEjml(): EjmlDoubleVector = when { - this is EjmlDoubleVector<*> && origin is DMatrixRMaj -> this as EjmlDoubleVector - else -> EjmlDoubleVector(DMatrixRMaj(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } - }) - } - - override fun buildMatrix( - rows: Int, - columns: Int, - initializer: DoubleField.(i: Int, j: Int) -> Double, - ): EjmlDoubleMatrix = DMatrixRMaj(rows, columns).also { - (0 until rows).forEach { row -> - (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } - } - }.wrapMatrix() - - override fun buildVector( - size: Int, - initializer: DoubleField.(Int) -> Double, - ): EjmlDoubleVector = EjmlDoubleVector(DMatrixRMaj(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } - }) - - private fun T.wrapMatrix() = EjmlDoubleMatrix(this) - private fun T.wrapVector() = EjmlDoubleVector(this) - - override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } - - override fun Matrix.dot(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixRMaj(1, 1) - CommonOps_DDRM.mult(toEjml().origin, other.toEjml().origin, out) - return out.wrapMatrix() - } - - override fun Matrix.dot(vector: Point): EjmlDoubleVector { - val out = DMatrixRMaj(1, 1) - CommonOps_DDRM.mult(toEjml().origin, vector.toEjml().origin, out) - return out.wrapVector() - } - - override operator fun Matrix.minus(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixRMaj(1, 1) - - CommonOps_DDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - ) - - return out.wrapMatrix() - } - - override operator fun Matrix.times(value: Double): EjmlDoubleMatrix { - val res = DMatrixRMaj(1, 1) - CommonOps_DDRM.scale(value, toEjml().origin, res) - return res.wrapMatrix() - } - - override fun Point.unaryMinus(): EjmlDoubleVector { - val res = DMatrixRMaj(1, 1) - CommonOps_DDRM.changeSign(toEjml().origin, res) - return res.wrapVector() - } - - override fun Matrix.plus(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixRMaj(1, 1) - - CommonOps_DDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - ) - - return out.wrapMatrix() - } - - override fun Point.plus(other: Point): EjmlDoubleVector { - val out = DMatrixRMaj(1, 1) - - CommonOps_DDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - ) - - return out.wrapVector() - } - - override fun Point.minus(other: Point): EjmlDoubleVector { - val out = DMatrixRMaj(1, 1) - - CommonOps_DDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - ) - - return out.wrapVector() - } - - override fun Double.times(m: Matrix): EjmlDoubleMatrix = m * this - - override fun Point.times(value: Double): EjmlDoubleVector { - val res = DMatrixRMaj(1, 1) - CommonOps_DDRM.scale(value, toEjml().origin, res) - return res.wrapVector() - } - - override fun Double.times(v: Point): EjmlDoubleVector = v * this - - @UnstableKMathAPI - override fun computeFeature(structure: Matrix, type: KClass): F? { - structure.getFeature(type)?.let { return it } - val origin = structure.toEjml().origin - - return when (type) { - InverseMatrixFeature::class -> object : InverseMatrixFeature { - override val inverse: Matrix by lazy { - val res = origin.copy() - CommonOps_DDRM.invert(res) - res.wrapMatrix() - } - } - - DeterminantFeature::class -> object : DeterminantFeature { - override val determinant: Double by lazy { CommonOps_DDRM.det(origin) } - } - - SingularValueDecompositionFeature::class -> object : SingularValueDecompositionFeature { - private val svd by lazy { - DecompositionFactory_DDRM.svd(origin.numRows, origin.numCols, true, true, false) - .apply { decompose(origin.copy()) } - } - - override val u: Matrix by lazy { svd.getU(null, false).wrapMatrix() } - override val s: Matrix by lazy { svd.getW(null).wrapMatrix() } - override val v: Matrix by lazy { svd.getV(null, false).wrapMatrix() } - override val singularValues: Point by lazy { DoubleBuffer(svd.singularValues) } - } - - QRDecompositionFeature::class -> object : QRDecompositionFeature { - private val qr by lazy { - DecompositionFactory_DDRM.qr().apply { decompose(origin.copy()) } - } - - override val q: Matrix by lazy { - qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) - } - - override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } - } - - CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { - override val l: Matrix by lazy { - val cholesky = - DecompositionFactory_DDRM.chol(structure.rowNum, true).apply { decompose(origin.copy()) } - - cholesky.getT(null).wrapMatrix().withFeature(LFeature) - } - } - - LupDecompositionFeature::class -> object : LupDecompositionFeature { - private val lup by lazy { - DecompositionFactory_DDRM.lu(origin.numRows, origin.numCols).apply { decompose(origin.copy()) } - } - - override val l: Matrix by lazy { - lup.getLower(null).wrapMatrix().withFeature(LFeature) - } - - override val u: Matrix by lazy { - lup.getUpper(null).wrapMatrix().withFeature(UFeature) - } - - override val p: Matrix by lazy { lup.getRowPivot(null).wrapMatrix() } - } - - else -> null - }?.let{ - type.cast(it) - } - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p matrix. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Matrix): EjmlDoubleMatrix { - val res = DMatrixRMaj(1, 1) - CommonOps_DDRM.solve(DMatrixRMaj(a.toEjml().origin), DMatrixRMaj(b.toEjml().origin), res) - return res.wrapMatrix() - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p vector. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Point): EjmlDoubleVector { - val res = DMatrixRMaj(1, 1) - CommonOps_DDRM.solve(DMatrixRMaj(a.toEjml().origin), DMatrixRMaj(b.toEjml().origin), res) - return EjmlDoubleVector(res) - } -} - -/** - * [EjmlLinearSpace] implementation based on [CommonOps_FDRM], [DecompositionFactory_FDRM] operations and - * [FMatrixRMaj] matrices. - */ -public object EjmlLinearSpaceFDRM : EjmlLinearSpace() { - /** - * The [FloatField] reference. - */ - override val elementAlgebra: FloatField get() = FloatField - - @Suppress("UNCHECKED_CAST") - override fun Matrix.toEjml(): EjmlFloatMatrix = when { - this is EjmlFloatMatrix<*> && origin is FMatrixRMaj -> this as EjmlFloatMatrix - else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } - } - - @Suppress("UNCHECKED_CAST") - override fun Point.toEjml(): EjmlFloatVector = when { - this is EjmlFloatVector<*> && origin is FMatrixRMaj -> this as EjmlFloatVector - else -> EjmlFloatVector(FMatrixRMaj(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } - }) - } - - override fun buildMatrix( - rows: Int, - columns: Int, - initializer: FloatField.(i: Int, j: Int) -> Float, - ): EjmlFloatMatrix = FMatrixRMaj(rows, columns).also { - (0 until rows).forEach { row -> - (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } - } - }.wrapMatrix() - - override fun buildVector( - size: Int, - initializer: FloatField.(Int) -> Float, - ): EjmlFloatVector = EjmlFloatVector(FMatrixRMaj(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } - }) - - private fun T.wrapMatrix() = EjmlFloatMatrix(this) - private fun T.wrapVector() = EjmlFloatVector(this) - - override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } - - override fun Matrix.dot(other: Matrix): EjmlFloatMatrix { - val out = FMatrixRMaj(1, 1) - CommonOps_FDRM.mult(toEjml().origin, other.toEjml().origin, out) - return out.wrapMatrix() - } - - override fun Matrix.dot(vector: Point): EjmlFloatVector { - val out = FMatrixRMaj(1, 1) - CommonOps_FDRM.mult(toEjml().origin, vector.toEjml().origin, out) - return out.wrapVector() - } - - override operator fun Matrix.minus(other: Matrix): EjmlFloatMatrix { - val out = FMatrixRMaj(1, 1) - - CommonOps_FDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - ) - - return out.wrapMatrix() - } - - override operator fun Matrix.times(value: Float): EjmlFloatMatrix { - val res = FMatrixRMaj(1, 1) - CommonOps_FDRM.scale(value, toEjml().origin, res) - return res.wrapMatrix() - } - - override fun Point.unaryMinus(): EjmlFloatVector { - val res = FMatrixRMaj(1, 1) - CommonOps_FDRM.changeSign(toEjml().origin, res) - return res.wrapVector() - } - - override fun Matrix.plus(other: Matrix): EjmlFloatMatrix { - val out = FMatrixRMaj(1, 1) - - CommonOps_FDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - ) - - return out.wrapMatrix() - } - - override fun Point.plus(other: Point): EjmlFloatVector { - val out = FMatrixRMaj(1, 1) - - CommonOps_FDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - ) - - return out.wrapVector() - } - - override fun Point.minus(other: Point): EjmlFloatVector { - val out = FMatrixRMaj(1, 1) - - CommonOps_FDRM.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - ) - - return out.wrapVector() - } - - override fun Float.times(m: Matrix): EjmlFloatMatrix = m * this - - override fun Point.times(value: Float): EjmlFloatVector { - val res = FMatrixRMaj(1, 1) - CommonOps_FDRM.scale(value, toEjml().origin, res) - return res.wrapVector() - } - - override fun Float.times(v: Point): EjmlFloatVector = v * this - - @UnstableKMathAPI - override fun computeFeature(structure: Matrix, type: KClass): F? { - structure.getFeature(type)?.let { return it } - val origin = structure.toEjml().origin - - return when (type) { - InverseMatrixFeature::class -> object : InverseMatrixFeature { - override val inverse: Matrix by lazy { - val res = origin.copy() - CommonOps_FDRM.invert(res) - res.wrapMatrix() - } - } - - DeterminantFeature::class -> object : DeterminantFeature { - override val determinant: Float by lazy { CommonOps_FDRM.det(origin) } - } - - SingularValueDecompositionFeature::class -> object : SingularValueDecompositionFeature { - private val svd by lazy { - DecompositionFactory_FDRM.svd(origin.numRows, origin.numCols, true, true, false) - .apply { decompose(origin.copy()) } - } - - override val u: Matrix by lazy { svd.getU(null, false).wrapMatrix() } - override val s: Matrix by lazy { svd.getW(null).wrapMatrix() } - override val v: Matrix by lazy { svd.getV(null, false).wrapMatrix() } - override val singularValues: Point by lazy { FloatBuffer(svd.singularValues) } - } - - QRDecompositionFeature::class -> object : QRDecompositionFeature { - private val qr by lazy { - DecompositionFactory_FDRM.qr().apply { decompose(origin.copy()) } - } - - override val q: Matrix by lazy { - qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) - } - - override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } - } - - CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { - override val l: Matrix by lazy { - val cholesky = - DecompositionFactory_FDRM.chol(structure.rowNum, true).apply { decompose(origin.copy()) } - - cholesky.getT(null).wrapMatrix().withFeature(LFeature) - } - } - - LupDecompositionFeature::class -> object : LupDecompositionFeature { - private val lup by lazy { - DecompositionFactory_FDRM.lu(origin.numRows, origin.numCols).apply { decompose(origin.copy()) } - } - - override val l: Matrix by lazy { - lup.getLower(null).wrapMatrix().withFeature(LFeature) - } - - override val u: Matrix by lazy { - lup.getUpper(null).wrapMatrix().withFeature(UFeature) - } - - override val p: Matrix by lazy { lup.getRowPivot(null).wrapMatrix() } - } - - else -> null - }?.let{ - type.cast(it) - } - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p matrix. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Matrix): EjmlFloatMatrix { - val res = FMatrixRMaj(1, 1) - CommonOps_FDRM.solve(FMatrixRMaj(a.toEjml().origin), FMatrixRMaj(b.toEjml().origin), res) - return res.wrapMatrix() - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p vector. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Point): EjmlFloatVector { - val res = FMatrixRMaj(1, 1) - CommonOps_FDRM.solve(FMatrixRMaj(a.toEjml().origin), FMatrixRMaj(b.toEjml().origin), res) - return EjmlFloatVector(res) - } -} - -/** - * [EjmlLinearSpace] implementation based on [CommonOps_DSCC], [DecompositionFactory_DSCC] operations and - * [DMatrixSparseCSC] matrices. - */ -public object EjmlLinearSpaceDSCC : EjmlLinearSpace() { - /** - * The [DoubleField] reference. - */ - override val elementAlgebra: DoubleField get() = DoubleField - - @Suppress("UNCHECKED_CAST") - override fun Matrix.toEjml(): EjmlDoubleMatrix = when { - this is EjmlDoubleMatrix<*> && origin is DMatrixSparseCSC -> this as EjmlDoubleMatrix - else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } - } - - @Suppress("UNCHECKED_CAST") - override fun Point.toEjml(): EjmlDoubleVector = when { - this is EjmlDoubleVector<*> && origin is DMatrixSparseCSC -> this as EjmlDoubleVector - else -> EjmlDoubleVector(DMatrixSparseCSC(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } - }) - } - - override fun buildMatrix( - rows: Int, - columns: Int, - initializer: DoubleField.(i: Int, j: Int) -> Double, - ): EjmlDoubleMatrix = DMatrixSparseCSC(rows, columns).also { - (0 until rows).forEach { row -> - (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } - } - }.wrapMatrix() - - override fun buildVector( - size: Int, - initializer: DoubleField.(Int) -> Double, - ): EjmlDoubleVector = EjmlDoubleVector(DMatrixSparseCSC(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } - }) - - private fun T.wrapMatrix() = EjmlDoubleMatrix(this) - private fun T.wrapVector() = EjmlDoubleVector(this) - - override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } - - override fun Matrix.dot(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.mult(toEjml().origin, other.toEjml().origin, out) - return out.wrapMatrix() - } - - override fun Matrix.dot(vector: Point): EjmlDoubleVector { - val out = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.mult(toEjml().origin, vector.toEjml().origin, out) - return out.wrapVector() - } - - override operator fun Matrix.minus(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixSparseCSC(1, 1) - - CommonOps_DSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapMatrix() - } - - override operator fun Matrix.times(value: Double): EjmlDoubleMatrix { - val res = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.scale(value, toEjml().origin, res) - return res.wrapMatrix() - } - - override fun Point.unaryMinus(): EjmlDoubleVector { - val res = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.changeSign(toEjml().origin, res) - return res.wrapVector() - } - - override fun Matrix.plus(other: Matrix): EjmlDoubleMatrix { - val out = DMatrixSparseCSC(1, 1) - - CommonOps_DSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapMatrix() - } - - override fun Point.plus(other: Point): EjmlDoubleVector { - val out = DMatrixSparseCSC(1, 1) - - CommonOps_DSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapVector() - } - - override fun Point.minus(other: Point): EjmlDoubleVector { - val out = DMatrixSparseCSC(1, 1) - - CommonOps_DSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapVector() - } - - override fun Double.times(m: Matrix): EjmlDoubleMatrix = m * this - - override fun Point.times(value: Double): EjmlDoubleVector { - val res = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.scale(value, toEjml().origin, res) - return res.wrapVector() - } - - override fun Double.times(v: Point): EjmlDoubleVector = v * this - - @UnstableKMathAPI - override fun computeFeature(structure: Matrix, type: KClass): F? { - structure.getFeature(type)?.let { return it } - val origin = structure.toEjml().origin - - return when (type) { - QRDecompositionFeature::class -> object : QRDecompositionFeature { - private val qr by lazy { - DecompositionFactory_DSCC.qr(FillReducing.NONE).apply { decompose(origin.copy()) } - } - - override val q: Matrix by lazy { - qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) - } - - override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } - } - - CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { - override val l: Matrix by lazy { - val cholesky = - DecompositionFactory_DSCC.cholesky().apply { decompose(origin.copy()) } - - (cholesky.getT(null) as DMatrix).wrapMatrix().withFeature(LFeature) - } - } - - LUDecompositionFeature::class, DeterminantFeature::class, InverseMatrixFeature::class -> object : - LUDecompositionFeature, DeterminantFeature, InverseMatrixFeature { - private val lu by lazy { - DecompositionFactory_DSCC.lu(FillReducing.NONE).apply { decompose(origin.copy()) } - } - - override val l: Matrix by lazy { - lu.getLower(null).wrapMatrix().withFeature(LFeature) - } - - override val u: Matrix by lazy { - lu.getUpper(null).wrapMatrix().withFeature(UFeature) - } - - override val inverse: Matrix by lazy { - var a = origin - val inverse = DMatrixRMaj(1, 1) - val solver = LinearSolverFactory_DSCC.lu(FillReducing.NONE) - if (solver.modifiesA()) a = a.copy() - val i = CommonOps_DDRM.identity(a.numRows) - solver.solve(i, inverse) - inverse.wrapMatrix() - } - - override val determinant: Double by lazy { elementAlgebra.number(lu.computeDeterminant().real) } - } - - else -> null - }?.let{ - type.cast(it) - } - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p matrix. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Matrix): EjmlDoubleMatrix { - val res = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.solve(DMatrixSparseCSC(a.toEjml().origin), DMatrixSparseCSC(b.toEjml().origin), res) - return res.wrapMatrix() - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p vector. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Point): EjmlDoubleVector { - val res = DMatrixSparseCSC(1, 1) - CommonOps_DSCC.solve(DMatrixSparseCSC(a.toEjml().origin), DMatrixSparseCSC(b.toEjml().origin), res) - return EjmlDoubleVector(res) - } -} - -/** - * [EjmlLinearSpace] implementation based on [CommonOps_FSCC], [DecompositionFactory_FSCC] operations and - * [FMatrixSparseCSC] matrices. - */ -public object EjmlLinearSpaceFSCC : EjmlLinearSpace() { - /** - * The [FloatField] reference. - */ - override val elementAlgebra: FloatField get() = FloatField - - @Suppress("UNCHECKED_CAST") - override fun Matrix.toEjml(): EjmlFloatMatrix = when { - this is EjmlFloatMatrix<*> && origin is FMatrixSparseCSC -> this as EjmlFloatMatrix - else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } - } - - @Suppress("UNCHECKED_CAST") - override fun Point.toEjml(): EjmlFloatVector = when { - this is EjmlFloatVector<*> && origin is FMatrixSparseCSC -> this as EjmlFloatVector - else -> EjmlFloatVector(FMatrixSparseCSC(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } - }) - } - - override fun buildMatrix( - rows: Int, - columns: Int, - initializer: FloatField.(i: Int, j: Int) -> Float, - ): EjmlFloatMatrix = FMatrixSparseCSC(rows, columns).also { - (0 until rows).forEach { row -> - (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } - } - }.wrapMatrix() - - override fun buildVector( - size: Int, - initializer: FloatField.(Int) -> Float, - ): EjmlFloatVector = EjmlFloatVector(FMatrixSparseCSC(size, 1).also { - (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } - }) - - private fun T.wrapMatrix() = EjmlFloatMatrix(this) - private fun T.wrapVector() = EjmlFloatVector(this) - - override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } - - override fun Matrix.dot(other: Matrix): EjmlFloatMatrix { - val out = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.mult(toEjml().origin, other.toEjml().origin, out) - return out.wrapMatrix() - } - - override fun Matrix.dot(vector: Point): EjmlFloatVector { - val out = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.mult(toEjml().origin, vector.toEjml().origin, out) - return out.wrapVector() - } - - override operator fun Matrix.minus(other: Matrix): EjmlFloatMatrix { - val out = FMatrixSparseCSC(1, 1) - - CommonOps_FSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapMatrix() - } - - override operator fun Matrix.times(value: Float): EjmlFloatMatrix { - val res = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.scale(value, toEjml().origin, res) - return res.wrapMatrix() - } - - override fun Point.unaryMinus(): EjmlFloatVector { - val res = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.changeSign(toEjml().origin, res) - return res.wrapVector() - } - - override fun Matrix.plus(other: Matrix): EjmlFloatMatrix { - val out = FMatrixSparseCSC(1, 1) - - CommonOps_FSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapMatrix() - } - - override fun Point.plus(other: Point): EjmlFloatVector { - val out = FMatrixSparseCSC(1, 1) - - CommonOps_FSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra.one, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapVector() - } - - override fun Point.minus(other: Point): EjmlFloatVector { - val out = FMatrixSparseCSC(1, 1) - - CommonOps_FSCC.add( - elementAlgebra.one, - toEjml().origin, - elementAlgebra { -one }, - other.toEjml().origin, - out, - null, - null, - ) - - return out.wrapVector() - } - - override fun Float.times(m: Matrix): EjmlFloatMatrix = m * this - - override fun Point.times(value: Float): EjmlFloatVector { - val res = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.scale(value, toEjml().origin, res) - return res.wrapVector() - } - - override fun Float.times(v: Point): EjmlFloatVector = v * this - - @UnstableKMathAPI - override fun computeFeature(structure: Matrix, type: KClass): F? { - structure.getFeature(type)?.let { return it } - val origin = structure.toEjml().origin - - return when (type) { - QRDecompositionFeature::class -> object : QRDecompositionFeature { - private val qr by lazy { - DecompositionFactory_FSCC.qr(FillReducing.NONE).apply { decompose(origin.copy()) } - } - - override val q: Matrix by lazy { - qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) - } - - override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } - } - - CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { - override val l: Matrix by lazy { - val cholesky = - DecompositionFactory_FSCC.cholesky().apply { decompose(origin.copy()) } - - (cholesky.getT(null) as FMatrix).wrapMatrix().withFeature(LFeature) - } - } - - LUDecompositionFeature::class, DeterminantFeature::class, InverseMatrixFeature::class -> object : - LUDecompositionFeature, DeterminantFeature, InverseMatrixFeature { - private val lu by lazy { - DecompositionFactory_FSCC.lu(FillReducing.NONE).apply { decompose(origin.copy()) } - } - - override val l: Matrix by lazy { - lu.getLower(null).wrapMatrix().withFeature(LFeature) - } - - override val u: Matrix by lazy { - lu.getUpper(null).wrapMatrix().withFeature(UFeature) - } - - override val inverse: Matrix by lazy { - var a = origin - val inverse = FMatrixRMaj(1, 1) - val solver = LinearSolverFactory_FSCC.lu(FillReducing.NONE) - if (solver.modifiesA()) a = a.copy() - val i = CommonOps_FDRM.identity(a.numRows) - solver.solve(i, inverse) - inverse.wrapMatrix() - } - - override val determinant: Float by lazy { elementAlgebra.number(lu.computeDeterminant().real) } - } - - else -> null - }?.let{ - type.cast(it) - } - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p matrix. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Matrix): EjmlFloatMatrix { - val res = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.solve(FMatrixSparseCSC(a.toEjml().origin), FMatrixSparseCSC(b.toEjml().origin), res) - return res.wrapMatrix() - } - - /** - * Solves for *x* in the following equation: *x = [a] -1 · [b]*. - * - * @param a the base matrix. - * @param b n by p vector. - * @return the solution for *x* that is n by p. - */ - public fun solve(a: Matrix, b: Point): EjmlFloatVector { - val res = FMatrixSparseCSC(1, 1) - CommonOps_FSCC.solve(FMatrixSparseCSC(a.toEjml().origin), FMatrixSparseCSC(b.toEjml().origin), res) - return EjmlFloatVector(res) - } -} - diff --git a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt index 90ec29ce3..eafd55513 100644 --- a/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt +++ b/kmath-histograms/src/commonMain/kotlin/space/kscience/kmath/histogram/UniformHistogramGroupND.kt @@ -28,7 +28,7 @@ public class UniformHistogramGroupND>( private val lower: Buffer, private val upper: Buffer, private val binNums: IntArray = IntArray(lower.size) { 20 }, - private val bufferFactory: BufferFactory = Buffer.Companion::boxing, + private val bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), ) : HistogramGroupND { init { @@ -114,7 +114,7 @@ public class UniformHistogramGroupND>( public fun > Histogram.Companion.uniformNDFromRanges( valueAlgebraND: FieldOpsND, vararg ranges: ClosedFloatingPointRange, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), ): UniformHistogramGroupND = UniformHistogramGroupND( valueAlgebraND, ranges.map(ClosedFloatingPointRange::start).asBuffer(), @@ -140,7 +140,7 @@ public fun Histogram.Companion.uniformDoubleNDFromRanges( public fun > Histogram.Companion.uniformNDFromRanges( valueAlgebraND: FieldOpsND, vararg ranges: Pair, Int>, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), ): UniformHistogramGroupND = UniformHistogramGroupND( valueAlgebraND, ListBuffer( diff --git a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt b/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt index 1dc318517..0de2d8349 100644 --- a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt +++ b/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt @@ -6,6 +6,7 @@ package space.kscience.kmath.multik import org.jetbrains.kotlinx.multik.ndarray.data.DataType +import space.kscience.kmath.misc.PerformancePitfall import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.ExponentialOperations @@ -22,10 +23,13 @@ public object MultikDoubleAlgebra : MultikDivisionTensorAlgebra): MultikTensor = sin(arg) / cos(arg) + @PerformancePitfall override fun asin(arg: StructureND): MultikTensor = arg.map { asin(it) } + @PerformancePitfall override fun acos(arg: StructureND): MultikTensor = arg.map { acos(it) } + @PerformancePitfall override fun atan(arg: StructureND): MultikTensor = arg.map { atan(it) } override fun exp(arg: StructureND): MultikTensor = multikMath.mathEx.exp(arg.asMultik().array).wrap() @@ -42,10 +46,13 @@ public object MultikDoubleAlgebra : MultikDivisionTensorAlgebra): MultikTensor = arg.map { asinh(it) } + @PerformancePitfall override fun acosh(arg: StructureND): MultikTensor = arg.map { acosh(it) } + @PerformancePitfall override fun atanh(arg: StructureND): MultikTensor = arg.map { atanh(it) } } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt index a88f3e437..890318e31 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt @@ -35,7 +35,7 @@ public fun interface Sampler { public fun Sampler.sampleBuffer( generator: RandomGenerator, size: Int, - bufferFactory: BufferFactory = Buffer.Companion::boxing, + bufferFactory: BufferFactory = BufferFactory(Buffer.Companion::boxing), ): Chain> { require(size > 1) //creating temporary storage once -- 2.34.1 From f5fe53a9f234edd47ecb2e7d73e7700e12f4a01c Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 15 Jul 2022 16:20:28 +0300 Subject: [PATCH 56/59] Grand derivative refactoring. Phase 2 --- .../kscience/kmath/expressions/DSAlgebra.kt | 437 ++++++++++++++++++ .../kmath/expressions/DerivativeStructure.kt | 157 ------- .../DerivativeStructureExpression.kt | 349 -------------- .../DerivativeStructureExpressionTest.kt | 4 +- 4 files changed, 439 insertions(+), 508 deletions(-) create mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt delete mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt delete mode 100644 kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt new file mode 100644 index 000000000..d9fc46b47 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt @@ -0,0 +1,437 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. + */ + +package space.kscience.kmath.expressions + +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.operations.* +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.MutableBuffer +import space.kscience.kmath.structures.MutableBufferFactory +import space.kscience.kmath.structures.asBuffer +import kotlin.math.max +import kotlin.math.min + +/** + * Class representing both the value and the differentials of a function. + * + * This class is the workhorse of the differentiation package. + * + * This class is an implementation of the extension to Rall's numbers described in Dan Kalman's paper + * [Doubly Recursive Multivariate Automatic Differentiation](http://www1.american.edu/cas/mathstat/People/kalman/pdffiles/mmgautodiff.pdf), + * Mathematics Magazine, vol. 75, no. 3, June 2002. Rall's numbers are an extension to the real numbers used + * throughout mathematical expressions; they hold the derivative together with the value of a function. Dan Kalman's + * derivative structures hold all partial derivatives up to any specified order, with respect to any number of free + * parameters. Rall's numbers therefore can be seen as derivative structures for order one derivative and one free + * parameter, and real numbers can be seen as derivative structures with zero order derivative and no free parameters. + * + * Derived from + * [Commons Math's `DerivativeStructure`](https://github.com/apache/commons-math/blob/924f6c357465b39beb50e3c916d5eb6662194175/commons-math-legacy/src/main/java/org/apache/commons/math4/legacy/analysis/differentiation/DerivativeStructure.java). + */ +@UnstableKMathAPI +public interface DS> { + public val derivativeAlgebra: DSAlgebra + public val data: Buffer +} + +/** + * Get a partial derivative. + * + * @param orders derivation orders with respect to each variable (if all orders are 0, the value is returned). + * @return partial derivative. + * @see value + */ +@UnstableKMathAPI +public fun > DS.getPartialDerivative(vararg orders: Int): T = + data[derivativeAlgebra.compiler.getPartialDerivativeIndex(*orders)] + +/** + * The value part of the derivative structure. + * + * @see getPartialDerivative + */ +@UnstableKMathAPI +public val > DS.value: T get() = data[0] + +@UnstableKMathAPI +public abstract class DSAlgebra>( + public val algebra: A, + public val bufferFactory: MutableBufferFactory, + public val order: Int, + bindings: Map, +) : ExpressionAlgebra> { + + @OptIn(UnstableKMathAPI::class) + private fun bufferForVariable(index: Int, value: T): Buffer { + val buffer = bufferFactory(compiler.size) { algebra.zero } + buffer[0] = value + if (compiler.order > 0) { + // the derivative of the variable with respect to itself is 1. + + val indexOfDerivative = compiler.getPartialDerivativeIndex(*IntArray(numberOfVariables).apply { + set(index, 1) + }) + + buffer[indexOfDerivative] = algebra.one + } + return buffer + } + + @UnstableKMathAPI + protected inner class DSImpl internal constructor( + override val data: Buffer, + ) : DS { + override val derivativeAlgebra: DSAlgebra get() = this@DSAlgebra + } + + protected fun DS(data: Buffer): DS = DSImpl(data) + + + /** + * Build an instance representing a variable. + * + * Instances built using this constructor are considered to be the free variables with respect to which + * differentials are computed. As such, their differential with respect to themselves is +1. + */ + public fun variable( + index: Int, + value: T, + ): DS { + require(index < compiler.freeParameters) { "number is too large: $index >= ${compiler.freeParameters}" } + return DS(bufferForVariable(index, value)) + } + + /** + * Build an instance from all its derivatives. + * + * @param derivatives derivatives sorted according to [DSCompiler.getPartialDerivativeIndex]. + */ + public fun ofDerivatives( + vararg derivatives: T, + ): DS { + require(derivatives.size == compiler.size) { "dimension mismatch: ${derivatives.size} and ${compiler.size}" } + val data = derivatives.asBuffer() + + return DS(data) + } + + /** + * A class implementing both [DS] and [Symbol]. + */ + @UnstableKMathAPI + public inner class DSSymbol internal constructor( + index: Int, + symbol: Symbol, + value: T, + ) : Symbol by symbol, DS { + override val derivativeAlgebra: DSAlgebra get() = this@DSAlgebra + override val data: Buffer = bufferForVariable(index, value) + } + + + public val numberOfVariables: Int = bindings.size + + /** + * Get the compiler for number of free parameters and order. + * + * @return cached rules set. + */ + @PublishedApi + internal val compiler: DSCompiler by lazy { + // get the cached compilers + val cache: Array?>>? = null + + // we need to create more compilers + val maxParameters: Int = max(numberOfVariables, cache?.size ?: 0) + val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) + val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } + + if (cache != null) { + // preserve the already created compilers + for (i in cache.indices) { + cache[i].copyInto(newCache[i], endIndex = cache[i].size) + } + } + + // create the array in increasing diagonal order + for (diag in 0..numberOfVariables + order) { + for (o in max(0, diag - numberOfVariables)..min(order, diag)) { + val p: Int = diag - o + if (newCache[p][o] == null) { + val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! + val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! + + newCache[p][o] = DSCompiler( + algebra, + bufferFactory, + p, + o, + valueCompiler, + derivativeCompiler, + ) + } + } + } + + return@lazy newCache[numberOfVariables][order]!! + } + + private val variables: Map = bindings.entries.mapIndexed { index, (key, value) -> + key to DSSymbol( + index, + key, + value, + ) + }.toMap() + + + public override fun const(value: T): DS { + val buffer = bufferFactory(compiler.size) { algebra.zero } + buffer[0] = value + + return DS(buffer) + } + + override fun bindSymbolOrNull(value: String): DSSymbol? = variables[StringSymbol(value)] + + override fun bindSymbol(value: String): DSSymbol = + bindSymbolOrNull(value) ?: error("Symbol '$value' is not supported in $this") + + public fun bindSymbolOrNull(symbol: Symbol): DSSymbol? = variables[symbol.identity] + + public fun bindSymbol(symbol: Symbol): DSSymbol = + bindSymbolOrNull(symbol.identity) ?: error("Symbol '${symbol}' is not supported in $this") + + public fun DS.derivative(symbols: List): T { + require(symbols.size <= order) { "The order of derivative ${symbols.size} exceeds computed order $order" } + val ordersCount = symbols.groupBy { it }.mapValues { it.value.size } + return getPartialDerivative(*variables.keys.map { ordersCount[it] ?: 0 }.toIntArray()) + } + + public fun DS.derivative(vararg symbols: Symbol): T = derivative(symbols.toList()) + +} + + +/** + * A ring over [DS]. + * + * @property order The derivation order. + * @param bindings The map of bindings values. All bindings are considered free parameters. + */ +@UnstableKMathAPI +public open class DSRing( + algebra: A, + bufferFactory: MutableBufferFactory, + order: Int, + bindings: Map, +) : DSAlgebra(algebra, bufferFactory, order, bindings), + Ring>, ScaleOperations>, + NumericAlgebra>, + NumbersAddOps> where A : Ring, A : NumericAlgebra, A : ScaleOperations { + + override fun bindSymbolOrNull(value: String): DSSymbol? = + super.bindSymbolOrNull(value) + + override fun DS.unaryMinus(): DS = mapData { -it } + + /** + * Create a copy of given [Buffer] and modify it according to [block] + */ + protected inline fun DS.transformDataBuffer(block: A.(MutableBuffer) -> Unit): DS { + require(derivativeAlgebra == this@DSRing) { "All derivative operations should be done in the same algebra" } + val newData = bufferFactory(compiler.size) { data[it] } + algebra.block(newData) + return DS(newData) + } + + protected fun DS.mapData(block: A.(T) -> T): DS { + require(derivativeAlgebra == this@DSRing) { "All derivative operations should be done in the same algebra" } + val newData: Buffer = data.map(bufferFactory) { + algebra.block(it) + } + return DS(newData) + } + + protected fun DS.mapDataIndexed(block: (Int, T) -> T): DS { + require(derivativeAlgebra == this@DSRing) { "All derivative operations should be done in the same algebra" } + val newData: Buffer = data.mapIndexed(bufferFactory, block) + return DS(newData) + } + + override val zero: DS by lazy { + const(algebra.zero) + } + + override val one: DS by lazy { + const(algebra.one) + } + + override fun number(value: Number): DS = const(algebra.number(value)) + + override fun add(left: DS, right: DS): DS = left.transformDataBuffer { result -> + require(right.derivativeAlgebra == this@DSRing) { "All derivative operations should be done in the same algebra" } + compiler.add(left.data, 0, right.data, 0, result, 0) + } + + override fun scale(a: DS, value: Double): DS = a.mapData { + it.times(value) + } + + override fun multiply( + left: DS, + right: DS, + ): DS = left.transformDataBuffer { result -> + compiler.multiply(left.data, 0, right.data, 0, result, 0) + } +// +// override fun DS.minus(arg: DS): DS = transformDataBuffer { result -> +// subtract(data, 0, arg.data, 0, result, 0) +// } + + override operator fun DS.plus(other: Number): DS = transformDataBuffer { + it[0] += number(other) + } + +// +// override operator fun DS.minus(other: Number): DS = +// this + (-other.toDouble()) + + override operator fun Number.plus(other: DS): DS = other + this + override operator fun Number.minus(other: DS): DS = other - this +} + +@UnstableKMathAPI +public class DerivativeStructureRingExpression( + public val algebra: A, + public val bufferFactory: MutableBufferFactory, + public val function: DSRing.() -> DS, +) : DifferentiableExpression where A : Ring, A : ScaleOperations, A : NumericAlgebra { + override operator fun invoke(arguments: Map): T = + DSRing(algebra, bufferFactory, 0, arguments).function().value + + override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> + with( + DSRing( + algebra, + bufferFactory, + symbols.size, + arguments + ) + ) { function().derivative(symbols) } + } +} + +/** + * A field over commons-math [DerivativeStructure]. + * + * @property order The derivation order. + * @param bindings The map of bindings values. All bindings are considered free parameters. + */ +@UnstableKMathAPI +public class DSField>( + algebra: A, + bufferFactory: MutableBufferFactory, + order: Int, + bindings: Map, +) : DSRing(algebra, bufferFactory, order, bindings), ExtendedField> { + override fun number(value: Number): DS = const(algebra.number(value)) + + override fun divide(left: DS, right: DS): DS = left.transformDataBuffer { result -> + compiler.divide(left.data, 0, right.data, 0, result, 0) + } + + override fun sin(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.sin(arg.data, 0, result, 0) + } + + override fun cos(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.cos(arg.data, 0, result, 0) + } + + override fun tan(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.tan(arg.data, 0, result, 0) + } + + override fun asin(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.asin(arg.data, 0, result, 0) + } + + override fun acos(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.acos(arg.data, 0, result, 0) + } + + override fun atan(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.atan(arg.data, 0, result, 0) + } + + override fun sinh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.sinh(arg.data, 0, result, 0) + } + + override fun cosh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.cosh(arg.data, 0, result, 0) + } + + override fun tanh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.tanh(arg.data, 0, result, 0) + } + + override fun asinh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.asinh(arg.data, 0, result, 0) + } + + override fun acosh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.acosh(arg.data, 0, result, 0) + } + + override fun atanh(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.atanh(arg.data, 0, result, 0) + } + + override fun power(arg: DS, pow: Number): DS = when (pow) { + is Int -> arg.transformDataBuffer { result -> + compiler.pow(arg.data, 0, pow, result, 0) + } + else -> arg.transformDataBuffer { result -> + compiler.pow(arg.data, 0, pow.toDouble(), result, 0) + } + } + + override fun sqrt(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.sqrt(arg.data, 0, result, 0) + } + + public fun power(arg: DS, pow: DS): DS = arg.transformDataBuffer { result -> + compiler.pow(arg.data, 0, pow.data, 0, result, 0) + } + + override fun exp(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.exp(arg.data, 0, result, 0) + } + + override fun ln(arg: DS): DS = arg.transformDataBuffer { result -> + compiler.ln(arg.data, 0, result, 0) + } +} + +@UnstableKMathAPI +public class DerivativeStructureFieldExpression>( + public val algebra: A, + public val bufferFactory: MutableBufferFactory, + public val function: DSField.() -> DS, +) : DifferentiableExpression { + override operator fun invoke(arguments: Map): T = + DSField(algebra, bufferFactory, 0, arguments).function().value + + override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> + DSField( + algebra, + bufferFactory, + symbols.size, + arguments, + ).run { function().derivative(symbols) } + } +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt deleted file mode 100644 index 01c045cdb..000000000 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructure.kt +++ /dev/null @@ -1,157 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. - */ - -package space.kscience.kmath.expressions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.structures.Buffer -import space.kscience.kmath.structures.asBuffer - -/** - * Class representing both the value and the differentials of a function. - * - * This class is the workhorse of the differentiation package. - * - * This class is an implementation of the extension to Rall's numbers described in Dan Kalman's paper [Doubly Recursive - * Multivariate Automatic Differentiation](http://www1.american.edu/cas/mathstat/People/kalman/pdffiles/mmgautodiff.pdf), - * Mathematics Magazine, vol. 75, no. 3, June 2002. Rall's numbers are an extension to the real numbers used - * throughout mathematical expressions; they hold the derivative together with the value of a function. Dan Kalman's - * derivative structures hold all partial derivatives up to any specified order, with respect to any number of free - * parameters. Rall's numbers therefore can be seen as derivative structures for order one derivative and one free - * parameter, and real numbers can be seen as derivative structures with zero order derivative and no free parameters. - * - * Derived from - * [Commons Math's `DerivativeStructure`](https://github.com/apache/commons-math/blob/924f6c357465b39beb50e3c916d5eb6662194175/commons-math-legacy/src/main/java/org/apache/commons/math4/legacy/analysis/differentiation/DerivativeStructure.java). - */ -@UnstableKMathAPI -public open class DerivativeStructure> @PublishedApi internal constructor( - private val derivativeAlgebra: DerivativeStructureAlgebra, - @PublishedApi internal val data: Buffer, -) { - - public val compiler: DSCompiler get() = derivativeAlgebra.compiler - - /** - * The number of free parameters. - */ - public val freeParameters: Int get() = compiler.freeParameters - - /** - * The derivation order. - */ - public val order: Int get() = compiler.order - - /** - * The value part of the derivative structure. - * - * @see getPartialDerivative - */ - public val value: T get() = data[0] - - /** - * Get a partial derivative. - * - * @param orders derivation orders with respect to each variable (if all orders are 0, the value is returned). - * @return partial derivative. - * @see value - */ - public fun getPartialDerivative(vararg orders: Int): T = data[compiler.getPartialDerivativeIndex(*orders)] - - - /** - * Test for the equality of two derivative structures. - * - * Derivative structures are considered equal if they have the same number - * of free parameters, the same derivation order, and the same derivatives. - * - * @return `true` if two derivative structures are equal. - */ - public override fun equals(other: Any?): Boolean { - if (this === other) return true - - if (other is DerivativeStructure<*, *>) { - return ((freeParameters == other.freeParameters) && - (order == other.order) && - data == other.data) - } - - return false - } - - public override fun hashCode(): Int = - 227 + 229 * freeParameters + 233 * order + 239 * data.hashCode() - - public companion object { - - /** - * Build an instance representing a variable. - * - * Instances built using this constructor are considered to be the free variables with respect to which - * differentials are computed. As such, their differential with respect to themselves is +1. - */ - public fun > variable( - derivativeAlgebra: DerivativeStructureAlgebra, - index: Int, - value: T, - ): DerivativeStructure { - val compiler = derivativeAlgebra.compiler - require(index < compiler.freeParameters) { "number is too large: $index >= ${compiler.freeParameters}" } - return DerivativeStructure(derivativeAlgebra, derivativeAlgebra.bufferForVariable(index, value)) - } - - /** - * Build an instance from all its derivatives. - * - * @param derivatives derivatives sorted according to [DSCompiler.getPartialDerivativeIndex]. - */ - public fun > ofDerivatives( - derivativeAlgebra: DerivativeStructureAlgebra, - vararg derivatives: T, - ): DerivativeStructure { - val compiler = derivativeAlgebra.compiler - require(derivatives.size == compiler.size) { "dimension mismatch: ${derivatives.size} and ${compiler.size}" } - val data = derivatives.asBuffer() - - return DerivativeStructure( - derivativeAlgebra, - data - ) - } - } -} - -@OptIn(UnstableKMathAPI::class) -private fun > DerivativeStructureAlgebra.bufferForVariable(index: Int, value: T): Buffer { - val buffer = bufferFactory(compiler.size) { algebra.zero } - buffer[0] = value - if (compiler.order > 0) { - // the derivative of the variable with respect to itself is 1. - - val indexOfDerivative = compiler.getPartialDerivativeIndex(*IntArray(numberOfVariables).apply { - set(index, 1) - }) - - buffer[indexOfDerivative] = algebra.one - } - return buffer -} - -/** - * A class implementing both [DerivativeStructure] and [Symbol]. - */ -@UnstableKMathAPI -public class DerivativeStructureSymbol> internal constructor( - derivativeAlgebra: DerivativeStructureAlgebra, - index: Int, - symbol: Symbol, - value: T, -) : Symbol by symbol, DerivativeStructure( - derivativeAlgebra, derivativeAlgebra.bufferForVariable(index, value) -) { - override fun toString(): String = symbol.toString() - override fun equals(other: Any?): Boolean = (other as? Symbol) == symbol - override fun hashCode(): Int = symbol.hashCode() -} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt deleted file mode 100644 index 638057921..000000000 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpression.kt +++ /dev/null @@ -1,349 +0,0 @@ -/* - * Copyright 2018-2021 KMath contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. - */ - -package space.kscience.kmath.expressions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.* -import space.kscience.kmath.structures.Buffer -import space.kscience.kmath.structures.MutableBuffer -import space.kscience.kmath.structures.MutableBufferFactory -import kotlin.math.max -import kotlin.math.min - -@UnstableKMathAPI -public abstract class DerivativeStructureAlgebra>( - public val algebra: A, - public val bufferFactory: MutableBufferFactory, - public val order: Int, - bindings: Map, -) : ExpressionAlgebra> { - - public val numberOfVariables: Int = bindings.size - - - /** - * Get the compiler for number of free parameters and order. - * - * @return cached rules set. - */ - @PublishedApi - internal val compiler: DSCompiler by lazy { - // get the cached compilers - val cache: Array?>>? = null - - // we need to create more compilers - val maxParameters: Int = max(numberOfVariables, cache?.size ?: 0) - val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) - val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } - - if (cache != null) { - // preserve the already created compilers - for (i in cache.indices) { - cache[i].copyInto(newCache[i], endIndex = cache[i].size) - } - } - - // create the array in increasing diagonal order - for (diag in 0..numberOfVariables + order) { - for (o in max(0, diag - numberOfVariables)..min(order, diag)) { - val p: Int = diag - o - if (newCache[p][o] == null) { - val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! - val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! - - newCache[p][o] = DSCompiler( - algebra, - bufferFactory, - p, - o, - valueCompiler, - derivativeCompiler, - ) - } - } - } - - return@lazy newCache[numberOfVariables][order]!! - } - - private val variables: Map> = - bindings.entries.mapIndexed { index, (key, value) -> - key to DerivativeStructureSymbol( - this, - index, - key, - value, - ) - }.toMap() - - - - public override fun const(value: T): DerivativeStructure { - val buffer = bufferFactory(compiler.size) { algebra.zero } - buffer[0] = value - - return DerivativeStructure( - this, - buffer - ) - } - - override fun bindSymbolOrNull(value: String): DerivativeStructureSymbol? = variables[StringSymbol(value)] - - override fun bindSymbol(value: String): DerivativeStructureSymbol = - bindSymbolOrNull(value) ?: error("Symbol '$value' is not supported in $this") - - public fun bindSymbolOrNull(symbol: Symbol): DerivativeStructureSymbol? = variables[symbol.identity] - - public fun bindSymbol(symbol: Symbol): DerivativeStructureSymbol = - bindSymbolOrNull(symbol.identity) ?: error("Symbol '${symbol}' is not supported in $this") - - public fun DerivativeStructure.derivative(symbols: List): T { - require(symbols.size <= order) { "The order of derivative ${symbols.size} exceeds computed order $order" } - val ordersCount = symbols.groupBy { it }.mapValues { it.value.size } - return getPartialDerivative(*variables.keys.map { ordersCount[it] ?: 0 }.toIntArray()) - } - - public fun DerivativeStructure.derivative(vararg symbols: Symbol): T = derivative(symbols.toList()) - -} - - -/** - * A ring over [DerivativeStructure]. - * - * @property order The derivation order. - * @param bindings The map of bindings values. All bindings are considered free parameters. - */ -@UnstableKMathAPI -public open class DerivativeStructureRing( - algebra: A, - bufferFactory: MutableBufferFactory, - order: Int, - bindings: Map, -) : DerivativeStructureAlgebra(algebra, bufferFactory, order, bindings), - Ring>, ScaleOperations>, - NumericAlgebra>, - NumbersAddOps> where A : Ring, A : NumericAlgebra, A : ScaleOperations { - - override fun bindSymbolOrNull(value: String): DerivativeStructureSymbol? = - super.bindSymbolOrNull(value) - - override fun DerivativeStructure.unaryMinus(): DerivativeStructure { - val newData = algebra { data.map(bufferFactory) { -it } } - return DerivativeStructure(this@DerivativeStructureRing, newData) - } - - /** - * Create a copy of given [Buffer] and modify it according to [block] - */ - protected inline fun DerivativeStructure.transformDataBuffer(block: DSCompiler.(MutableBuffer) -> Unit): DerivativeStructure { - val newData = bufferFactory(compiler.size) { data[it] } - compiler.block(newData) - return DerivativeStructure(this@DerivativeStructureRing, newData) - } - - protected fun DerivativeStructure.mapData(block: (T) -> T): DerivativeStructure { - val newData: Buffer = data.map(bufferFactory, block) - return DerivativeStructure(this@DerivativeStructureRing, newData) - } - - protected fun DerivativeStructure.mapDataIndexed(block: (Int, T) -> T): DerivativeStructure { - val newData: Buffer = data.mapIndexed(bufferFactory, block) - return DerivativeStructure(this@DerivativeStructureRing, newData) - } - - override val zero: DerivativeStructure by lazy { - const(algebra.zero) - } - - override val one: DerivativeStructure by lazy { - const(algebra.one) - } - - override fun number(value: Number): DerivativeStructure = const(algebra.number(value)) - - override fun add(left: DerivativeStructure, right: DerivativeStructure): DerivativeStructure { - left.compiler.checkCompatibility(right.compiler) - return left.transformDataBuffer { result -> - add(left.data, 0, right.data, 0, result, 0) - } - } - - override fun scale(a: DerivativeStructure, value: Double): DerivativeStructure = algebra { - a.mapData { it.times(value) } - } - - override fun multiply( - left: DerivativeStructure, - right: DerivativeStructure, - ): DerivativeStructure { - left.compiler.checkCompatibility(right.compiler) - return left.transformDataBuffer { result -> - multiply(left.data, 0, right.data, 0, result, 0) - } - } - - override fun DerivativeStructure.minus(arg: DerivativeStructure): DerivativeStructure { - compiler.checkCompatibility(arg.compiler) - return transformDataBuffer { result -> - subtract(data, 0, arg.data, 0, result, 0) - } - } - - override operator fun DerivativeStructure.plus(other: Number): DerivativeStructure = algebra { - transformDataBuffer { - it[0] += number(other) - } - } - - override operator fun DerivativeStructure.minus(other: Number): DerivativeStructure = - this + (-other.toDouble()) - - override operator fun Number.plus(other: DerivativeStructure): DerivativeStructure = other + this - override operator fun Number.minus(other: DerivativeStructure): DerivativeStructure = other - this -} - -@UnstableKMathAPI -public class DerivativeStructureRingExpression( - public val algebra: A, - public val bufferFactory: MutableBufferFactory, - public val function: DerivativeStructureRing.() -> DerivativeStructure, -) : DifferentiableExpression where A : Ring, A : ScaleOperations, A : NumericAlgebra { - override operator fun invoke(arguments: Map): T = - DerivativeStructureRing(algebra, bufferFactory, 0, arguments).function().value - - override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> - with( - DerivativeStructureRing( - algebra, - bufferFactory, - symbols.size, - arguments - ) - ) { function().derivative(symbols) } - } -} - -/** - * A field over commons-math [DerivativeStructure]. - * - * @property order The derivation order. - * @param bindings The map of bindings values. All bindings are considered free parameters. - */ -@UnstableKMathAPI -public class DerivativeStructureField>( - algebra: A, - bufferFactory: MutableBufferFactory, - order: Int, - bindings: Map, -) : DerivativeStructureRing(algebra, bufferFactory, order, bindings), ExtendedField> { - override fun number(value: Number): DerivativeStructure = const(algebra.number(value)) - - override fun divide(left: DerivativeStructure, right: DerivativeStructure): DerivativeStructure { - left.compiler.checkCompatibility(right.compiler) - return left.transformDataBuffer { result -> - left.compiler.divide(left.data, 0, right.data, 0, result, 0) - } - } - - override fun sin(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - sin(arg.data, 0, result, 0) - } - - override fun cos(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - cos(arg.data, 0, result, 0) - } - - override fun tan(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - tan(arg.data, 0, result, 0) - } - - override fun asin(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - asin(arg.data, 0, result, 0) - } - - override fun acos(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - acos(arg.data, 0, result, 0) - } - - override fun atan(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - atan(arg.data, 0, result, 0) - } - - override fun sinh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - sinh(arg.data, 0, result, 0) - } - - override fun cosh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - cosh(arg.data, 0, result, 0) - } - - override fun tanh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - tanh(arg.data, 0, result, 0) - } - - override fun asinh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - asinh(arg.data, 0, result, 0) - } - - override fun acosh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - acosh(arg.data, 0, result, 0) - } - - override fun atanh(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - atanh(arg.data, 0, result, 0) - } - - override fun power(arg: DerivativeStructure, pow: Number): DerivativeStructure = when (pow) { - is Int -> arg.transformDataBuffer { result -> - pow(arg.data, 0, pow, result, 0) - } - else -> arg.transformDataBuffer { result -> - pow(arg.data, 0, pow.toDouble(), result, 0) - } - } - - override fun sqrt(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - sqrt(arg.data, 0, result, 0) - } - - public fun power(arg: DerivativeStructure, pow: DerivativeStructure): DerivativeStructure { - arg.compiler.checkCompatibility(pow.compiler) - return arg.transformDataBuffer { result -> - pow(arg.data, 0, pow.data, 0, result, 0) - } - } - - override fun exp(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - exp(arg.data, 0, result, 0) - } - - override fun ln(arg: DerivativeStructure): DerivativeStructure = arg.transformDataBuffer { result -> - ln(arg.data, 0, result, 0) - } -} - -@UnstableKMathAPI -public class DerivativeStructureFieldExpression>( - public val algebra: A, - public val bufferFactory: MutableBufferFactory, - public val function: DerivativeStructureField.() -> DerivativeStructure, -) : DifferentiableExpression { - override operator fun invoke(arguments: Map): T = - DerivativeStructureField(algebra, bufferFactory, 0, arguments).function().value - - override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> - with( - DerivativeStructureField( - algebra, - bufferFactory, - symbols.size, - arguments, - ) - ) { function().derivative(symbols) } - } -} diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt index 429fe310b..fdeda4512 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt @@ -19,10 +19,10 @@ import kotlin.test.assertFails internal inline fun diff( order: Int, vararg parameters: Pair, - block: DerivativeStructureField.() -> Unit, + block: DSField.() -> Unit, ) { contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - DerivativeStructureField(DoubleField, ::DoubleBuffer, order, mapOf(*parameters)).block() + DSField(DoubleField, ::DoubleBuffer, order, mapOf(*parameters)).block() } internal class AutoDiffTest { -- 2.34.1 From 846a6d2620810dc9e15538befba437f0882a77db Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 15 Jul 2022 17:20:00 +0300 Subject: [PATCH 57/59] Grand derivative refactoring. Phase 3 --- .../kscience/kmath/expressions/DSAlgebra.kt | 143 ++++++++++-------- .../kscience/kmath/expressions/DSCompiler.kt | 28 ++-- 2 files changed, 96 insertions(+), 75 deletions(-) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt index d9fc46b47..506fbd001 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt @@ -44,9 +44,29 @@ public interface DS> { * @see value */ @UnstableKMathAPI -public fun > DS.getPartialDerivative(vararg orders: Int): T = +private fun > DS.getPartialDerivative(vararg orders: Int): T = data[derivativeAlgebra.compiler.getPartialDerivativeIndex(*orders)] +/** + * Provide a partial derivative with given symbols. On symbol could me mentioned multiple times + */ +@UnstableKMathAPI +public fun > DS.derivative(symbols: List): T { + require(symbols.size <= derivativeAlgebra.order) { "The order of derivative ${symbols.size} exceeds computed order ${derivativeAlgebra.order}" } + val ordersCount: Map = symbols.map { it.identity }.groupBy { it }.mapValues { it.value.size } + return getPartialDerivative(*symbols.map { ordersCount[it] ?: 0 }.toIntArray()) +} + +/** + * Provide a partial derivative with given symbols. On symbol could me mentioned multiple times + */ +@UnstableKMathAPI +public fun > DS.derivative(vararg symbols: Symbol): T { + require(symbols.size <= derivativeAlgebra.order) { "The order of derivative ${symbols.size} exceeds computed order ${derivativeAlgebra.order}" } + val ordersCount: Map = symbols.map { it.identity }.groupBy { it }.mapValues { it.value.size } + return getPartialDerivative(*symbols.map { ordersCount[it] ?: 0 }.toIntArray()) +} + /** * The value part of the derivative structure. * @@ -61,9 +81,67 @@ public abstract class DSAlgebra>( public val bufferFactory: MutableBufferFactory, public val order: Int, bindings: Map, -) : ExpressionAlgebra> { +) : ExpressionAlgebra>, SymbolIndexer { + + /** + * Get the compiler for number of free parameters and order. + * + * @return cached rules set. + */ + @PublishedApi + internal val compiler: DSCompiler by lazy { + // get the cached compilers + val cache: Array?>>? = null + + // we need to create more compilers + val maxParameters: Int = max(numberOfVariables, cache?.size ?: 0) + val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) + val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } + + if (cache != null) { + // preserve the already created compilers + for (i in cache.indices) { + cache[i].copyInto(newCache[i], endIndex = cache[i].size) + } + } + + // create the array in increasing diagonal order + for (diag in 0..numberOfVariables + order) { + for (o in max(0, diag - numberOfVariables)..min(order, diag)) { + val p: Int = diag - o + if (newCache[p][o] == null) { + val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! + val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! + + newCache[p][o] = DSCompiler( + algebra, + bufferFactory, + p, + o, + valueCompiler, + derivativeCompiler, + ) + } + } + } + + return@lazy newCache[numberOfVariables][order]!! + } + + private val variables: Map by lazy { + bindings.entries.mapIndexed { index, (key, value) -> + key to DSSymbol( + index, + key, + value, + ) + }.toMap() + } + override val symbols: List = bindings.map { it.key } + + public val numberOfVariables: Int get() = symbols.size + - @OptIn(UnstableKMathAPI::class) private fun bufferForVariable(index: Int, value: T): Buffer { val buffer = bufferFactory(compiler.size) { algebra.zero } buffer[0] = value @@ -80,7 +158,7 @@ public abstract class DSAlgebra>( } @UnstableKMathAPI - protected inner class DSImpl internal constructor( + private inner class DSImpl( override val data: Buffer, ) : DS { override val derivativeAlgebra: DSAlgebra get() = this@DSAlgebra @@ -130,63 +208,6 @@ public abstract class DSAlgebra>( override val data: Buffer = bufferForVariable(index, value) } - - public val numberOfVariables: Int = bindings.size - - /** - * Get the compiler for number of free parameters and order. - * - * @return cached rules set. - */ - @PublishedApi - internal val compiler: DSCompiler by lazy { - // get the cached compilers - val cache: Array?>>? = null - - // we need to create more compilers - val maxParameters: Int = max(numberOfVariables, cache?.size ?: 0) - val maxOrder: Int = max(order, if (cache == null) 0 else cache[0].size) - val newCache: Array?>> = Array(maxParameters + 1) { arrayOfNulls(maxOrder + 1) } - - if (cache != null) { - // preserve the already created compilers - for (i in cache.indices) { - cache[i].copyInto(newCache[i], endIndex = cache[i].size) - } - } - - // create the array in increasing diagonal order - for (diag in 0..numberOfVariables + order) { - for (o in max(0, diag - numberOfVariables)..min(order, diag)) { - val p: Int = diag - o - if (newCache[p][o] == null) { - val valueCompiler: DSCompiler? = if (p == 0) null else newCache[p - 1][o]!! - val derivativeCompiler: DSCompiler? = if (o == 0) null else newCache[p][o - 1]!! - - newCache[p][o] = DSCompiler( - algebra, - bufferFactory, - p, - o, - valueCompiler, - derivativeCompiler, - ) - } - } - } - - return@lazy newCache[numberOfVariables][order]!! - } - - private val variables: Map = bindings.entries.mapIndexed { index, (key, value) -> - key to DSSymbol( - index, - key, - value, - ) - }.toMap() - - public override fun const(value: T): DS { val buffer = bufferFactory(compiler.size) { algebra.zero } buffer[0] = value diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt index e0050cf03..b5b2988a3 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSCompiler.kt @@ -52,20 +52,20 @@ internal fun MutableBuffer.fill(element: T, fromIndex: Int = 0, toIndex: * * @property freeParameters Number of free parameters. * @property order Derivation order. - * @see DerivativeStructure + * @see DS */ -class DSCompiler> internal constructor( - val algebra: A, - val bufferFactory: MutableBufferFactory, - val freeParameters: Int, - val order: Int, +public class DSCompiler> internal constructor( + public val algebra: A, + public val bufferFactory: MutableBufferFactory, + public val freeParameters: Int, + public val order: Int, valueCompiler: DSCompiler?, derivativeCompiler: DSCompiler?, ) { /** * Number of partial derivatives (including the single 0 order derivative element). */ - val sizes: Array by lazy { + public val sizes: Array by lazy { compileSizes( freeParameters, order, @@ -76,7 +76,7 @@ class DSCompiler> internal constructor( /** * Indirection array for partial derivatives. */ - val derivativesIndirection: Array by lazy { + internal val derivativesIndirection: Array by lazy { compileDerivativesIndirection( freeParameters, order, valueCompiler, derivativeCompiler, @@ -86,7 +86,7 @@ class DSCompiler> internal constructor( /** * Indirection array of the lower derivative elements. */ - val lowerIndirection: IntArray by lazy { + internal val lowerIndirection: IntArray by lazy { compileLowerIndirection( freeParameters, order, valueCompiler, derivativeCompiler, @@ -96,7 +96,7 @@ class DSCompiler> internal constructor( /** * Indirection arrays for multiplication. */ - val multIndirection: Array> by lazy { + internal val multIndirection: Array> by lazy { compileMultiplicationIndirection( freeParameters, order, valueCompiler, derivativeCompiler, lowerIndirection, @@ -106,7 +106,7 @@ class DSCompiler> internal constructor( /** * Indirection arrays for function composition. */ - val compositionIndirection: Array> by lazy { + internal val compositionIndirection: Array> by lazy { compileCompositionIndirection( freeParameters, order, valueCompiler, derivativeCompiler, @@ -120,7 +120,7 @@ class DSCompiler> internal constructor( * This number includes the single 0 order derivative element, which is * guaranteed to be stored in the first element of the array. */ - val size: Int get() = sizes[freeParameters][order] + public val size: Int get() = sizes[freeParameters][order] /** * Get the index of a partial derivative in the array. @@ -147,7 +147,7 @@ class DSCompiler> internal constructor( * @return index of the partial derivative. * @see getPartialDerivativeOrders */ - fun getPartialDerivativeIndex(vararg orders: Int): Int { + public fun getPartialDerivativeIndex(vararg orders: Int): Int { // safety check require(orders.size == freeParameters) { "dimension mismatch: ${orders.size} and $freeParameters" } return getPartialDerivativeIndex(freeParameters, order, sizes, *orders) @@ -162,7 +162,7 @@ class DSCompiler> internal constructor( * @return orders derivation orders with respect to each parameter * @see getPartialDerivativeIndex */ - fun getPartialDerivativeOrders(index: Int): IntArray = derivativesIndirection[index] + public fun getPartialDerivativeOrders(index: Int): IntArray = derivativesIndirection[index] } /** -- 2.34.1 From bfadf5b33d545ac0e4d40f2253e20e0ad88e4ba0 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 15 Jul 2022 17:31:28 +0300 Subject: [PATCH 58/59] Name refactor --- .../kotlin/space/kscience/kmath/expressions/DSAlgebra.kt | 2 +- .../kmath/expressions/DerivativeStructureExpressionTest.kt | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt index 506fbd001..59e6f4f6f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DSAlgebra.kt @@ -439,7 +439,7 @@ public class DSField>( } @UnstableKMathAPI -public class DerivativeStructureFieldExpression>( +public class DSFieldExpression>( public val algebra: A, public val bufferFactory: MutableBufferFactory, public val function: DSField.() -> DS, diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt index fdeda4512..e5bc9805a 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DerivativeStructureExpressionTest.kt @@ -30,7 +30,7 @@ internal class AutoDiffTest { private val y by symbol @Test - fun derivativeStructureFieldTest() { + fun dsAlgebraTest() { diff(2, x to 1.0, y to 1.0) { val x = bindSymbol(x)//by binding() val y = bindSymbol("y") @@ -44,8 +44,8 @@ internal class AutoDiffTest { } @Test - fun autoDifTest() { - val f = DerivativeStructureFieldExpression(DoubleField, ::DoubleBuffer) { + fun dsExpressionTest() { + val f = DSFieldExpression(DoubleField, ::DoubleBuffer) { val x by binding val y by binding x.pow(2) + 2 * x * y + y.pow(2) + 1 -- 2.34.1 From 18ae964e57a2d1059aaa4f17909da45c3a4a1972 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Fri, 15 Jul 2022 17:35:13 +0300 Subject: [PATCH 59/59] Name refactor --- .../space/kscience/kmath/ejml/_generated.kt | 1003 +++++++++++++++++ 1 file changed, 1003 insertions(+) create mode 100644 kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt new file mode 100644 index 000000000..aac327a84 --- /dev/null +++ b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/_generated.kt @@ -0,0 +1,1003 @@ +/* + * Copyright 2018-2021 KMath contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. + */ + +/* This file is generated with buildSrc/src/main/kotlin/space/kscience/kmath/ejml/codegen/ejmlCodegen.kt */ + +package space.kscience.kmath.ejml + +import org.ejml.data.* +import org.ejml.dense.row.CommonOps_DDRM +import org.ejml.dense.row.CommonOps_FDRM +import org.ejml.dense.row.factory.DecompositionFactory_DDRM +import org.ejml.dense.row.factory.DecompositionFactory_FDRM +import org.ejml.sparse.FillReducing +import org.ejml.sparse.csc.CommonOps_DSCC +import org.ejml.sparse.csc.CommonOps_FSCC +import org.ejml.sparse.csc.factory.DecompositionFactory_DSCC +import org.ejml.sparse.csc.factory.DecompositionFactory_FSCC +import org.ejml.sparse.csc.factory.LinearSolverFactory_DSCC +import org.ejml.sparse.csc.factory.LinearSolverFactory_FSCC +import space.kscience.kmath.linear.* +import space.kscience.kmath.linear.Matrix +import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.nd.StructureFeature +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.operations.FloatField +import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.structures.FloatBuffer +import kotlin.reflect.KClass +import kotlin.reflect.cast + +/** + * [EjmlVector] specialization for [Double]. + */ +public class EjmlDoubleVector(override val origin: M) : EjmlVector(origin) { + init { + require(origin.numRows == 1) { "The origin matrix must have only one row to form a vector" } + } + + override operator fun get(index: Int): Double = origin[0, index] +} + +/** + * [EjmlVector] specialization for [Float]. + */ +public class EjmlFloatVector(override val origin: M) : EjmlVector(origin) { + init { + require(origin.numRows == 1) { "The origin matrix must have only one row to form a vector" } + } + + override operator fun get(index: Int): Float = origin[0, index] +} + +/** + * [EjmlMatrix] specialization for [Double]. + */ +public class EjmlDoubleMatrix(override val origin: M) : EjmlMatrix(origin) { + override operator fun get(i: Int, j: Int): Double = origin[i, j] +} + +/** + * [EjmlMatrix] specialization for [Float]. + */ +public class EjmlFloatMatrix(override val origin: M) : EjmlMatrix(origin) { + override operator fun get(i: Int, j: Int): Float = origin[i, j] +} + +/** + * [EjmlLinearSpace] implementation based on [CommonOps_DDRM], [DecompositionFactory_DDRM] operations and + * [DMatrixRMaj] matrices. + */ +public object EjmlLinearSpaceDDRM : EjmlLinearSpace() { + /** + * The [DoubleField] reference. + */ + override val elementAlgebra: DoubleField get() = DoubleField + + @Suppress("UNCHECKED_CAST") + override fun Matrix.toEjml(): EjmlDoubleMatrix = when { + this is EjmlDoubleMatrix<*> && origin is DMatrixRMaj -> this as EjmlDoubleMatrix + else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } + } + + @Suppress("UNCHECKED_CAST") + override fun Point.toEjml(): EjmlDoubleVector = when { + this is EjmlDoubleVector<*> && origin is DMatrixRMaj -> this as EjmlDoubleVector + else -> EjmlDoubleVector(DMatrixRMaj(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } + }) + } + + override fun buildMatrix( + rows: Int, + columns: Int, + initializer: DoubleField.(i: Int, j: Int) -> Double, + ): EjmlDoubleMatrix = DMatrixRMaj(rows, columns).also { + (0 until rows).forEach { row -> + (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } + } + }.wrapMatrix() + + override fun buildVector( + size: Int, + initializer: DoubleField.(Int) -> Double, + ): EjmlDoubleVector = EjmlDoubleVector(DMatrixRMaj(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } + }) + + private fun T.wrapMatrix() = EjmlDoubleMatrix(this) + private fun T.wrapVector() = EjmlDoubleVector(this) + + override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } + + override fun Matrix.dot(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixRMaj(1, 1) + CommonOps_DDRM.mult(toEjml().origin, other.toEjml().origin, out) + return out.wrapMatrix() + } + + override fun Matrix.dot(vector: Point): EjmlDoubleVector { + val out = DMatrixRMaj(1, 1) + CommonOps_DDRM.mult(toEjml().origin, vector.toEjml().origin, out) + return out.wrapVector() + } + + override operator fun Matrix.minus(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixRMaj(1, 1) + + CommonOps_DDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + ) + + return out.wrapMatrix() + } + + override operator fun Matrix.times(value: Double): EjmlDoubleMatrix { + val res = DMatrixRMaj(1, 1) + CommonOps_DDRM.scale(value, toEjml().origin, res) + return res.wrapMatrix() + } + + override fun Point.unaryMinus(): EjmlDoubleVector { + val res = DMatrixRMaj(1, 1) + CommonOps_DDRM.changeSign(toEjml().origin, res) + return res.wrapVector() + } + + override fun Matrix.plus(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixRMaj(1, 1) + + CommonOps_DDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + ) + + return out.wrapMatrix() + } + + override fun Point.plus(other: Point): EjmlDoubleVector { + val out = DMatrixRMaj(1, 1) + + CommonOps_DDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + ) + + return out.wrapVector() + } + + override fun Point.minus(other: Point): EjmlDoubleVector { + val out = DMatrixRMaj(1, 1) + + CommonOps_DDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + ) + + return out.wrapVector() + } + + override fun Double.times(m: Matrix): EjmlDoubleMatrix = m * this + + override fun Point.times(value: Double): EjmlDoubleVector { + val res = DMatrixRMaj(1, 1) + CommonOps_DDRM.scale(value, toEjml().origin, res) + return res.wrapVector() + } + + override fun Double.times(v: Point): EjmlDoubleVector = v * this + + @UnstableKMathAPI + override fun computeFeature(structure: Matrix, type: KClass): F? { + structure.getFeature(type)?.let { return it } + val origin = structure.toEjml().origin + + return when (type) { + InverseMatrixFeature::class -> object : InverseMatrixFeature { + override val inverse: Matrix by lazy { + val res = origin.copy() + CommonOps_DDRM.invert(res) + res.wrapMatrix() + } + } + + DeterminantFeature::class -> object : DeterminantFeature { + override val determinant: Double by lazy { CommonOps_DDRM.det(origin) } + } + + SingularValueDecompositionFeature::class -> object : SingularValueDecompositionFeature { + private val svd by lazy { + DecompositionFactory_DDRM.svd(origin.numRows, origin.numCols, true, true, false) + .apply { decompose(origin.copy()) } + } + + override val u: Matrix by lazy { svd.getU(null, false).wrapMatrix() } + override val s: Matrix by lazy { svd.getW(null).wrapMatrix() } + override val v: Matrix by lazy { svd.getV(null, false).wrapMatrix() } + override val singularValues: Point by lazy { DoubleBuffer(svd.singularValues) } + } + + QRDecompositionFeature::class -> object : QRDecompositionFeature { + private val qr by lazy { + DecompositionFactory_DDRM.qr().apply { decompose(origin.copy()) } + } + + override val q: Matrix by lazy { + qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) + } + + override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } + } + + CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { + override val l: Matrix by lazy { + val cholesky = + DecompositionFactory_DDRM.chol(structure.rowNum, true).apply { decompose(origin.copy()) } + + cholesky.getT(null).wrapMatrix().withFeature(LFeature) + } + } + + LupDecompositionFeature::class -> object : LupDecompositionFeature { + private val lup by lazy { + DecompositionFactory_DDRM.lu(origin.numRows, origin.numCols).apply { decompose(origin.copy()) } + } + + override val l: Matrix by lazy { + lup.getLower(null).wrapMatrix().withFeature(LFeature) + } + + override val u: Matrix by lazy { + lup.getUpper(null).wrapMatrix().withFeature(UFeature) + } + + override val p: Matrix by lazy { lup.getRowPivot(null).wrapMatrix() } + } + + else -> null + }?.let{ + type.cast(it) + } + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p matrix. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Matrix): EjmlDoubleMatrix { + val res = DMatrixRMaj(1, 1) + CommonOps_DDRM.solve(DMatrixRMaj(a.toEjml().origin), DMatrixRMaj(b.toEjml().origin), res) + return res.wrapMatrix() + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p vector. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Point): EjmlDoubleVector { + val res = DMatrixRMaj(1, 1) + CommonOps_DDRM.solve(DMatrixRMaj(a.toEjml().origin), DMatrixRMaj(b.toEjml().origin), res) + return EjmlDoubleVector(res) + } +} + +/** + * [EjmlLinearSpace] implementation based on [CommonOps_FDRM], [DecompositionFactory_FDRM] operations and + * [FMatrixRMaj] matrices. + */ +public object EjmlLinearSpaceFDRM : EjmlLinearSpace() { + /** + * The [FloatField] reference. + */ + override val elementAlgebra: FloatField get() = FloatField + + @Suppress("UNCHECKED_CAST") + override fun Matrix.toEjml(): EjmlFloatMatrix = when { + this is EjmlFloatMatrix<*> && origin is FMatrixRMaj -> this as EjmlFloatMatrix + else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } + } + + @Suppress("UNCHECKED_CAST") + override fun Point.toEjml(): EjmlFloatVector = when { + this is EjmlFloatVector<*> && origin is FMatrixRMaj -> this as EjmlFloatVector + else -> EjmlFloatVector(FMatrixRMaj(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } + }) + } + + override fun buildMatrix( + rows: Int, + columns: Int, + initializer: FloatField.(i: Int, j: Int) -> Float, + ): EjmlFloatMatrix = FMatrixRMaj(rows, columns).also { + (0 until rows).forEach { row -> + (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } + } + }.wrapMatrix() + + override fun buildVector( + size: Int, + initializer: FloatField.(Int) -> Float, + ): EjmlFloatVector = EjmlFloatVector(FMatrixRMaj(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } + }) + + private fun T.wrapMatrix() = EjmlFloatMatrix(this) + private fun T.wrapVector() = EjmlFloatVector(this) + + override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } + + override fun Matrix.dot(other: Matrix): EjmlFloatMatrix { + val out = FMatrixRMaj(1, 1) + CommonOps_FDRM.mult(toEjml().origin, other.toEjml().origin, out) + return out.wrapMatrix() + } + + override fun Matrix.dot(vector: Point): EjmlFloatVector { + val out = FMatrixRMaj(1, 1) + CommonOps_FDRM.mult(toEjml().origin, vector.toEjml().origin, out) + return out.wrapVector() + } + + override operator fun Matrix.minus(other: Matrix): EjmlFloatMatrix { + val out = FMatrixRMaj(1, 1) + + CommonOps_FDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + ) + + return out.wrapMatrix() + } + + override operator fun Matrix.times(value: Float): EjmlFloatMatrix { + val res = FMatrixRMaj(1, 1) + CommonOps_FDRM.scale(value, toEjml().origin, res) + return res.wrapMatrix() + } + + override fun Point.unaryMinus(): EjmlFloatVector { + val res = FMatrixRMaj(1, 1) + CommonOps_FDRM.changeSign(toEjml().origin, res) + return res.wrapVector() + } + + override fun Matrix.plus(other: Matrix): EjmlFloatMatrix { + val out = FMatrixRMaj(1, 1) + + CommonOps_FDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + ) + + return out.wrapMatrix() + } + + override fun Point.plus(other: Point): EjmlFloatVector { + val out = FMatrixRMaj(1, 1) + + CommonOps_FDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + ) + + return out.wrapVector() + } + + override fun Point.minus(other: Point): EjmlFloatVector { + val out = FMatrixRMaj(1, 1) + + CommonOps_FDRM.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + ) + + return out.wrapVector() + } + + override fun Float.times(m: Matrix): EjmlFloatMatrix = m * this + + override fun Point.times(value: Float): EjmlFloatVector { + val res = FMatrixRMaj(1, 1) + CommonOps_FDRM.scale(value, toEjml().origin, res) + return res.wrapVector() + } + + override fun Float.times(v: Point): EjmlFloatVector = v * this + + @UnstableKMathAPI + override fun computeFeature(structure: Matrix, type: KClass): F? { + structure.getFeature(type)?.let { return it } + val origin = structure.toEjml().origin + + return when (type) { + InverseMatrixFeature::class -> object : InverseMatrixFeature { + override val inverse: Matrix by lazy { + val res = origin.copy() + CommonOps_FDRM.invert(res) + res.wrapMatrix() + } + } + + DeterminantFeature::class -> object : DeterminantFeature { + override val determinant: Float by lazy { CommonOps_FDRM.det(origin) } + } + + SingularValueDecompositionFeature::class -> object : SingularValueDecompositionFeature { + private val svd by lazy { + DecompositionFactory_FDRM.svd(origin.numRows, origin.numCols, true, true, false) + .apply { decompose(origin.copy()) } + } + + override val u: Matrix by lazy { svd.getU(null, false).wrapMatrix() } + override val s: Matrix by lazy { svd.getW(null).wrapMatrix() } + override val v: Matrix by lazy { svd.getV(null, false).wrapMatrix() } + override val singularValues: Point by lazy { FloatBuffer(svd.singularValues) } + } + + QRDecompositionFeature::class -> object : QRDecompositionFeature { + private val qr by lazy { + DecompositionFactory_FDRM.qr().apply { decompose(origin.copy()) } + } + + override val q: Matrix by lazy { + qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) + } + + override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } + } + + CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { + override val l: Matrix by lazy { + val cholesky = + DecompositionFactory_FDRM.chol(structure.rowNum, true).apply { decompose(origin.copy()) } + + cholesky.getT(null).wrapMatrix().withFeature(LFeature) + } + } + + LupDecompositionFeature::class -> object : LupDecompositionFeature { + private val lup by lazy { + DecompositionFactory_FDRM.lu(origin.numRows, origin.numCols).apply { decompose(origin.copy()) } + } + + override val l: Matrix by lazy { + lup.getLower(null).wrapMatrix().withFeature(LFeature) + } + + override val u: Matrix by lazy { + lup.getUpper(null).wrapMatrix().withFeature(UFeature) + } + + override val p: Matrix by lazy { lup.getRowPivot(null).wrapMatrix() } + } + + else -> null + }?.let{ + type.cast(it) + } + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p matrix. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Matrix): EjmlFloatMatrix { + val res = FMatrixRMaj(1, 1) + CommonOps_FDRM.solve(FMatrixRMaj(a.toEjml().origin), FMatrixRMaj(b.toEjml().origin), res) + return res.wrapMatrix() + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p vector. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Point): EjmlFloatVector { + val res = FMatrixRMaj(1, 1) + CommonOps_FDRM.solve(FMatrixRMaj(a.toEjml().origin), FMatrixRMaj(b.toEjml().origin), res) + return EjmlFloatVector(res) + } +} + +/** + * [EjmlLinearSpace] implementation based on [CommonOps_DSCC], [DecompositionFactory_DSCC] operations and + * [DMatrixSparseCSC] matrices. + */ +public object EjmlLinearSpaceDSCC : EjmlLinearSpace() { + /** + * The [DoubleField] reference. + */ + override val elementAlgebra: DoubleField get() = DoubleField + + @Suppress("UNCHECKED_CAST") + override fun Matrix.toEjml(): EjmlDoubleMatrix = when { + this is EjmlDoubleMatrix<*> && origin is DMatrixSparseCSC -> this as EjmlDoubleMatrix + else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } + } + + @Suppress("UNCHECKED_CAST") + override fun Point.toEjml(): EjmlDoubleVector = when { + this is EjmlDoubleVector<*> && origin is DMatrixSparseCSC -> this as EjmlDoubleVector + else -> EjmlDoubleVector(DMatrixSparseCSC(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } + }) + } + + override fun buildMatrix( + rows: Int, + columns: Int, + initializer: DoubleField.(i: Int, j: Int) -> Double, + ): EjmlDoubleMatrix = DMatrixSparseCSC(rows, columns).also { + (0 until rows).forEach { row -> + (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } + } + }.wrapMatrix() + + override fun buildVector( + size: Int, + initializer: DoubleField.(Int) -> Double, + ): EjmlDoubleVector = EjmlDoubleVector(DMatrixSparseCSC(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } + }) + + private fun T.wrapMatrix() = EjmlDoubleMatrix(this) + private fun T.wrapVector() = EjmlDoubleVector(this) + + override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } + + override fun Matrix.dot(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.mult(toEjml().origin, other.toEjml().origin, out) + return out.wrapMatrix() + } + + override fun Matrix.dot(vector: Point): EjmlDoubleVector { + val out = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.mult(toEjml().origin, vector.toEjml().origin, out) + return out.wrapVector() + } + + override operator fun Matrix.minus(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixSparseCSC(1, 1) + + CommonOps_DSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapMatrix() + } + + override operator fun Matrix.times(value: Double): EjmlDoubleMatrix { + val res = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.scale(value, toEjml().origin, res) + return res.wrapMatrix() + } + + override fun Point.unaryMinus(): EjmlDoubleVector { + val res = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.changeSign(toEjml().origin, res) + return res.wrapVector() + } + + override fun Matrix.plus(other: Matrix): EjmlDoubleMatrix { + val out = DMatrixSparseCSC(1, 1) + + CommonOps_DSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapMatrix() + } + + override fun Point.plus(other: Point): EjmlDoubleVector { + val out = DMatrixSparseCSC(1, 1) + + CommonOps_DSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapVector() + } + + override fun Point.minus(other: Point): EjmlDoubleVector { + val out = DMatrixSparseCSC(1, 1) + + CommonOps_DSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapVector() + } + + override fun Double.times(m: Matrix): EjmlDoubleMatrix = m * this + + override fun Point.times(value: Double): EjmlDoubleVector { + val res = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.scale(value, toEjml().origin, res) + return res.wrapVector() + } + + override fun Double.times(v: Point): EjmlDoubleVector = v * this + + @UnstableKMathAPI + override fun computeFeature(structure: Matrix, type: KClass): F? { + structure.getFeature(type)?.let { return it } + val origin = structure.toEjml().origin + + return when (type) { + QRDecompositionFeature::class -> object : QRDecompositionFeature { + private val qr by lazy { + DecompositionFactory_DSCC.qr(FillReducing.NONE).apply { decompose(origin.copy()) } + } + + override val q: Matrix by lazy { + qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) + } + + override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } + } + + CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { + override val l: Matrix by lazy { + val cholesky = + DecompositionFactory_DSCC.cholesky().apply { decompose(origin.copy()) } + + (cholesky.getT(null) as DMatrix).wrapMatrix().withFeature(LFeature) + } + } + + LUDecompositionFeature::class, DeterminantFeature::class, InverseMatrixFeature::class -> object : + LUDecompositionFeature, DeterminantFeature, InverseMatrixFeature { + private val lu by lazy { + DecompositionFactory_DSCC.lu(FillReducing.NONE).apply { decompose(origin.copy()) } + } + + override val l: Matrix by lazy { + lu.getLower(null).wrapMatrix().withFeature(LFeature) + } + + override val u: Matrix by lazy { + lu.getUpper(null).wrapMatrix().withFeature(UFeature) + } + + override val inverse: Matrix by lazy { + var a = origin + val inverse = DMatrixRMaj(1, 1) + val solver = LinearSolverFactory_DSCC.lu(FillReducing.NONE) + if (solver.modifiesA()) a = a.copy() + val i = CommonOps_DDRM.identity(a.numRows) + solver.solve(i, inverse) + inverse.wrapMatrix() + } + + override val determinant: Double by lazy { elementAlgebra.number(lu.computeDeterminant().real) } + } + + else -> null + }?.let{ + type.cast(it) + } + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p matrix. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Matrix): EjmlDoubleMatrix { + val res = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.solve(DMatrixSparseCSC(a.toEjml().origin), DMatrixSparseCSC(b.toEjml().origin), res) + return res.wrapMatrix() + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p vector. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Point): EjmlDoubleVector { + val res = DMatrixSparseCSC(1, 1) + CommonOps_DSCC.solve(DMatrixSparseCSC(a.toEjml().origin), DMatrixSparseCSC(b.toEjml().origin), res) + return EjmlDoubleVector(res) + } +} + +/** + * [EjmlLinearSpace] implementation based on [CommonOps_FSCC], [DecompositionFactory_FSCC] operations and + * [FMatrixSparseCSC] matrices. + */ +public object EjmlLinearSpaceFSCC : EjmlLinearSpace() { + /** + * The [FloatField] reference. + */ + override val elementAlgebra: FloatField get() = FloatField + + @Suppress("UNCHECKED_CAST") + override fun Matrix.toEjml(): EjmlFloatMatrix = when { + this is EjmlFloatMatrix<*> && origin is FMatrixSparseCSC -> this as EjmlFloatMatrix + else -> buildMatrix(rowNum, colNum) { i, j -> get(i, j) } + } + + @Suppress("UNCHECKED_CAST") + override fun Point.toEjml(): EjmlFloatVector = when { + this is EjmlFloatVector<*> && origin is FMatrixSparseCSC -> this as EjmlFloatVector + else -> EjmlFloatVector(FMatrixSparseCSC(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = get(row) } + }) + } + + override fun buildMatrix( + rows: Int, + columns: Int, + initializer: FloatField.(i: Int, j: Int) -> Float, + ): EjmlFloatMatrix = FMatrixSparseCSC(rows, columns).also { + (0 until rows).forEach { row -> + (0 until columns).forEach { col -> it[row, col] = elementAlgebra.initializer(row, col) } + } + }.wrapMatrix() + + override fun buildVector( + size: Int, + initializer: FloatField.(Int) -> Float, + ): EjmlFloatVector = EjmlFloatVector(FMatrixSparseCSC(size, 1).also { + (0 until it.numRows).forEach { row -> it[row, 0] = elementAlgebra.initializer(row) } + }) + + private fun T.wrapMatrix() = EjmlFloatMatrix(this) + private fun T.wrapVector() = EjmlFloatVector(this) + + override fun Matrix.unaryMinus(): Matrix = this * elementAlgebra { -one } + + override fun Matrix.dot(other: Matrix): EjmlFloatMatrix { + val out = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.mult(toEjml().origin, other.toEjml().origin, out) + return out.wrapMatrix() + } + + override fun Matrix.dot(vector: Point): EjmlFloatVector { + val out = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.mult(toEjml().origin, vector.toEjml().origin, out) + return out.wrapVector() + } + + override operator fun Matrix.minus(other: Matrix): EjmlFloatMatrix { + val out = FMatrixSparseCSC(1, 1) + + CommonOps_FSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapMatrix() + } + + override operator fun Matrix.times(value: Float): EjmlFloatMatrix { + val res = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.scale(value, toEjml().origin, res) + return res.wrapMatrix() + } + + override fun Point.unaryMinus(): EjmlFloatVector { + val res = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.changeSign(toEjml().origin, res) + return res.wrapVector() + } + + override fun Matrix.plus(other: Matrix): EjmlFloatMatrix { + val out = FMatrixSparseCSC(1, 1) + + CommonOps_FSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapMatrix() + } + + override fun Point.plus(other: Point): EjmlFloatVector { + val out = FMatrixSparseCSC(1, 1) + + CommonOps_FSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra.one, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapVector() + } + + override fun Point.minus(other: Point): EjmlFloatVector { + val out = FMatrixSparseCSC(1, 1) + + CommonOps_FSCC.add( + elementAlgebra.one, + toEjml().origin, + elementAlgebra { -one }, + other.toEjml().origin, + out, + null, + null, + ) + + return out.wrapVector() + } + + override fun Float.times(m: Matrix): EjmlFloatMatrix = m * this + + override fun Point.times(value: Float): EjmlFloatVector { + val res = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.scale(value, toEjml().origin, res) + return res.wrapVector() + } + + override fun Float.times(v: Point): EjmlFloatVector = v * this + + @UnstableKMathAPI + override fun computeFeature(structure: Matrix, type: KClass): F? { + structure.getFeature(type)?.let { return it } + val origin = structure.toEjml().origin + + return when (type) { + QRDecompositionFeature::class -> object : QRDecompositionFeature { + private val qr by lazy { + DecompositionFactory_FSCC.qr(FillReducing.NONE).apply { decompose(origin.copy()) } + } + + override val q: Matrix by lazy { + qr.getQ(null, false).wrapMatrix().withFeature(OrthogonalFeature) + } + + override val r: Matrix by lazy { qr.getR(null, false).wrapMatrix().withFeature(UFeature) } + } + + CholeskyDecompositionFeature::class -> object : CholeskyDecompositionFeature { + override val l: Matrix by lazy { + val cholesky = + DecompositionFactory_FSCC.cholesky().apply { decompose(origin.copy()) } + + (cholesky.getT(null) as FMatrix).wrapMatrix().withFeature(LFeature) + } + } + + LUDecompositionFeature::class, DeterminantFeature::class, InverseMatrixFeature::class -> object : + LUDecompositionFeature, DeterminantFeature, InverseMatrixFeature { + private val lu by lazy { + DecompositionFactory_FSCC.lu(FillReducing.NONE).apply { decompose(origin.copy()) } + } + + override val l: Matrix by lazy { + lu.getLower(null).wrapMatrix().withFeature(LFeature) + } + + override val u: Matrix by lazy { + lu.getUpper(null).wrapMatrix().withFeature(UFeature) + } + + override val inverse: Matrix by lazy { + var a = origin + val inverse = FMatrixRMaj(1, 1) + val solver = LinearSolverFactory_FSCC.lu(FillReducing.NONE) + if (solver.modifiesA()) a = a.copy() + val i = CommonOps_FDRM.identity(a.numRows) + solver.solve(i, inverse) + inverse.wrapMatrix() + } + + override val determinant: Float by lazy { elementAlgebra.number(lu.computeDeterminant().real) } + } + + else -> null + }?.let{ + type.cast(it) + } + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p matrix. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Matrix): EjmlFloatMatrix { + val res = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.solve(FMatrixSparseCSC(a.toEjml().origin), FMatrixSparseCSC(b.toEjml().origin), res) + return res.wrapMatrix() + } + + /** + * Solves for *x* in the following equation: *x = [a] -1 · [b]*. + * + * @param a the base matrix. + * @param b n by p vector. + * @return the solution for *x* that is n by p. + */ + public fun solve(a: Matrix, b: Point): EjmlFloatVector { + val res = FMatrixSparseCSC(1, 1) + CommonOps_FSCC.solve(FMatrixSparseCSC(a.toEjml().origin), FMatrixSparseCSC(b.toEjml().origin), res) + return EjmlFloatVector(res) + } +} + -- 2.34.1