diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index cffef64b0..6ad294e18 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -7,26 +7,18 @@ on: jobs: build: - strategy: - matrix: - os: [ macOS-latest, windows-latest ] - runs-on: ${{matrix.os}} - timeout-minutes: 40 + runs-on: windows-latest + timeout-minutes: 20 steps: - - uses: actions/checkout@v3.0.0 - - uses: actions/setup-java@v3.0.0 + - uses: actions/checkout@v3 + - uses: actions/setup-java@v3.5.1 with: - java-version: 11 - distribution: liberica - - name: Cache konan - uses: actions/cache@v3.0.1 - with: - path: ~/.konan - key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} - restore-keys: | - ${{ runner.os }}-gradle- + java-version: '11' + distribution: 'liberica' + cache: 'gradle' - name: Gradle Wrapper Validation uses: gradle/wrapper-validation-action@v1.0.4 - - uses: gradle/gradle-build-action@v2.1.5 + - name: Gradle Build + uses: gradle/gradle-build-action@v2.4.2 with: - arguments: build + arguments: test jvmTest diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 2abaf0b9f..ba1f5d1e3 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -22,7 +22,7 @@ jobs: key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} restore-keys: | ${{ runner.os }}-gradle- - - uses: gradle/gradle-build-action@v2.1.5 + - uses: gradle/gradle-build-action@v2.4.2 with: arguments: dokkaHtmlMultiModule --no-parallel - uses: JamesIves/github-pages-deploy-action@v4.3.0 diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 794881b09..31d539cdd 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -15,7 +15,7 @@ jobs: runs-on: ${{matrix.os}} steps: - uses: actions/checkout@v3.0.0 - - uses: actions/setup-java@v3.0.0 + - uses: actions/setup-java@v3.10.0 with: java-version: 11 distribution: liberica @@ -26,26 +26,25 @@ jobs: key: ${{ runner.os }}-gradle-${{ hashFiles('*.gradle.kts') }} restore-keys: | ${{ runner.os }}-gradle- - - uses: gradle/wrapper-validation-action@v1.0.4 - name: Publish Windows Artifacts if: matrix.os == 'windows-latest' - uses: gradle/gradle-build-action@v2.1.5 + uses: gradle/gradle-build-action@v2.4.2 with: arguments: | - releaseAll - -Ppublishing.enabled=true - -Ppublishing.sonatype=false + publishAllPublicationsToSpaceRepository + -Ppublishing.targets=all -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} - name: Publish Mac Artifacts if: matrix.os == 'macOS-latest' - uses: gradle/gradle-build-action@v2.1.5 + uses: gradle/gradle-build-action@v2.4.2 with: arguments: | - releaseMacosX64 - releaseIosArm64 - releaseIosX64 - -Ppublishing.enabled=true - -Ppublishing.sonatype=false + publishMacosX64PublicationToSpaceRepository + publishMacosArm64PublicationToSpaceRepository + publishIosX64PublicationToSpaceRepository + publishIosArm64PublicationToSpaceRepository + publishIosSimulatorArm64PublicationToSpaceRepository + -Ppublishing.targets=all -Ppublishing.space.user=${{ secrets.SPACE_APP_ID }} -Ppublishing.space.token=${{ secrets.SPACE_APP_SECRET }} diff --git a/.gitignore b/.gitignore index 5ddd846a8..96a556ae1 100644 --- a/.gitignore +++ b/.gitignore @@ -3,9 +3,9 @@ build/ out/ .idea/ - - .vscode/ +.fleet/ + # Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored) !gradle-wrapper.jar @@ -19,4 +19,5 @@ out/ !/.idea/copyright/ !/.idea/scopes/ -/kotlin-js-store/yarn.lock +/gradle/yarn.lock + diff --git a/.idea/copyright/kmath.xml b/.idea/copyright/kmath.xml index 17e44e4d0..840e0c87c 100644 --- a/.idea/copyright/kmath.xml +++ b/.idea/copyright/kmath.xml @@ -1,6 +1,7 @@ - - - + + + \ No newline at end of file diff --git a/.idea/copyright/profiles_settings.xml b/.idea/copyright/profiles_settings.xml index b538bdf41..1c10bd6f5 100644 --- a/.idea/copyright/profiles_settings.xml +++ b/.idea/copyright/profiles_settings.xml @@ -1,5 +1,5 @@ - + diff --git a/.space.kts b/.space.kts index c9500e967..ce52a2f5c 100644 --- a/.space.kts +++ b/.space.kts @@ -1,3 +1,48 @@ +import kotlin.io.path.readText + +val projectName = "kmath" + job("Build") { - gradlew("openjdk:11", "build") + //Perform only jvm tests + gradlew("spc.registry.jetbrains.space/p/sci/containers/kotlin-ci:1.0.3", "test", "jvmTest") +} + +job("Publish") { + startOn { + gitPush { enabled = false } + } + container("spc.registry.jetbrains.space/p/sci/containers/kotlin-ci:1.0.3") { + env["SPACE_USER"] = "{{ project:space_user }}" + env["SPACE_TOKEN"] = "{{ project:space_token }}" + kotlinScript { api -> + + val spaceUser = System.getenv("SPACE_USER") + val spaceToken = System.getenv("SPACE_TOKEN") + + // write the version to the build directory + api.gradlew("version") + + //read the version from build file + val version = java.nio.file.Path.of("build/project-version.txt").readText() + + val revisionSuffix = if (version.endsWith("SNAPSHOT")) { + "-" + api.gitRevision().take(7) + } else { + "" + } + + api.space().projects.automation.deployments.start( + project = api.projectIdentifier(), + targetIdentifier = TargetIdentifier.Key(projectName), + version = version+revisionSuffix, + // automatically update deployment status based on the status of a job + syncWithAutomationJob = true + ) + api.gradlew( + "publishAllPublicationsToSpaceRepository", + "-Ppublishing.space.user=\"$spaceUser\"", + "-Ppublishing.space.token=\"$spaceToken\"", + ) + } + } } \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index 4852f474a..2f011881f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,13 +1,10 @@ # KMath -## [Unreleased] +## Unreleased + ### Added -- Autodiff for generic algebra elements in core! -- Algebra now has an obligatory `bufferFactory` (#477). ### Changed -- Kotlin 1.7 -- `LazyStructure` `deffered` -> `async` to comply with coroutines code style ### Deprecated @@ -17,7 +14,34 @@ ### Security -## [0.3.0] +## 0.3.1 - 2023-04-09 + +### Added +- Wasm support for `memory`, `core`, `complex` and `functions` modules. +- Generic builders for `BufferND` and `MutableBufferND` +- `NamedMatrix` - matrix with symbol-based indexing +- `Expression` with default arguments +- Type-aliases for numbers like `Float64` +- Autodiff for generic algebra elements in core! +- Algebra now has an obligatory `bufferFactory` (#477). + +### Changed +- Geometry uses type-safe angles +- Tensor operations switched to prefix notation +- Row-wise and column-wise ND shapes in the core +- Shape is read-only +- Major refactor of tensors (only minor API changes) +- Kotlin 1.8.20 +- `LazyStructure` `deffered` -> `async` to comply with coroutines code style +- Default `dot` operation in tensor algebra no longer support broadcasting. Instead `matmul` operation is added to `DoubleTensorAlgebra`. +- Multik went MPP + +### Removed +- Trajectory moved to https://github.com/SciProgCentre/maps-kt +- Polynomials moved to https://github.com/SciProgCentre/kmath-polynomial + +## 0.3.0 + ### Added - `ScaleOperations` interface - `Field` extends `ScaleOperations` @@ -42,8 +66,8 @@ - `contentEquals` with tolerance: #364 - Compilation to TeX for MST: #254 - ### Changed +- Annotations moved to `space.kscience.kmath` - Exponential operations merged with hyperbolic functions - Space is replaced by Group. Space is reserved for vector spaces. - VectorSpace is now a vector space @@ -75,11 +99,9 @@ - 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 @@ -90,15 +112,12 @@ - Second generic from DifferentiableExpression - Algebra elements are completely removed. Use algebra contexts instead. - ### Fixed - Ring inherits RingOperations, not GroupOperations - Univariate histogram filling +## 0.2.0 -### Security - -## [0.2.0] ### Added - `fun` annotation for SAM interfaces in library - Explicit `public` visibility for all public APIs @@ -118,7 +137,6 @@ - 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 @@ -143,7 +161,6 @@ - `symbol` method in `Algebra` renamed to `bindSymbol` to avoid ambiguity - Add `out` projection to `Buffer` generic - ### Removed - `kmath-koma` module because it doesn't support Kotlin 1.4. - Support of `legacy` JS backend (we will support only IR) @@ -152,11 +169,11 @@ - `Real` class - StructureND identity and equals - ### Fixed - `symbol` method in `MstExtendedField` (https://github.com/mipt-npm/kmath/pull/140) -## [0.1.4] +## 0.1.4 + ### Added - Functional Expressions API - Mathematical Syntax Tree, its interpreter and API @@ -174,7 +191,6 @@ - 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`. @@ -186,10 +202,9 @@ - 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 \ No newline at end of file +- Multiplication of BigInt by scalar diff --git a/README.md b/README.md index b9d36df50..7c1f759c1 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,8 @@ [![JetBrains Research](https://jb.gg/badges/research.svg)](https://confluence.jetbrains.com/display/ALL/JetBrains+on+GitHub) [![DOI](https://zenodo.org/badge/129486382.svg)](https://zenodo.org/badge/latestdoi/129486382) -![Gradle build](https://github.com/mipt-npm/kmath/workflows/Gradle%20build/badge.svg) +![Gradle build](https://github.com/SciProgCentre/kmath/workflows/Gradle%20build/badge.svg) [![Maven Central](https://img.shields.io/maven-central/v/space.kscience/kmath-core.svg?label=Maven%20Central)](https://search.maven.org/search?q=g:%22space.kscience%22) -[![Space](https://img.shields.io/badge/dynamic/xml?color=orange&label=Space&query=//metadata/versioning/latest&url=https%3A%2F%2Fmaven.pkg.jetbrains.space%2Fmipt-npm%2Fp%2Fsci%2Fmaven%2Fspace%2Fkscience%2Fkmath-core%2Fmaven-metadata.xml)](https://maven.pkg.jetbrains.space/mipt-npm/p/sci/maven/space/kscience/) +[![Space](https://img.shields.io/badge/dynamic/xml?color=orange&label=Space&query=//metadata/versioning/latest&url=https%3A%2F%2Fmaven.pkg.jetbrains.space%2Fmipt-npm%2Fp%2Fsci%2Fmaven%2Fspace%2Fkscience%2Fkmath-core%2Fmaven-metadata.xml)](https://maven.pkg.jetbrains.space/spc/p/sci/maven/space/kscience/) # KMath @@ -11,7 +11,7 @@ analog to Python's NumPy library. Later we found that kotlin is much more flexib architecture designs. In contrast to `numpy` and `scipy` it is modular and has a lightweight core. The `numpy`-like experience could be achieved with [kmath-for-real](/kmath-for-real) extension module. -[Documentation site (**WIP**)](https://mipt-npm.github.io/kmath/) +[Documentation site (**WIP**)](https://SciProgCentre.github.io/kmath/) ## Publications and talks @@ -214,28 +214,6 @@ One can still use generic algebras though. > > **Maturity**: EXPERIMENTAL -### [kmath-polynomial](kmath-polynomial) -> -> -> **Maturity**: PROTOTYPE -> -> **Features:** -> - [polynomial abstraction](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt) : Abstraction for polynomial spaces. -> - [rational function abstraction](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/RationalFunction.kt) : Abstraction for rational functions spaces. -> - ["list" polynomials](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListRationalFunction.kt) : List implementation of univariate polynomials. -> - ["list" rational functions](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListPolynomial.kt) : List implementation of univariate rational functions. -> - ["list" polynomials and rational functions constructors](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listConstructors.kt) : Constructors for list polynomials and rational functions. -> - ["list" polynomials and rational functions utilities](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listUtil.kt) : Utilities for list polynomials and rational functions. -> - ["numbered" polynomials](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedRationalFunction.kt) : Numbered implementation of multivariate polynomials. -> - ["numbered" rational functions](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedPolynomial.kt) : Numbered implementation of multivariate rational functions. -> - ["numbered" polynomials and rational functions constructors](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedConstructors.kt) : Constructors for numbered polynomials and rational functions. -> - ["numbered" polynomials and rational functions utilities](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedUtil.kt) : Utilities for numbered polynomials and rational functions. -> - ["labeled" polynomials](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/LabeledRationalFunction.kt) : Labeled implementation of multivariate polynomials. -> - ["labeled" rational functions](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/LabeledPolynomial.kt) : Labeled implementation of multivariate rational functions. -> - ["labeled" polynomials and rational functions constructors](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledConstructors.kt) : Constructors for labeled polynomials and rational functions. -> - ["labeled" polynomials and rational functions utilities](kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledUtil.kt) : Utilities for labeled polynomials and rational functions. - - ### [kmath-stat](kmath-stat) > > @@ -262,11 +240,6 @@ One can still use generic algebras though. > - [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-trajectory](kmath-trajectory) -> Path and trajectory optimization -> -> **Maturity**: PROTOTYPE - ### [kmath-viktor](kmath-viktor) > > @@ -324,5 +297,4 @@ Gradle `6.0+` is required for multiplatform artifacts. The project requires a lot of additional work. The most important thing we need is a feedback about what features are required the most. Feel free to create feature requests. We are also welcome to code contributions, especially in issues -marked with -[waiting for a hero](https://github.com/mipt-npm/kmath/labels/waiting%20for%20a%20hero) label. \ No newline at end of file +marked with [waiting for a hero](https://github.com/SciProgCentre/kmath/labels/waiting%20for%20a%20hero) label. \ No newline at end of file diff --git a/benchmarks/build.gradle.kts b/benchmarks/build.gradle.kts index 22712816d..24471a9e4 100644 --- a/benchmarks/build.gradle.kts +++ b/benchmarks/build.gradle.kts @@ -1,10 +1,11 @@ @file:Suppress("UNUSED_VARIABLE") +import org.jetbrains.kotlin.gradle.tasks.KotlinJvmCompile import space.kscience.kmath.benchmarks.addBenchmarkProperties plugins { kotlin("multiplatform") - kotlin("plugin.allopen") + alias(spclibs.plugins.kotlin.plugin.allopen) id("org.jetbrains.kotlinx.benchmark") } @@ -15,6 +16,8 @@ repositories { mavenCentral() } +val multikVersion: String by rootProject.extra + kotlin { jvm() @@ -26,6 +29,9 @@ kotlin { all { languageSettings { progressiveMode = true + optIn("kotlin.contracts.ExperimentalContracts") + optIn("kotlin.ExperimentalUnsignedTypes") + optIn("space.kscience.kmath.UnstableKMathAPI") } } @@ -39,7 +45,9 @@ kotlin { implementation(project(":kmath-dimensions")) implementation(project(":kmath-for-real")) implementation(project(":kmath-tensors")) - implementation("org.jetbrains.kotlinx:kotlinx-benchmark-runtime:0.4.2") + implementation(project(":kmath-multik")) + implementation("org.jetbrains.kotlinx:multik-default:$multikVersion") + implementation(spclibs.kotlinx.benchmark.runtime) } } @@ -51,7 +59,6 @@ kotlin { implementation(project(":kmath-kotlingrad")) 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") @@ -138,12 +145,10 @@ benchmark { commonConfiguration() include("ViktorLogBenchmark") } -} -// Fix kotlinx-benchmarks bug -afterEvaluate { - val jvmBenchmarkJar by tasks.getting(org.gradle.jvm.tasks.Jar::class) { - duplicatesStrategy = DuplicatesStrategy.EXCLUDE + configurations.register("integration") { + commonConfiguration() + include("IntegrationBenchmark") } } @@ -151,11 +156,11 @@ kotlin.sourceSets.all { with(languageSettings) { optIn("kotlin.contracts.ExperimentalContracts") optIn("kotlin.ExperimentalUnsignedTypes") - optIn("space.kscience.kmath.misc.UnstableKMathAPI") + optIn("space.kscience.kmath.UnstableKMathAPI") } } -tasks.withType { +tasks.withType { kotlinOptions { jvmTarget = "11" freeCompilerArgs = freeCompilerArgs + "-Xjvm-default=all" + "-Xlambdas=indy" @@ -163,7 +168,7 @@ tasks.withType { } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } addBenchmarkProperties() diff --git a/benchmarks/src/jsMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt b/benchmarks/src/jsMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt index 126a2e648..cb07e489a 100644 --- a/benchmarks/src/jsMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt +++ b/benchmarks/src/jsMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -9,8 +9,8 @@ import kotlinx.benchmark.Benchmark import kotlinx.benchmark.Blackhole import kotlinx.benchmark.Scope import kotlinx.benchmark.State +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.* -import space.kscience.kmath.operations.Algebra import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.bindSymbol import space.kscience.kmath.operations.invoke @@ -94,6 +94,7 @@ class ExpressionsInterpretersBenchmark { } private val mst = node.toExpression(DoubleField) + @OptIn(UnstableKMathAPI::class) private val wasm = node.wasmCompileToExpression(DoubleField) private val estree = node.estreeCompileToExpression(DoubleField) diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ArrayBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ArrayBenchmark.kt index ff933997f..abfc8cbf2 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ArrayBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ArrayBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BigIntBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BigIntBenchmark.kt index 188a48ca7..d07b7b4df 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BigIntBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BigIntBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,7 +10,7 @@ import kotlinx.benchmark.Blackhole import org.openjdk.jmh.annotations.Benchmark import org.openjdk.jmh.annotations.Scope import org.openjdk.jmh.annotations.State -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.BigIntField import space.kscience.kmath.operations.JBigIntegerField import space.kscience.kmath.operations.invoke diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BufferBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BufferBenchmark.kt index 39819d407..c2616303b 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BufferBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/BufferBenchmark.kt @@ -1,39 +1,80 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.complex.Complex +import space.kscience.kmath.complex.ComplexField import space.kscience.kmath.complex.complex +import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer -import space.kscience.kmath.structures.MutableBuffer +import space.kscience.kmath.structures.getDouble +import space.kscience.kmath.structures.permute @State(Scope.Benchmark) internal class BufferBenchmark { + + @Benchmark + fun doubleArrayReadWrite(blackhole: Blackhole) { + val buffer = DoubleArray(size) { it.toDouble() } + var res = 0.0 + (0 until size).forEach { + res += buffer[it] + } + blackhole.consume(res) + } + @Benchmark - fun genericDoubleBufferReadWrite() { + fun doubleBufferReadWrite(blackhole: Blackhole) { val buffer = DoubleBuffer(size) { it.toDouble() } + var res = 0.0 + (0 until size).forEach { + res += buffer[it] + } + blackhole.consume(res) + } + + @Benchmark + fun bufferViewReadWrite(blackhole: Blackhole) { + val buffer = DoubleBuffer(size) { it.toDouble() }.permute(reversedIndices) + var res = 0.0 + (0 until size).forEach { + res += buffer[it] + } + blackhole.consume(res) + } + @Benchmark + fun bufferViewReadWriteSpecialized(blackhole: Blackhole) { + val buffer = DoubleBuffer(size) { it.toDouble() }.permute(reversedIndices) + var res = 0.0 (0 until size).forEach { - buffer[it] + res += buffer.getDouble(it) } + blackhole.consume(res) } @Benchmark - fun complexBufferReadWrite() { - val buffer = MutableBuffer.complex(size / 2) { Complex(it.toDouble(), -it.toDouble()) } + fun complexBufferReadWrite(blackhole: Blackhole) = ComplexField { + val buffer = Buffer.complex(size / 2) { Complex(it.toDouble(), -it.toDouble()) } + var res = zero (0 until size / 2).forEach { - buffer[it] + res += buffer[it] } + + blackhole.consume(res) } private companion object { private const val size = 100 + private val reversedIndices = IntArray(size){it}.apply { reverse() } } } 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 7ceecb5ab..7cbe83113 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/DotBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,7 +13,6 @@ import space.kscience.kmath.commons.linear.CMLinearSpace import space.kscience.kmath.ejml.EjmlLinearSpaceDDRM 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.tensorflow.produceWithTF @@ -78,7 +77,7 @@ internal class DotBenchmark { } @Benchmark - fun multikDot(blackhole: Blackhole) = with(DoubleField.multikAlgebra) { + fun multikDot(blackhole: Blackhole) = with(multikAlgebra) { blackhole.consume(matrix1 dot matrix2) } diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt index db3524e67..4df5f372f 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ExpressionsInterpretersBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/IntegrationBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/IntegrationBenchmark.kt new file mode 100644 index 000000000..6cc649fe9 --- /dev/null +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/IntegrationBenchmark.kt @@ -0,0 +1,40 @@ +/* + * Copyright 2018-2023 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 org.openjdk.jmh.annotations.Benchmark +import org.openjdk.jmh.annotations.Scope +import org.openjdk.jmh.annotations.State +import org.openjdk.jmh.infra.Blackhole +import space.kscience.kmath.complex.Complex +import space.kscience.kmath.complex.algebra +import space.kscience.kmath.integration.gaussIntegrator +import space.kscience.kmath.integration.integrate +import space.kscience.kmath.integration.value +import space.kscience.kmath.operations.algebra + + +@State(Scope.Benchmark) +internal class IntegrationBenchmark { + + @Benchmark + fun doubleIntegration(blackhole: Blackhole) { + val res = Double.algebra.gaussIntegrator.integrate(0.0..1.0, intervals = 1000) { x: Double -> + //sin(1 / x) + 1/x + }.value + blackhole.consume(res) + } + + @Benchmark + fun complexIntegration(blackhole: Blackhole) = with(Complex.algebra) { + val res = gaussIntegrator.integrate(0.0..1.0, intervals = 1000) { x: Double -> +// sin(1 / x) + i * cos(1 / x) + 1/x - i/x + }.value + blackhole.consume(res) + } +} \ No newline at end of file diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/JafamaBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/JafamaBenchmark.kt index 5d4eee7c0..041f7e92a 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/JafamaBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/JafamaBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/MatrixInverseBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/MatrixInverseBenchmark.kt index 4ff687aac..f7aac8199 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/MatrixInverseBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/MatrixInverseBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/NDFieldBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/NDFieldBenchmark.kt index 89673acd4..fb8d845e8 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/NDFieldBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/NDFieldBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,11 +13,8 @@ import org.jetbrains.kotlinx.multik.api.Multik import org.jetbrains.kotlinx.multik.api.ones import org.jetbrains.kotlinx.multik.ndarray.data.DN import org.jetbrains.kotlinx.multik.ndarray.data.DataType -import space.kscience.kmath.multik.multikAlgebra -import space.kscience.kmath.nd.BufferedFieldOpsND -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.nd.ndAlgebra -import space.kscience.kmath.nd.one +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.nd.* import space.kscience.kmath.nd4j.nd4j import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.tensors.core.DoubleTensor @@ -43,7 +40,7 @@ internal class NDFieldBenchmark { } @Benchmark - fun multikAdd(blackhole: Blackhole) = with(multikField) { + fun multikAdd(blackhole: Blackhole) = with(multikAlgebra) { var res: StructureND = one(shape) repeat(n) { res += 1.0 } blackhole.consume(res) @@ -70,9 +67,10 @@ internal class NDFieldBenchmark { blackhole.consume(res) } + @OptIn(UnsafeKMathAPI::class) @Benchmark - fun multikInPlaceAdd(blackhole: Blackhole) = with(DoubleField.multikAlgebra) { - val res = Multik.ones(shape, DataType.DoubleDataType).wrap() + fun multikInPlaceAdd(blackhole: Blackhole) = with(multikAlgebra) { + val res = Multik.ones(shape.asArray(), DataType.DoubleDataType).wrap() repeat(n) { res += 1.0 } blackhole.consume(res) } @@ -87,11 +85,10 @@ internal class NDFieldBenchmark { private companion object { private const val dim = 1000 private const val n = 100 - private val shape = intArrayOf(dim, dim) + private val shape = ShapeND(dim, dim) private val specializedField = DoubleField.ndAlgebra private val genericField = BufferedFieldOpsND(DoubleField) private val nd4jField = DoubleField.nd4j - private val multikField = DoubleField.multikAlgebra private val viktorField = DoubleField.viktorAlgebra } } diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt index 38e064e53..c4382374a 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/TensorAlgebraBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,6 +13,8 @@ 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.symEigJacobi +import space.kscience.kmath.tensors.core.symEigSvd import space.kscience.kmath.tensors.core.tensorAlgebra import kotlin.random.Random @@ -27,11 +29,11 @@ internal class TensorAlgebraBenchmark { @Benchmark fun tensorSymEigSvd(blackhole: Blackhole) = with(Double.tensorAlgebra) { - blackhole.consume(matrix.symEigSvd(1e-10)) + blackhole.consume(symEigSvd(matrix, 1e-10)) } @Benchmark fun tensorSymEigJacobi(blackhole: Blackhole) = with(Double.tensorAlgebra) { - blackhole.consume(matrix.symEigJacobi(50, 1e-10)) + blackhole.consume(symEigJacobi(matrix, 50, 1e-10)) } } \ No newline at end of file diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorBenchmark.kt index 0e92a703e..90f3cb765 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,7 +10,7 @@ import kotlinx.benchmark.Blackhole import kotlinx.benchmark.Scope import kotlinx.benchmark.State import org.jetbrains.bio.viktor.F64Array -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.ndAlgebra import space.kscience.kmath.nd.one @@ -49,7 +49,7 @@ internal class ViktorBenchmark { private companion object { private const val dim = 1000 private const val n = 100 - private val shape = Shape(dim, dim) + private val shape = ShapeND(dim, dim) // automatically build context most suited for given type. private val doubleField = DoubleField.ndAlgebra diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorLogBenchmark.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorLogBenchmark.kt index 7bb0b876e..4ec4605ed 100644 --- a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorLogBenchmark.kt +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/ViktorLogBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,7 +10,7 @@ import kotlinx.benchmark.Blackhole import kotlinx.benchmark.Scope import kotlinx.benchmark.State import org.jetbrains.bio.viktor.F64Array -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.ndAlgebra import space.kscience.kmath.nd.one import space.kscience.kmath.operations.DoubleField @@ -49,7 +49,7 @@ internal class ViktorLogBenchmark { private companion object { private const val dim = 1000 private const val n = 100 - private val shape = Shape(dim, dim) + private val shape = ShapeND(dim, dim) // automatically build context most suited for given type. private val doubleField = DoubleField.ndAlgebra diff --git a/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/globals.kt b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/globals.kt new file mode 100644 index 000000000..f6d278d83 --- /dev/null +++ b/benchmarks/src/jvmMain/kotlin/space/kscience/kmath/benchmarks/globals.kt @@ -0,0 +1,11 @@ +/* + * Copyright 2018-2022 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 org.jetbrains.kotlinx.multik.default.DefaultEngine +import space.kscience.kmath.multik.MultikDoubleAlgebra + +val multikAlgebra = MultikDoubleAlgebra(DefaultEngine()) \ No newline at end of file diff --git a/build.gradle.kts b/build.gradle.kts index d8c591799..aed79909c 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -1,6 +1,10 @@ +import space.kscience.gradle.isInDevelopment +import space.kscience.gradle.useApache2Licence +import space.kscience.gradle.useSPCTeam + plugins { - id("ru.mipt.npm.gradle.project") - id("org.jetbrains.kotlinx.kover") version "0.5.0" + id("space.kscience.gradle.project") + id("org.jetbrains.kotlinx.kover") version "0.6.0" } allprojects { @@ -11,7 +15,7 @@ allprojects { } group = "space.kscience" - version = "0.3.1-dev-1" + version = "0.3.1" } subprojects { @@ -31,7 +35,7 @@ subprojects { localDirectory.set(kotlinDir) remoteUrl.set( - java.net.URL("https://github.com/mipt-npm/kmath/tree/master/${this@subprojects.name}/$kotlinDirPath") + java.net.URL("https://github.com/SciProgCentre/kmath/tree/master/${this@subprojects.name}/$kotlinDirPath") ) } @@ -51,26 +55,26 @@ 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") ksciencePublish { - github("kmath", addToRelease = false) - space() - sonatype() + pom("https://github.com/SciProgCentre/kmath") { + useApache2Licence() + useSPCTeam() + } + github("kmath", "SciProgCentre") + space( + if (isInDevelopment) { + "https://maven.pkg.jetbrains.space/spc/p/sci/dev" + } else { + "https://maven.pkg.jetbrains.space/spc/p/sci/maven" + } + ) + sonatype("https://oss.sonatype.org") } -apiValidation.nonPublicMarkers.add("space.kscience.kmath.misc.UnstableKMathAPI") +apiValidation.nonPublicMarkers.add("space.kscience.kmath.UnstableKMathAPI") + +val multikVersion by extra("0.2.0") diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts index 20611e92d..734f60091 100644 --- a/buildSrc/build.gradle.kts +++ b/buildSrc/build.gradle.kts @@ -1,12 +1,8 @@ plugins { - kotlin("jvm") version "1.7.0" `kotlin-dsl` `version-catalog` - alias(npmlibs.plugins.kotlin.plugin.serialization) } -java.targetCompatibility = JavaVersion.VERSION_11 - repositories { mavenLocal() maven("https://repo.kotlin.link") @@ -14,20 +10,25 @@ repositories { gradlePluginPortal() } -val toolsVersion = npmlibs.versions.tools.get() -val kotlinVersion = npmlibs.versions.kotlin.asProvider().get() -val benchmarksVersion = npmlibs.versions.kotlinx.benchmark.get() +val toolsVersion = spclibs.versions.tools.get() +val kotlinVersion = spclibs.versions.kotlin.asProvider().get() +val benchmarksVersion = spclibs.versions.kotlinx.benchmark.get() dependencies { - api("ru.mipt.npm:gradle-tools:$toolsVersion") - api(npmlibs.atomicfu.gradle) + api("space.kscience:gradle-tools:$toolsVersion") //plugins form benchmarks - api("org.jetbrains.kotlinx:kotlinx-benchmark-plugin:$benchmarksVersion") - api("org.jetbrains.kotlin:kotlin-allopen:$kotlinVersion") + api("org.jetbrains.kotlinx:kotlinx-benchmark-plugin:0.4.7") + //api("org.jetbrains.kotlin:kotlin-allopen:$kotlinVersion") //to be used inside build-script only - implementation(npmlibs.kotlinx.serialization.json) + //implementation(spclibs.kotlinx.serialization.json) + implementation("com.fasterxml.jackson.module:jackson-module-kotlin:2.14.+") } -kotlin.sourceSets.all { - languageSettings.optIn("kotlin.OptIn") +kotlin{ + jvmToolchain{ + languageVersion.set(JavaLanguageVersion.of(11)) + } + sourceSets.all { + languageSettings.optIn("kotlin.OptIn") + } } diff --git a/buildSrc/settings.gradle.kts b/buildSrc/settings.gradle.kts index bce265510..e6b69b0b3 100644 --- a/buildSrc/settings.gradle.kts +++ b/buildSrc/settings.gradle.kts @@ -2,6 +2,7 @@ * 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. */ +rootProject.name = "kmath" enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS") @@ -26,8 +27,8 @@ dependencyResolutionManagement { } versionCatalogs { - create("npmlibs") { - from("ru.mipt.npm:version-catalog:$toolsVersion") + create("spclibs") { + from("space.kscience:version-catalog:$toolsVersion") } } } diff --git a/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/JmhReport.kt b/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/JmhReport.kt index eaa0f59d8..3a4fcdc79 100644 --- a/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/JmhReport.kt +++ b/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/JmhReport.kt @@ -1,13 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.serialization.Serializable - -@Serializable data class JmhReport( val jmhVersion: String, val benchmark: String, @@ -37,7 +34,6 @@ data class JmhReport( val scoreUnit: String } - @Serializable data class PrimaryMetric( override val score: Double, override val scoreError: Double, @@ -48,7 +44,6 @@ data class JmhReport( val rawData: List>? = null, ) : Metric - @Serializable data class SecondaryMetric( override val score: Double, override val scoreError: Double, diff --git a/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/addBenchmarkProperties.kt b/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/addBenchmarkProperties.kt index dc9327348..a3a475885 100644 --- a/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/addBenchmarkProperties.kt +++ b/buildSrc/src/main/kotlin/space/kscience/kmath/benchmarks/addBenchmarkProperties.kt @@ -1,21 +1,22 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 com.fasterxml.jackson.module.kotlin.jacksonObjectMapper +import com.fasterxml.jackson.module.kotlin.readValue import kotlinx.benchmark.gradle.BenchmarksExtension -import kotlinx.serialization.decodeFromString -import kotlinx.serialization.json.Json import org.gradle.api.Project -import ru.mipt.npm.gradle.KScienceReadmeExtension +import space.kscience.gradle.KScienceReadmeExtension import java.time.LocalDateTime import java.time.ZoneId import java.time.format.DateTimeFormatter import java.time.format.DateTimeFormatterBuilder import java.time.format.SignStyle import java.time.temporal.ChronoField.* +import java.util.* private val ISO_DATE_TIME: DateTimeFormatter = DateTimeFormatterBuilder().run { parseCaseInsensitive() @@ -45,12 +46,14 @@ private val ISO_DATE_TIME: DateTimeFormatter = DateTimeFormatterBuilder().run { private fun noun(number: Number, singular: String, plural: String) = if (number.toLong() == 1L) singular else plural +private val jsonMapper = jacksonObjectMapper() + fun Project.addBenchmarkProperties() { val benchmarksProject = this rootProject.subprojects.forEach { p -> p.extensions.findByType(KScienceReadmeExtension::class.java)?.run { benchmarksProject.extensions.findByType(BenchmarksExtension::class.java)?.configurations?.forEach { cfg -> - property("benchmark${cfg.name.capitalize()}") { + property("benchmark${cfg.name.replaceFirstChar { if (it.isLowerCase()) it.titlecase(Locale.getDefault()) else it.toString() }}") { val launches = benchmarksProject.buildDir.resolve("reports/benchmarks/${cfg.name}") val resDirectory = launches.listFiles()?.maxByOrNull { @@ -60,8 +63,7 @@ fun Project.addBenchmarkProperties() { if (resDirectory == null || !(resDirectory.resolve("jvm.json")).exists()) { "> **Can't find appropriate benchmark data. Try generating readme files after running benchmarks**." } else { - val reports = - Json.decodeFromString>(resDirectory.resolve("jvm.json").readText()) + val reports: List = jsonMapper.readValue>(resDirectory.resolve("jvm.json")) buildString { appendLine("
") 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 7c23d8ea0..d973ebae4 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -385,7 +385,7 @@ 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.UnstableKMathAPI import space.kscience.kmath.nd.StructureFeature import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.FloatField diff --git a/docs/images/KM.svg b/docs/images/KM.svg index 6f80e4d08..55a4339b1 100644 --- a/docs/images/KM.svg +++ b/docs/images/KM.svg @@ -1,6 +1,6 @@ diff --git a/docs/images/KM_mono.svg b/docs/images/KM_mono.svg index 8f8e470b2..f1194f887 100644 --- a/docs/images/KM_mono.svg +++ b/docs/images/KM_mono.svg @@ -1,6 +1,6 @@ diff --git a/docs/images/KMath.svg b/docs/images/KMath.svg index f751d8eb9..509a184bc 100644 --- a/docs/images/KMath.svg +++ b/docs/images/KMath.svg @@ -1,6 +1,6 @@ diff --git a/docs/images/KMath_mono.svg b/docs/images/KMath_mono.svg index 8ca6c5e84..e781979e2 100644 --- a/docs/images/KMath_mono.svg +++ b/docs/images/KMath_mono.svg @@ -1,6 +1,6 @@ diff --git a/docs/templates/ARTIFACT-TEMPLATE.md b/docs/templates/ARTIFACT-TEMPLATE.md index 1bac2a8ff..a3e47e693 100644 --- a/docs/templates/ARTIFACT-TEMPLATE.md +++ b/docs/templates/ARTIFACT-TEMPLATE.md @@ -3,10 +3,12 @@ The Maven coordinates of this project are `${group}:${name}:${version}`. **Gradle:** -```gradle +```groovy repositories { maven { url 'https://repo.kotlin.link' } mavenCentral() + // development and snapshot versions + maven { url 'https://maven.pkg.jetbrains.space/spc/p/sci/dev' } } dependencies { @@ -18,6 +20,8 @@ dependencies { repositories { maven("https://repo.kotlin.link") mavenCentral() + // development and snapshot versions + maven("https://maven.pkg.jetbrains.space/spc/p/sci/dev") } dependencies { diff --git a/docs/templates/README-TEMPLATE.md b/docs/templates/README-TEMPLATE.md index 1633f3ff1..d7d5a806d 100644 --- a/docs/templates/README-TEMPLATE.md +++ b/docs/templates/README-TEMPLATE.md @@ -1,6 +1,6 @@ [![JetBrains Research](https://jb.gg/badges/research.svg)](https://confluence.jetbrains.com/display/ALL/JetBrains+on+GitHub) [![DOI](https://zenodo.org/badge/129486382.svg)](https://zenodo.org/badge/latestdoi/129486382) -![Gradle build](https://github.com/mipt-npm/kmath/workflows/Gradle%20build/badge.svg) +![Gradle build](https://github.com/SciProgCentre/kmath/workflows/Gradle%20build/badge.svg) [![Maven Central](https://img.shields.io/maven-central/v/space.kscience/kmath-core.svg?label=Maven%20Central)](https://search.maven.org/search?q=g:%22space.kscience%22) [![Space](https://img.shields.io/badge/dynamic/xml?color=orange&label=Space&query=//metadata/versioning/latest&url=https%3A%2F%2Fmaven.pkg.jetbrains.space%2Fmipt-npm%2Fp%2Fsci%2Fmaven%2Fspace%2Fkscience%2Fkmath-core%2Fmaven-metadata.xml)](https://maven.pkg.jetbrains.space/mipt-npm/p/sci/maven/space/kscience/) @@ -11,7 +11,7 @@ analog to Python's NumPy library. Later we found that kotlin is much more flexib architecture designs. In contrast to `numpy` and `scipy` it is modular and has a lightweight core. The `numpy`-like experience could be achieved with [kmath-for-real](/kmath-for-real) extension module. -[Documentation site (**WIP**)](https://mipt-npm.github.io/kmath/) +[Documentation site (**WIP**)](https://SciProgCentre.github.io/kmath/) ## Publications and talks diff --git a/examples/build.gradle.kts b/examples/build.gradle.kts index aa5c1f47a..7f2abc852 100644 --- a/examples/build.gradle.kts +++ b/examples/build.gradle.kts @@ -1,3 +1,5 @@ +import org.jetbrains.kotlin.gradle.tasks.KotlinJvmCompile + plugins { kotlin("jvm") } @@ -8,6 +10,8 @@ repositories { maven("https://maven.pkg.jetbrains.space/kotlin/p/kotlin/kotlin-js-wrappers") } +val multikVersion: String by rootProject.extra + dependencies { implementation(project(":kmath-ast")) implementation(project(":kmath-kotlingrad")) @@ -16,7 +20,6 @@ dependencies { implementation(project(":kmath-commons")) implementation(project(":kmath-complex")) implementation(project(":kmath-functions")) - implementation(project(":kmath-polynomial")) implementation(project(":kmath-optimization")) implementation(project(":kmath-stat")) implementation(project(":kmath-viktor")) @@ -30,7 +33,10 @@ dependencies { implementation(project(":kmath-jafama")) //multik implementation(project(":kmath-multik")) + implementation("org.jetbrains.kotlinx:multik-default:$multikVersion") + //datetime + implementation("org.jetbrains.kotlinx:kotlinx-datetime:0.4.0") implementation("org.nd4j:nd4j-native:1.0.0-beta7") @@ -44,29 +50,28 @@ dependencies { // } else implementation("org.nd4j:nd4j-native-platform:1.0.0-beta7") - // multik implementation - implementation("org.jetbrains.kotlinx:multik-default:0.1.0") - implementation("org.slf4j:slf4j-simple:1.7.32") // plotting implementation("space.kscience:plotlykt-server:0.5.0") } -kotlin.sourceSets.all { - with(languageSettings) { - optIn("kotlin.contracts.ExperimentalContracts") - optIn("kotlin.ExperimentalUnsignedTypes") - optIn("space.kscience.kmath.misc.UnstableKMathAPI") +kotlin { + jvmToolchain(11) + sourceSets.all { + languageSettings { + optIn("kotlin.contracts.ExperimentalContracts") + optIn("kotlin.ExperimentalUnsignedTypes") + optIn("space.kscience.kmath.UnstableKMathAPI") + } } } -tasks.withType { +tasks.withType { kotlinOptions { - jvmTarget = "11" freeCompilerArgs = freeCompilerArgs + "-Xjvm-default=all" + "-Xopt-in=kotlin.RequiresOptIn" + "-Xlambdas=indy" } } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } diff --git a/examples/notebooks/Naive classifier.ipynb b/examples/notebooks/Naive classifier.ipynb new file mode 100644 index 000000000..937f5b6c6 --- /dev/null +++ b/examples/notebooks/Naive classifier.ipynb @@ -0,0 +1,418 @@ +{ + "cells": [ + { + "cell_type": "code", + "source": [ + "%use kmath(0.3.1-dev-5)\n", + "%use plotly(0.5.0)\n", + "@file:DependsOn(\"space.kscience:kmath-commons:0.3.1-dev-5\")" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "lQbSB87rNAn9lV6poArVWW", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "//Uncomment to work in Jupyter classic or DataLore\n", + "//Plotly.jupyter.notebook()" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "0UP158hfccGgjQtHz0wAi6", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "# The model\n", + "\n", + "Defining the input data format, the statistic abstraction and the statistic implementation based on a weighted sum of elements." + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "class XYValues(val xValues: DoubleArray, val yValues: DoubleArray) {\n", + " init {\n", + " require(xValues.size == yValues.size)\n", + " }\n", + "}\n", + "\n", + "fun interface XYStatistic {\n", + " operator fun invoke(values: XYValues): Double\n", + "}\n", + "\n", + "class ConvolutionalXYStatistic(val weights: DoubleArray) : XYStatistic {\n", + " override fun invoke(values: XYValues): Double {\n", + " require(weights.size == values.yValues.size)\n", + " val norm = values.yValues.sum()\n", + " return values.yValues.zip(weights) { value, weight -> value * weight }.sum()/norm\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "Zhgz1Ui91PWz0meJiQpHol", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "# Generator\n", + "Generate sample data for parabolas and hyperbolas" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "execution_count": null, + "outputs": [], + "source": [ + "fun generateParabolas(xValues: DoubleArray, a: Double, b: Double, c: Double): XYValues {\n", + " val yValues = xValues.map { x -> a * x * x + b * x + c }.toDoubleArray()\n", + " return XYValues(xValues, yValues)\n", + "}\n", + "\n", + "fun generateHyperbols(xValues: DoubleArray, gamma: Double, x0: Double, y0: Double): XYValues {\n", + " val yValues = xValues.map { x -> y0 + gamma / (x - x0) }.toDoubleArray()\n", + " return XYValues(xValues, yValues)\n", + "}" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "val xValues = (1.0..10.0).step(1.0).toDoubleArray()\n", + "\n", + "val xy = generateHyperbols(xValues, 1.0, 0.0, 0.0)\n", + "\n", + "Plotly.plot {\n", + " scatter {\n", + " this.x.doubles = xValues\n", + " this.y.doubles = xy.yValues\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "ZE2atNvFzQsCvpAF8KK4ch", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "Create a default statistic with uniform weights" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "val statistic = ConvolutionalXYStatistic(DoubleArray(xValues.size){1.0})\n", + "statistic(xy)" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "EA5HaydTddRKYrtAUwd29h", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "import kotlin.random.Random\n", + "\n", + "val random = Random(1288)\n", + "\n", + "val parabolas = buildList{\n", + " repeat(500){\n", + " add(\n", + " generateParabolas(\n", + " xValues, \n", + " random.nextDouble(), \n", + " random.nextDouble(), \n", + " random.nextDouble()\n", + " )\n", + " )\n", + " }\n", + "}\n", + "\n", + "val hyperbolas: List = buildList{\n", + " repeat(500){\n", + " add(\n", + " generateHyperbols(\n", + " xValues, \n", + " random.nextDouble()*10, \n", + " random.nextDouble(), \n", + " random.nextDouble()\n", + " )\n", + " )\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "t5t6IYmD7Q1ykeo9uijFfQ", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "Plotly.plot { \n", + " scatter { \n", + " x.doubles = xValues\n", + " y.doubles = parabolas[257].yValues\n", + " }\n", + " scatter { \n", + " x.doubles = xValues\n", + " y.doubles = hyperbolas[252].yValues\n", + " }\n", + " }" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "oXB8lmju7YVYjMRXITKnhO", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "Plotly.plot { \n", + " histogram { \n", + " name = \"parabolae\"\n", + " x.numbers = parabolas.map { statistic(it) }\n", + " }\n", + " histogram { \n", + " name = \"hyperbolae\"\n", + " x.numbers = hyperbolas.map { statistic(it) }\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "8EIIecUZrt2NNrOkhxG5P0", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "val lossFunction: (XYStatistic) -> Double = { statistic ->\n", + " - abs(parabolas.sumOf { statistic(it) } - hyperbolas.sumOf { statistic(it) })\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "h7UmglJW5zXkAfKHK40oIL", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "Using commons-math optimizer to optimize weights" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "import org.apache.commons.math3.optim.*\n", + "import org.apache.commons.math3.optim.nonlinear.scalar.*\n", + "import org.apache.commons.math3.optim.nonlinear.scalar.noderiv.*\n", + "\n", + "val optimizer = SimplexOptimizer(1e-1, Double.MAX_VALUE)\n", + "\n", + "val result = optimizer.optimize(\n", + " ObjectiveFunction { point ->\n", + " lossFunction(ConvolutionalXYStatistic(point))\n", + " },\n", + " NelderMeadSimplex(xValues.size),\n", + " InitialGuess(DoubleArray(xValues.size){ 1.0 }),\n", + " GoalType.MINIMIZE,\n", + " MaxEval(100000)\n", + ")" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "0EG3K4aCUciMlgGQKPvJ57", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "Print resulting weights of optimization" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "result.point" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "LelUlY0ZSlJEO9yC6SLk5B", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "source": [ + "Plotly.plot { \n", + " scatter { \n", + " y.doubles = result.point\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "AuFOq5t9KpOIkGrOLsVXNf", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "markdown", + "source": [ + "# The resulting statistic distribution" + ], + "metadata": { + "collapsed": false + } + }, + { + "cell_type": "code", + "source": [ + "val resultStatistic = ConvolutionalXYStatistic(result.point)\n", + "Plotly.plot { \n", + " histogram { \n", + " name = \"parabolae\"\n", + " x.numbers = parabolas.map { resultStatistic(it) }\n", + " }\n", + " histogram { \n", + " name = \"hyperbolae\"\n", + " x.numbers = hyperbolas.map { resultStatistic(it) }\n", + " }\n", + "}" + ], + "execution_count": null, + "outputs": [], + "metadata": { + "datalore": { + "node_id": "zvmq42DRdM5mZ3SpzviHwI", + "type": "CODE", + "hide_input_from_viewers": false, + "hide_output_from_viewers": false + } + } + }, + { + "cell_type": "code", + "execution_count": null, + "outputs": [], + "source": [], + "metadata": { + "collapsed": false + } + } + ], + "metadata": { + "kernelspec": { + "display_name": "Kotlin", + "language": "kotlin", + "name": "kotlin" + }, + "datalore": { + "version": 1, + "computation_mode": "JUPYTER", + "package_manager": "pip", + "base_environment": "default", + "packages": [] + } + }, + "nbformat": 4, + "nbformat_minor": 4 +} diff --git a/examples/src/main/kotlin/space/kscience/kmath/ast/astRendering.kt b/examples/src/main/kotlin/space/kscience/kmath/ast/astRendering.kt index c4f263f97..e85bab8d8 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/ast/astRendering.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/ast/astRendering.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/ast/expressions.kt b/examples/src/main/kotlin/space/kscience/kmath/ast/expressions.kt index 907f1bbe4..cacb6683e 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/ast/expressions.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/ast/expressions.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/ast/kotlingradSupport.kt b/examples/src/main/kotlin/space/kscience/kmath/ast/kotlingradSupport.kt index dec3bfb81..b443e639d 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/ast/kotlingradSupport.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/ast/kotlingradSupport.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/ast/symjaSupport.kt b/examples/src/main/kotlin/space/kscience/kmath/ast/symjaSupport.kt index 7e09faeff..92ee1781b 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/ast/symjaSupport.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/ast/symjaSupport.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/expressions/autodiff.kt b/examples/src/main/kotlin/space/kscience/kmath/expressions/autodiff.kt new file mode 100644 index 000000000..863d6be7a --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/expressions/autodiff.kt @@ -0,0 +1,91 @@ +/* + * Copyright 2018-2023 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.expressions + +import space.kscience.kmath.UnstableKMathAPI +// Only kmath-core is needed. + +// Let's declare some variables +val x by symbol +val y by symbol +val z by symbol + +@OptIn(UnstableKMathAPI::class) +fun main() { + // Let's define some random expression. + val someExpression = Double.autodiff.differentiate { + // We bind variables `x` and `y` to the builder scope, + val x = bindSymbol(x) + val y = bindSymbol(y) + + // Then we use the bindings to define expression `xy + x + y - 1` + x * y + x + y - 1 + } + + // Then we can evaluate it at any point ((-1, -1) in the case): + println(someExpression(x to -1.0, y to -1.0)) + // >>> -2.0 + + // We can also construct its partial derivatives: + val dxExpression = someExpression.derivative(x) // ∂/∂x. Must be `y+1` + val dyExpression = someExpression.derivative(y) // ∂/∂y. Must be `x+1` + val dxdxExpression = someExpression.derivative(x, x) // ∂^2/∂x^2. Must be `0` + + // We can evaluate them as well + println(dxExpression(x to 57.0, y to 6.0)) + // >>> 7.0 + println(dyExpression(x to -1.0, y to 179.0)) + // >>> 0.0 + println(dxdxExpression(x to 239.0, y to 30.0)) + // >>> 0.0 + + // You can also provide extra arguments that obviously won't affect the result: + println(dxExpression(x to 57.0, y to 6.0, z to 42.0)) + // >>> 7.0 + println(dyExpression(x to -1.0, y to 179.0, z to 0.0)) + // >>> 0.0 + println(dxdxExpression(x to 239.0, y to 30.0, z to 100_000.0)) + // >>> 0.0 + + // But in case you forgot to specify bound symbol's value, exception is thrown: + println( runCatching { someExpression(z to 4.0) } ) + // >>> Failure(java.lang.IllegalStateException: Symbol 'x' is not supported in ...) + + // The reason is that the expression is evaluated lazily, + // and each `bindSymbol` operation actually substitutes the provided symbol with the corresponding value. + + // For example, let there be an expression + val simpleExpression = Double.autodiff.differentiate { + val x = bindSymbol(x) + x pow 2 + } + // When you evaluate it via + simpleExpression(x to 1.0, y to 57.0, z to 179.0) + // lambda above has the context of map `{x: 1.0, y: 57.0, z: 179.0}`. + // When x is bound, you can think of it as substitution `x -> 1.0`. + // Other values are unused which does not make any problem to us. + // But in the case the corresponding value is not provided, + // we cannot bind the variable. Thus, exception is thrown. + + // There is also a function `bindSymbolOrNull` that fixes the problem: + val fixedExpression = Double.autodiff.differentiate { + val x = bindSymbolOrNull(x) ?: const(8.0) + x pow -2 + } + println(fixedExpression()) + // >>> 0.015625 + // It works! + + // The expression provides a bunch of operations: + // 1. Constant bindings (via `const` and `number`). + // 2. Variable bindings (via `bindVariable`, `bindVariableOrNull`). + // 3. Arithmetic operations (via `+`, `-`, `*`, and `-`). + // 4. Exponentiation (via `pow` or `power`). + // 5. `exp` and `ln`. + // 6. Trigonometrical functions (`sin`, `cos`, `tan`, `cot`). + // 7. Inverse trigonometrical functions (`asin`, `acos`, `atan`, `acot`). + // 8. Hyperbolic functions and inverse hyperbolic functions. +} diff --git a/examples/src/main/kotlin/space/kscience/kmath/fit/chiSquared.kt b/examples/src/main/kotlin/space/kscience/kmath/fit/chiSquared.kt index 63e57bd8c..258ed0c84 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/fit/chiSquared.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/fit/chiSquared.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,10 +7,9 @@ package space.kscience.kmath.fit import kotlinx.html.br import kotlinx.html.h3 -import space.kscience.kmath.commons.expressions.DSProcessor import space.kscience.kmath.commons.optimization.CMOptimizer import space.kscience.kmath.distributions.NormalDistribution -import space.kscience.kmath.expressions.chiSquaredExpression +import space.kscience.kmath.expressions.autodiff import space.kscience.kmath.expressions.symbol import space.kscience.kmath.operations.asIterable import space.kscience.kmath.operations.toList @@ -18,10 +17,11 @@ import space.kscience.kmath.optimization.FunctionOptimizationTarget import space.kscience.kmath.optimization.optimizeWith import space.kscience.kmath.optimization.resultPoint import space.kscience.kmath.optimization.resultValue +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.real.DoubleVector import space.kscience.kmath.real.map import space.kscience.kmath.real.step -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.stat.chiSquaredExpression import space.kscience.plotly.* import space.kscience.plotly.models.ScatterMode import space.kscience.plotly.models.TraceValues @@ -67,7 +67,7 @@ suspend fun main() { val yErr = y.map { sqrt(it) }//RealVector.same(x.size, sigma) // compute differentiable chi^2 sum for given model ax^2 + bx + c - val chi2 = DSProcessor.chiSquaredExpression(x, y, yErr) { arg -> + val chi2 = Double.autodiff.chiSquaredExpression(x, y, yErr) { arg -> //bind variables to autodiff context val a = bindSymbol(a) val b = bindSymbol(b) diff --git a/examples/src/main/kotlin/space/kscience/kmath/fit/qowFit.kt b/examples/src/main/kotlin/space/kscience/kmath/fit/qowFit.kt index d52976671..fe7f48b72 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/fit/qowFit.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/fit/qowFit.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,21 +7,18 @@ package space.kscience.kmath.fit import kotlinx.html.br import kotlinx.html.h3 -import space.kscience.kmath.commons.expressions.DSProcessor import space.kscience.kmath.data.XYErrorColumnarData import space.kscience.kmath.distributions.NormalDistribution import space.kscience.kmath.expressions.Symbol +import space.kscience.kmath.expressions.autodiff import space.kscience.kmath.expressions.binding import space.kscience.kmath.expressions.symbol import space.kscience.kmath.operations.asIterable import space.kscience.kmath.operations.toList -import space.kscience.kmath.optimization.QowOptimizer -import space.kscience.kmath.optimization.chiSquaredOrNull -import space.kscience.kmath.optimization.fitWith -import space.kscience.kmath.optimization.resultPoint +import space.kscience.kmath.optimization.* +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.real.map import space.kscience.kmath.real.step -import space.kscience.kmath.stat.RandomGenerator import space.kscience.plotly.* import space.kscience.plotly.models.ScatterMode import kotlin.math.abs @@ -32,6 +29,8 @@ import kotlin.math.sqrt private val a by symbol private val b by symbol private val c by symbol +private val d by symbol +private val e by symbol /** @@ -63,17 +62,23 @@ suspend fun main() { val result = XYErrorColumnarData.of(x, y, yErr).fitWith( QowOptimizer, - DSProcessor, - mapOf(a to 0.9, b to 1.2, c to 2.0) + Double.autodiff, + mapOf(a to 0.9, b to 1.2, c to 2.0, e to 1.0, d to 1.0, e to 0.0), + OptimizationParameters(a, b, c, d) ) { arg -> //bind variables to autodiff context val a by binding val b by binding //Include default value for c if it is not provided as a parameter val c = bindSymbolOrNull(c) ?: one - a * arg.pow(2) + b * arg + c + val d by binding + val e by binding + + a * arg.pow(2) + b * arg + c + d * arg.pow(3) + e / arg } + println("Resulting chi2/dof: ${result.chiSquaredOrNull}/${result.dof}") + //display a page with plot and numerical results val page = Plotly.page { plot { @@ -89,7 +94,7 @@ suspend fun main() { scatter { mode = ScatterMode.lines x(x) - y(x.map { result.model(result.resultPoint + (Symbol.x to it)) }) + y(x.map { result.model(result.startPoint + result.resultPoint + (Symbol.x to it)) }) name = "fit" } } @@ -98,7 +103,7 @@ suspend fun main() { +"Fit result: ${result.resultPoint}" } h3 { - +"Chi2/dof = ${result.chiSquaredOrNull!! / (x.size - 3)}" + +"Chi2/dof = ${result.chiSquaredOrNull!! / result.dof}" } } 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 59eaba5bd..e8534d002 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/integrate.kt @@ -1,10 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.functions +import space.kscience.kmath.complex.Complex +import space.kscience.kmath.complex.ComplexField +import space.kscience.kmath.complex.ComplexField.div +import space.kscience.kmath.complex.ComplexField.minus +import space.kscience.kmath.complex.algebra import space.kscience.kmath.integration.gaussIntegrator import space.kscience.kmath.integration.integrate import space.kscience.kmath.integration.value @@ -20,4 +25,12 @@ fun main() { //the value is nullable because in some cases the integration could not succeed println(result.value) + + + repeat(100000) { + Complex.algebra.gaussIntegrator.integrate(0.0..1.0, intervals = 1000) { x: Double -> +// sin(1 / x) + i * cos(1 / x) + 1 / x - ComplexField.i / x + }.value + } } \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolate.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolate.kt index 8dbc7b7a4..b4ce6ad2d 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolate.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolate.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 a50df0931..7bcd96990 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/interpolateSquare.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/matrixIntegration.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/matrixIntegration.kt index 4f99aeb47..baba2eb28 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/matrixIntegration.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/functions/matrixIntegration.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,23 +12,21 @@ import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.structureND import space.kscience.kmath.nd.withNdAlgebra import space.kscience.kmath.operations.algebra -import space.kscience.kmath.operations.invoke +import kotlin.math.pow -fun main(): Unit = Double.algebra { - withNdAlgebra(2, 2) { +fun main(): Unit = Double.algebra.withNdAlgebra(2, 2) { - //Produce a diagonal StructureND - fun diagonal(v: Double) = structureND { (i, j) -> - if (i == j) v else 0.0 - } + //Produce a diagonal StructureND + fun diagonal(v: Double) = structureND { (i, j) -> + if (i == j) v else 0.0 + } - //Define a function in a nd space - val function: (Double) -> StructureND = { x: Double -> 3 * x.pow(2) + 2 * diagonal(x) + 1 } + //Define a function in a nd space + val function: (Double) -> StructureND = { x: Double -> 3 * x.pow(2) + 2 * diagonal(x) + 1 } - //get the result of the integration - val result = gaussIntegrator.integrate(0.0..10.0, function = function) + //get the result of the integration + val result = gaussIntegrator.integrate(0.0..10.0, function = function) - //the value is nullable because in some cases the integration could not succeed - println(result.value) - } -} \ No newline at end of file + //the value is nullable because in some cases the integration could not succeed + println(result.value) +} diff --git a/examples/src/main/kotlin/space/kscience/kmath/functions/polynomials.kt b/examples/src/main/kotlin/space/kscience/kmath/functions/polynomials.kt deleted file mode 100644 index c65ca589d..000000000 --- a/examples/src/main/kotlin/space/kscience/kmath/functions/polynomials.kt +++ /dev/null @@ -1,399 +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:Suppress("LocalVariableName") - -package space.kscience.kmath.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.expressions.symbol -import space.kscience.kmath.operations.algebra -import space.kscience.kmath.operations.invoke - - -/** - * Shows [ListPolynomial]s' and [ListRationalFunction]s' capabilities. - */ -fun listPolynomialsExample() { - // [ListPolynomial] is a representation of a univariate polynomial as a list of coefficients from the least term to - // the greatest term. For example, - val polynomial1: ListPolynomial = ListPolynomial(listOf(2, -3, 1)) - // represents polynomial 2 + (-3) x + x^2 - - // There are also shortcut fabrics: - val polynomial2: ListPolynomial = ListPolynomial(2, -3, 1) - println(polynomial1 == polynomial2) // true - // and even - val polynomial3: ListPolynomial = 57.asListPolynomial() - val polynomial4: ListPolynomial = ListPolynomial(listOf(57)) - println(polynomial3 == polynomial4) // true - - val polynomial5: ListPolynomial = ListPolynomial(3, -1) - // For every ring there can be provided a polynomial ring: - Int.algebra.listPolynomialSpace { - println(-polynomial5 == ListPolynomial(-3, 1)) // true - println(polynomial1 + polynomial5 == ListPolynomial(5, -4, 1)) // true - println(polynomial1 - polynomial5 == ListPolynomial(-1, -2, 1)) // true - println(polynomial1 * polynomial5 == ListPolynomial(6, -11, 6, -1)) // true - } - // You can even write - val x: ListPolynomial = ListPolynomial(0.0, 1.0) - val polynomial6: ListPolynomial = ListPolynomial(2.0, -3.0, 1.0) - Double.algebra.listPolynomialSpace { - println(2 - 3 * x + x * x == polynomial6) - println(2.0 - 3.0 * x + x * x == polynomial6) - } - - // Also there are some utilities for polynomials: - println(polynomial1.substitute(Int.algebra, 1) == 0) // true, because 2 + (-3) * 1 + 1^2 = 0 - println(polynomial1.substitute(Int.algebra, polynomial5) == polynomial1) // true, because 2 + (-3) * (3-x) + (3-x)^2 = 2 - 3x + x^2 - println(polynomial1.derivative(Int.algebra) == ListPolynomial(-3, 2)) // true, (2 - 3x + x^2)' = -3 + 2x - println(polynomial1.nthDerivative(Int.algebra, 2) == 2.asListPolynomial()) // true, (2 - 3x + x^2)'' = 2 - - // Lastly, there are rational functions and some other utilities: - Double.algebra.listRationalFunctionSpace { - val rationalFunction1: ListRationalFunction = ListRationalFunction(listOf(2.0, -3.0, 1.0), listOf(3.0, -1.0)) - // It's just (2 - 3x + x^2)/(3 - x) - - val rationalFunction2 : ListRationalFunction = ListRationalFunction(listOf(5.0, -4.0, 1.0), listOf(3.0, -1.0)) - // It's just (5 - 4x + x^2)/(3 - x) - - println(rationalFunction1 + 1 == rationalFunction2) - } -} - -/** - * Shows [NumberedPolynomial]s' and [NumberedRationalFunction]s' capabilities. - */ -fun numberedPolynomialsExample() { - // Consider polynomial - // 3 + 5 x_2 - 7 x_1^2 x_3 - // Consider, for example, its term -7 x_1^2 x_3. -7 is a coefficient of the term, whereas (2, 0, 1, 0, 0, ...) is - // description of degrees of variables x_1, x_2, ... in the term. Such description with removed leading zeros - // [2, 0, 1] is called "signature" of the term -7 x_1^2 x_3. - - val polynomial1: NumberedPolynomial - with(Int.algebra) { - // [NumberedPolynomial] is a representation of a multivariate polynomial, that stores terms in a map with terms' - // signatures as the map's keys and terms' coefficients as corresponding values. For example, - polynomial1 = NumberedPolynomial( - mapOf( - listOf() to 3, - listOf(0u, 1u) to 5, - listOf(2u, 0u, 1u) to -7, - ) - ) - // represents polynomial 3 + 5 x_2 - 7 x_1^2 x_3 - - // This `NumberedPolynomial` function needs context of either ring of constant (as `Int.algebra` in this example) - // or space of NumberedPolynomials over it. To understand why it is like this see documentations of functions - // NumberedPolynomial and NumberedPolynomialWithoutCheck - - // There are also shortcut fabrics: - val polynomial2: NumberedPolynomial = NumberedPolynomial( - listOf() to 3, - listOf(0u, 1u) to 5, - listOf(2u, 0u, 1u) to -7, - ) - println(polynomial1 == polynomial2) // true - // and even - val polynomial3: NumberedPolynomial = 57.asNumberedPolynomial() // This one actually does not algebraic context! - val polynomial4: NumberedPolynomial = NumberedPolynomial(listOf() to 57) - println(polynomial3 == polynomial4) // true - - numberedPolynomialSpace { - // Also there is DSL for constructing NumberedPolynomials: - val polynomial5: NumberedPolynomial = NumberedPolynomialDSL1 { - 3 {} - 5 { 1 inPowerOf 1u } - -7 with { 0 pow 2u; 2 pow 1u } - // `pow` and `inPowerOf` are the same - // `with` is omittable - } - println(polynomial1 == polynomial5) // true - - // Unfortunately the DSL does not work good in bare context of constants' ring, so for now it's disabled and - // works only in NumberedPolynomialSpace and NumberedRationalFunctionSpace - } - } - - val polynomial6: NumberedPolynomial = Int.algebra { - NumberedPolynomial( - listOf() to 7, - listOf(0u, 1u) to -5, - listOf(2u, 0u, 1u) to 0, - listOf(0u, 0u, 0u, 4u) to 4, - ) - } - // For every ring there can be provided a polynomial ring: - Int.algebra.numberedPolynomialSpace { - println( - -polynomial6 == NumberedPolynomial( - listOf() to -7, - listOf(0u, 1u) to 5, - listOf(2u, 0u, 1u) to 0, - listOf(0u, 0u, 0u, 4u) to (-4), - ) - ) // true - println( - polynomial1 + polynomial6 == NumberedPolynomial( - listOf() to 10, - listOf(0u, 1u) to 0, - listOf(2u, 0u, 1u) to -7, - listOf(0u, 0u, 0u, 4u) to 4, - ) - ) // true - println( - polynomial1 - polynomial6 == NumberedPolynomial( - listOf() to -4, - listOf(0u, 1u) to 10, - listOf(2u, 0u, 1u) to -7, - listOf(0u, 0u, 0u, 4u) to -4, - ) - ) // true - - polynomial1 * polynomial6 // Multiplication works too - } - - Double.algebra.numberedPolynomialSpace { - // You can even write - val x_1: NumberedPolynomial = NumberedPolynomial(listOf(1u) to 1.0) - val x_2: NumberedPolynomial = NumberedPolynomial(listOf(0u, 1u) to 1.0) - val x_3: NumberedPolynomial = NumberedPolynomial(listOf(0u, 0u, 1u) to 1.0) - val polynomial7: NumberedPolynomial = NumberedPolynomial( - listOf() to 3.0, - listOf(0u, 1u) to 5.0, - listOf(2u, 0u, 1u) to -7.0, - ) - Double.algebra.listPolynomialSpace { - println(3 + 5 * x_2 - 7 * x_1 * x_1 * x_3 == polynomial7) - println(3.0 + 5.0 * x_2 - 7.0 * x_1 * x_1 * x_3 == polynomial7) - } - } - - Int.algebra.numberedPolynomialSpace { - val x_4: NumberedPolynomial = NumberedPolynomial(listOf(0u, 0u, 0u, 4u) to 1) - // Also there are some utilities for polynomials: - println(polynomial1.substitute(mapOf(0 to 1, 1 to -2, 2 to -1)) == 0.asNumberedPolynomial()) // true, - // because it's substitution x_1 -> 1, x_2 -> -2, x_3 -> -1, - // so 3 + 5 x_2 - 7 x_1^2 x_3 = 3 + 5 * (-2) - 7 * 1^2 * (-1) = 3 - 10 + 7 = 0 - println( - polynomial1.substitute(mapOf(1 to x_4)) == NumberedPolynomial( - listOf() to 3, - listOf(0u, 1u) to 5, - listOf(2u, 0u, 1u) to -7, - ) - ) // true, because it's substitution x_2 -> x_4, so result is 3 + 5 x_4 - 7 x_1^2 x_3 - println( - polynomial1.derivativeWithRespectTo(Int.algebra, 1) == - NumberedPolynomial(listOf() to 5) - ) // true, d/dx_2 (3 + 5 x_2 - 7 x_1^2 x_3) = 5 - } - - // Lastly, there are rational functions and some other utilities: - Double.algebra.numberedRationalFunctionSpace { - val rationalFunction1: NumberedRationalFunction = NumberedRationalFunction( - NumberedPolynomial( - listOf() to 2.0, - listOf(1u) to -3.0, - listOf(2u) to 1.0, - ), - NumberedPolynomial( - listOf() to 3.0, - listOf(1u) to -1.0, - ) - ) - // It's just (2 - 3x + x^2)/(3 - x) where x = x_1 - - val rationalFunction2: NumberedRationalFunction = NumberedRationalFunction( - NumberedPolynomial( - listOf() to 5.0, - listOf(1u) to -4.0, - listOf(2u) to 1.0, - ), - NumberedPolynomial( - listOf() to 3.0, - listOf(1u) to -1.0, - ) - ) - // It's just (5 - 4x + x^2)/(3 - x) where x = x_1 - - println(rationalFunction1 + 1 == rationalFunction2) - } -} - -/** - * Shows [LabeledPolynomial]s' and [LabeledRationalFunction]s' capabilities. - */ -fun labeledPolynomialsExample() { - val x by symbol - val y by symbol - val z by symbol - val t by symbol - - // Consider polynomial - // 3 + 5 y - 7 x^2 z - // Consider, for example, its term -7 x^2 z. -7 is a coefficient of the term, whereas matching (x -> 2, z -> 3) is - // description of degrees of variables x_1, x_2, ... in the term. Such description is called "signature" of the - // term -7 x_1^2 x_3. - - val polynomial1: LabeledPolynomial - with(Int.algebra) { - // [LabeledPolynomial] is a representation of a multivariate polynomial, that stores terms in a map with terms' - // signatures as the map's keys and terms' coefficients as corresponding values. For example, - polynomial1 = LabeledPolynomial( - mapOf( - mapOf() to 3, - mapOf(y to 1u) to 5, - mapOf(x to 2u, z to 1u) to -7, - ) - ) - // represents polynomial 3 + 5 y - 7 x^2 z - - // This `LabeledPolynomial` function needs context of either ring of constant (as `Int.algebra` in this example) - // or space of LabeledPolynomials over it. To understand why it is like this see documentations of functions - // LabeledPolynomial and LabeledPolynomialWithoutCheck - - // There are also shortcut fabrics: - val polynomial2: LabeledPolynomial = LabeledPolynomial( - mapOf() to 3, - mapOf(y to 1u) to 5, - mapOf(x to 2u, z to 1u) to -7, - ) - println(polynomial1 == polynomial2) // true - // and even - val polynomial3: LabeledPolynomial = 57.asLabeledPolynomial() // This one actually does not algebraic context! - val polynomial4: LabeledPolynomial = LabeledPolynomial(mapOf() to 57) - println(polynomial3 == polynomial4) // true - - labeledPolynomialSpace { - // Also there is DSL for constructing NumberedPolynomials: - val polynomial5: LabeledPolynomial = LabeledPolynomialDSL1 { - 3 {} - 5 { y inPowerOf 1u } - -7 with { x pow 2u; z pow 1u } - // `pow` and `inPowerOf` are the same - // `with` is omittable - } - println(polynomial1 == polynomial5) // true - - // Unfortunately the DSL does not work good in bare context of constants' ring, so for now it's disabled and - // works only in NumberedPolynomialSpace and NumberedRationalFunctionSpace - } - } - - val polynomial6: LabeledPolynomial = Int.algebra { - LabeledPolynomial( - mapOf() to 7, - mapOf(y to 1u) to -5, - mapOf(x to 2u, z to 1u) to 0, - mapOf(t to 4u) to 4, - ) - } - // For every ring there can be provided a polynomial ring: - Int.algebra.labeledPolynomialSpace { - println( - -polynomial6 == LabeledPolynomial( - mapOf() to -7, - mapOf(y to 1u) to 5, - mapOf(x to 2u, z to 1u) to 0, - mapOf(t to 4u) to -4, - ) - ) // true - println( - polynomial1 + polynomial6 == LabeledPolynomial( - mapOf() to 10, - mapOf(y to 1u) to 0, - mapOf(x to 2u, z to 1u) to -7, - mapOf(t to 4u) to 4, - ) - ) // true - println( - polynomial1 - polynomial6 == LabeledPolynomial( - mapOf() to -4, - mapOf(y to 1u) to 10, - mapOf(x to 2u, z to 1u) to -7, - mapOf(t to 4u) to -4, - ) - ) // true - - polynomial1 * polynomial6 // Multiplication works too - } - - Double.algebra.labeledPolynomialSpace { - // You can even write - val polynomial7: LabeledPolynomial = LabeledPolynomial( - mapOf() to 3.0, - mapOf(y to 1u) to 5.0, - mapOf(x to 2u, z to 1u) to -7.0, - ) - Double.algebra.listPolynomialSpace { - println(3 + 5 * y - 7 * x * x * z == polynomial7) - println(3.0 + 5.0 * y - 7.0 * x * x * z == polynomial7) - } - } - - Int.algebra.labeledPolynomialSpace { - // Also there are some utilities for polynomials: - println(polynomial1.substitute(mapOf(x to 1, y to -2, z to -1)) == 0.asLabeledPolynomial()) // true, - // because it's substitution x -> 1, y -> -2, z -> -1, - // so 3 + 5 y - 7 x^2 z = 3 + 5 * (-2) - 7 * 1^2 * (-1) = 3 - 10 + 7 = 0 - println( - polynomial1.substitute(mapOf(y to t.asPolynomial())) == LabeledPolynomial( - mapOf() to 3, - mapOf(t to 1u) to 5, - mapOf(x to 2u, z to 1u) to -7, - ) - ) // true, because it's substitution y -> t, so result is 3 + 5 t - 7 x^2 z - println( - polynomial1.derivativeWithRespectTo(Int.algebra, y) == LabeledPolynomial(mapOf() to 5) - ) // true, d/dy (3 + 5 y - 7 x^2 z) = 5 - } - - // Lastly, there are rational functions and some other utilities: - Double.algebra.labeledRationalFunctionSpace { - val rationalFunction1: LabeledRationalFunction = LabeledRationalFunction( - LabeledPolynomial( - mapOf() to 2.0, - mapOf(x to 1u) to -3.0, - mapOf(x to 2u) to 1.0, - ), - LabeledPolynomial( - mapOf() to 3.0, - mapOf(x to 1u) to -1.0, - ) - ) - // It's just (2 - 3x + x^2)/(3 - x) - - val rationalFunction2: LabeledRationalFunction = LabeledRationalFunction( - LabeledPolynomial( - mapOf() to 5.0, - mapOf(x to 1u) to -4.0, - mapOf(x to 2u) to 1.0, - ), - LabeledPolynomial( - mapOf() to 3.0, - mapOf(x to 1u) to -1.0, - ) - ) - // It's just (5 - 4x + x^2)/(3 - x) - - println(rationalFunction1 + 1 == rationalFunction2) - } -} - -fun main() { - println("ListPolynomials:") - listPolynomialsExample() - println() - - println("NumberedPolynomials:") - numberedPolynomialsExample() - println() - - println("ListPolynomials:") - labeledPolynomialsExample() - println() -} diff --git a/examples/src/main/kotlin/space/kscience/kmath/jafama/JafamaDemo.kt b/examples/src/main/kotlin/space/kscience/kmath/jafama/JafamaDemo.kt index 9c3d0fdbe..52451e9f3 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/jafama/JafamaDemo.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/jafama/JafamaDemo.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/linear/dotPerformance.kt b/examples/src/main/kotlin/space/kscience/kmath/linear/dotPerformance.kt index a2d7d7c27..79eddc6c3 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/linear/dotPerformance.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/linear/dotPerformance.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,8 +7,10 @@ package space.kscience.kmath.linear import space.kscience.kmath.operations.algebra import kotlin.random.Random -import kotlin.system.measureTimeMillis +import kotlin.time.ExperimentalTime +import kotlin.time.measureTime +@OptIn(ExperimentalTime::class) fun main() { val random = Random(12224) val dim = 1000 @@ -21,7 +23,7 @@ fun main() { if (i <= j) random.nextDouble() else 0.0 } - val time = measureTimeMillis { + val time = measureTime { with(Double.algebra.linearSpace) { repeat(10) { matrix1 dot matrix2 diff --git a/examples/src/main/kotlin/space/kscience/kmath/linear/gradient.kt b/examples/src/main/kotlin/space/kscience/kmath/linear/gradient.kt index a01ea7fe2..52ed8f05f 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/linear/gradient.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/linear/gradient.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/operations/BigIntDemo.kt b/examples/src/main/kotlin/space/kscience/kmath/operations/BigIntDemo.kt index 51f439612..2447d06ed 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/operations/BigIntDemo.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/operations/BigIntDemo.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/operations/complexDemo.kt b/examples/src/main/kotlin/space/kscience/kmath/operations/complexDemo.kt index 285b8d000..77cfca4ae 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/operations/complexDemo.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/operations/complexDemo.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/operations/mixedNDOperations.kt b/examples/src/main/kotlin/space/kscience/kmath/operations/mixedNDOperations.kt index 62c9c8076..4a5d783e1 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/operations/mixedNDOperations.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/operations/mixedNDOperations.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,14 +8,14 @@ package space.kscience.kmath.operations import space.kscience.kmath.commons.linear.CMLinearSpace import space.kscience.kmath.linear.matrix import space.kscience.kmath.nd.DoubleBufferND -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.nd.ndAlgebra import space.kscience.kmath.viktor.ViktorStructureND import space.kscience.kmath.viktor.viktorAlgebra fun main() { - val viktorStructure: ViktorStructureND = DoubleField.viktorAlgebra.structureND(Shape(2, 2)) { (i, j) -> + val viktorStructure: ViktorStructureND = DoubleField.viktorAlgebra.structureND(ShapeND(2, 2)) { (i, j) -> if (i == j) 2.0 else 0.0 } diff --git a/examples/src/main/kotlin/space/kscience/kmath/series/DateTimeSeries.kt b/examples/src/main/kotlin/space/kscience/kmath/series/DateTimeSeries.kt new file mode 100644 index 000000000..ca10fc290 --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/series/DateTimeSeries.kt @@ -0,0 +1,17 @@ +/* + * Copyright 2018-2023 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.series + +import kotlinx.datetime.Instant +import space.kscience.kmath.operations.algebra +import space.kscience.kmath.operations.bufferAlgebra +import kotlin.time.Duration + +fun SeriesAlgebra.Companion.time(zero: Instant, step: Duration) = MonotonicSeriesAlgebra( + bufferAlgebra = Double.algebra.bufferAlgebra, + offsetToLabel = { zero + step * it }, + labelToOffset = { (it - zero) / step } +) \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/series/analyzeDif.kt b/examples/src/main/kotlin/space/kscience/kmath/series/analyzeDif.kt new file mode 100644 index 000000000..0e10f1a9a --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/series/analyzeDif.kt @@ -0,0 +1,56 @@ +package space.kscience.kmath.series + + +import kotlinx.html.h1 +import kotlinx.html.p +import space.kscience.kmath.operations.algebra +import space.kscience.kmath.operations.bufferAlgebra +import space.kscience.kmath.operations.toList +import space.kscience.kmath.stat.KMComparisonResult +import space.kscience.kmath.stat.ksComparisonStatistic +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.slice +import space.kscience.plotly.* +import kotlin.math.PI + +fun main() = with(Double.algebra.bufferAlgebra.seriesAlgebra()) { + + + fun Plot.plotSeries(name: String, buffer: Buffer) { + scatter { + this.name = name + x.numbers = buffer.labels + y.numbers = buffer.toList() + } + } + + + val s1 = series(100) { sin(2 * PI * it / 100) + 1.0 } + + val s2 = s1.slice(20..50).moveTo(40) + + val s3: Buffer = s1.zip(s2) { l, r -> l + r } //s1 + s2 + val s4 = s3.map { ln(it) } + + val kmTest: KMComparisonResult = ksComparisonStatistic(s1, s2) + + Plotly.page { + h1 { +"This is my plot" } + p{ + +"Kolmogorov-smirnov test for s1 and s2: ${kmTest.value}" + } + plot{ + plotSeries("s1", s1) + plotSeries("s2", s2) + plotSeries("s3", s3) + plotSeries("s4", s4) + layout { + xaxis { + range(0.0..100.0) + } + } + } + + }.makeFile() + +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionBenchmark.kt b/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionBenchmark.kt index 8e3cdf86f..031955e15 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionBenchmark.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionBenchmark.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,6 +10,7 @@ import kotlinx.coroutines.async import kotlinx.coroutines.runBlocking import org.apache.commons.rng.sampling.distribution.BoxMullerNormalizedGaussianSampler import org.apache.commons.rng.simple.RandomSource +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.samplers.GaussianSampler import java.time.Duration import java.time.Instant @@ -35,7 +36,7 @@ private suspend fun runKMathChained(): Duration { return Duration.between(startTime, Instant.now()) } -private fun runApacheDirect(): Duration { +private fun runCMDirect(): Duration { val rng = RandomSource.create(RandomSource.MT, 123L) val sampler = CMGaussianSampler.of( @@ -64,7 +65,7 @@ private fun runApacheDirect(): Duration { * Comparing chain sampling performance with direct sampling performance */ fun main(): Unit = runBlocking(Dispatchers.Default) { - val directJob = async { runApacheDirect() } + val directJob = async { runCMDirect() } val chainJob = async { runKMathChained() } println("KMath Chained: ${chainJob.await()}") println("Apache Direct: ${directJob.await()}") diff --git a/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionDemo.kt b/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionDemo.kt index 15654971f..8e6d096ed 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionDemo.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/stat/DistributionDemo.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -9,6 +9,7 @@ import kotlinx.coroutines.runBlocking import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.combineWithState import space.kscience.kmath.distributions.NormalDistribution +import space.kscience.kmath.random.RandomGenerator private data class AveragingChainState(var num: Int = 0, var value: Double = 0.0) diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/ComplexND.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/ComplexND.kt index d55f3df09..86d7c0d89 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/ComplexND.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/ComplexND.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/NDField.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/NDField.kt index d6ff1dceb..ba8f047a8 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/NDField.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/NDField.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -29,7 +29,7 @@ fun main() { Nd4j.zeros(0) val dim = 1000 val n = 1000 - val shape = Shape(dim, dim) + val shape = ShapeND(dim, dim) // specialized nd-field for Double. It works as generic Double field as well. diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/StreamDoubleFieldND.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/StreamDoubleFieldND.kt index 548fb16c1..2ce2c21a6 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/StreamDoubleFieldND.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/StreamDoubleFieldND.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.ExtendedField @@ -16,11 +17,11 @@ import java.util.stream.IntStream * A demonstration implementation of NDField over Real using Java [java.util.stream.DoubleStream] for parallel * execution. */ -class StreamDoubleFieldND(override val shape: IntArray) : FieldND, +class StreamDoubleFieldND(override val shape: ShapeND) : FieldND, NumbersAddOps>, ExtendedField> { - private val strides = DefaultStrides(shape) + private val strides = ColumnStrides(shape) override val elementAlgebra: DoubleField get() = DoubleField override val zero: BufferND by lazy { structureND(shape) { zero } } override val one: BufferND by lazy { structureND(shape) { one } } @@ -30,17 +31,19 @@ class StreamDoubleFieldND(override val shape: IntArray) : FieldND.buffer: DoubleBuffer get() = when { !shape.contentEquals(this@StreamDoubleFieldND.shape) -> throw ShapeMismatchException( this@StreamDoubleFieldND.shape, shape ) - this is BufferND && this.indices == this@StreamDoubleFieldND.strides -> this.buffer as DoubleBuffer + + this is BufferND && indices == this@StreamDoubleFieldND.strides -> this.buffer as DoubleBuffer else -> DoubleBuffer(strides.linearSize) { offset -> get(strides.index(offset)) } } - override fun structureND(shape: Shape, initializer: DoubleField.(IntArray) -> Double): BufferND { + override fun structureND(shape: ShapeND, initializer: DoubleField.(IntArray) -> Double): BufferND { val array = IntStream.range(0, strides.linearSize).parallel().mapToDouble { offset -> val index = strides.index(offset) DoubleField.initializer(index) @@ -49,6 +52,7 @@ class StreamDoubleFieldND(override val shape: IntArray) : FieldND.map( transform: DoubleField.(Double) -> Double, ): BufferND { @@ -56,6 +60,7 @@ class StreamDoubleFieldND(override val shape: IntArray) : FieldND.mapIndexed( transform: DoubleField.(index: IntArray, Double) -> Double, ): BufferND { @@ -69,6 +74,7 @@ class StreamDoubleFieldND(override val shape: IntArray) : FieldND, right: StructureND, @@ -105,4 +111,4 @@ class StreamDoubleFieldND(override val shape: IntArray) : FieldND): BufferND = arg.map { atanh(it) } } -fun DoubleField.ndStreaming(vararg shape: Int): StreamDoubleFieldND = StreamDoubleFieldND(shape) +fun DoubleField.ndStreaming(vararg shape: Int): StreamDoubleFieldND = StreamDoubleFieldND(ShapeND(shape)) diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/StructureReadBenchmark.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/StructureReadBenchmark.kt index de36c664d..e6ff0ee28 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/StructureReadBenchmark.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/StructureReadBenchmark.kt @@ -1,20 +1,23 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.nd.BufferND -import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.nd.ColumnStrides +import space.kscience.kmath.nd.ShapeND import kotlin.system.measureTimeMillis @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE") +@OptIn(PerformancePitfall::class) fun main() { val n = 6000 val array = DoubleArray(n * n) { 1.0 } val buffer = DoubleBuffer(array) - val strides = DefaultStrides(intArrayOf(n, n)) + val strides = ColumnStrides(ShapeND(n, n)) val structure = BufferND(strides, buffer) measureTimeMillis { diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/StructureWriteBenchmark.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/StructureWriteBenchmark.kt index dea7095a8..14c058417 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/StructureWriteBenchmark.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/StructureWriteBenchmark.kt @@ -1,20 +1,27 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.nd.BufferND +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.nd.mapToBuffer +import space.kscience.kmath.operations.mapToBuffer import kotlin.system.measureTimeMillis +private inline fun BufferND.mapToBufferND( + bufferFactory: BufferFactory = BufferFactory.auto(), + crossinline block: (T) -> R, +): BufferND = BufferND(indices, buffer.mapToBuffer(bufferFactory, block)) + @Suppress("UNUSED_VARIABLE") fun main() { val n = 6000 - val structure = StructureND.buffered(intArrayOf(n, n), Buffer.Companion::auto) { 1.0 } - structure.mapToBuffer { it + 1 } // warm-up - val time1 = measureTimeMillis { val res = structure.mapToBuffer { it + 1 } } + val structure = StructureND.buffered(ShapeND(n, n), Buffer.Companion::auto) { 1.0 } + structure.mapToBufferND { it + 1 } // warm-up + val time1 = measureTimeMillis { val res = structure.mapToBufferND { it + 1 } } println("Structure mapping finished in $time1 millis") val array = DoubleArray(n * n) { 1.0 } diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/buffers.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/buffers.kt index 889ea99bd..2ac0dc6a4 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/buffers.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/buffers.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/structures/typeSafeDimensions.kt b/examples/src/main/kotlin/space/kscience/kmath/structures/typeSafeDimensions.kt index c28b566b9..1ba0e3503 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/structures/typeSafeDimensions.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/structures/typeSafeDimensions.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticDifficultTest.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticDifficultTest.kt new file mode 100644 index 000000000..e6f575262 --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticDifficultTest.kt @@ -0,0 +1,90 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt.StaticLm + +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.component1 +import space.kscience.kmath.tensors.LevenbergMarquardt.funcDifficultForLm +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.div +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.LMInput +import space.kscience.kmath.tensors.core.levenbergMarquardt +import kotlin.math.roundToInt + +fun main() { + val NData = 200 + var t_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + t_example[i, 0] = t_example[i, 0] * (i + 1) - 104 + } + + val Nparams = 15 + var p_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_example[i, 0] = p_example[i, 0] + i - 25 + } + + val exampleNumber = 1 + + var y_hat = funcDifficultForLm(t_example, p_example, exampleNumber) + + var p_init = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_init[i, 0] = (p_example[i, 0] + 0.9) + } + + var t = t_example + val y_dat = y_hat + val weight = 1.0 / Nparams * 1.0 - 0.085 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var p_min = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / -50.0) + val p_max = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / 50.0) + val opts = doubleArrayOf(3.0, 10000.0, 1e-6, 1e-6, 1e-6, 1e-6, 1e-2, 11.0, 9.0, 1.0) +// val opts = doubleArrayOf(3.0, 10000.0, 1e-6, 1e-6, 1e-6, 1e-6, 1e-3, 11.0, 9.0, 1.0) + + val inputData = LMInput(::funcDifficultForLm, + p_init.as2D(), + t, + y_dat, + weight, + dp, + p_min.as2D(), + p_max.as2D(), + opts[1].toInt(), + doubleArrayOf(opts[2], opts[3], opts[4], opts[5]), + doubleArrayOf(opts[6], opts[7], opts[8]), + opts[9].toInt(), + 10, + 1) + + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + + println("Parameters:") + for (i in 0 until result.resultParameters.shape.component1()) { + val x = (result.resultParameters[i, 0] * 10000).roundToInt() / 10000.0 + print("$x ") + } + println() + + println("Y true and y received:") + var y_hat_after = funcDifficultForLm(t_example, result.resultParameters, exampleNumber) + for (i in 0 until y_hat.shape.component1()) { + val x = (y_hat[i, 0] * 10000).roundToInt() / 10000.0 + val y = (y_hat_after[i, 0] * 10000).roundToInt() / 10000.0 + println("$x $y") + } + + println("Сhi_sq:") + println(result.resultChiSq) + println("Number of iterations:") + println(result.iterations) +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticEasyTest.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticEasyTest.kt new file mode 100644 index 000000000..507943031 --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticEasyTest.kt @@ -0,0 +1,57 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt.StaticLm + +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.component1 +import space.kscience.kmath.tensors.LevenbergMarquardt.funcDifficultForLm +import space.kscience.kmath.tensors.LevenbergMarquardt.funcEasyForLm +import space.kscience.kmath.tensors.LevenbergMarquardt.getStartDataForFuncEasy +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.LMInput +import space.kscience.kmath.tensors.core.levenbergMarquardt +import kotlin.math.roundToInt + +fun main() { + val startedData = getStartDataForFuncEasy() + val inputData = LMInput(::funcEasyForLm, + DoubleTensorAlgebra.ones(ShapeND(intArrayOf(4, 1))).as2D(), + startedData.t, + startedData.y_dat, + startedData.weight, + startedData.dp, + startedData.p_min, + startedData.p_max, + startedData.opts[1].toInt(), + doubleArrayOf(startedData.opts[2], startedData.opts[3], startedData.opts[4], startedData.opts[5]), + doubleArrayOf(startedData.opts[6], startedData.opts[7], startedData.opts[8]), + startedData.opts[9].toInt(), + 10, + startedData.example_number) + + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + + println("Parameters:") + for (i in 0 until result.resultParameters.shape.component1()) { + val x = (result.resultParameters[i, 0] * 10000).roundToInt() / 10000.0 + print("$x ") + } + println() + + println("Y true and y received:") + var y_hat_after = funcDifficultForLm(startedData.t, result.resultParameters, startedData.example_number) + for (i in 0 until startedData.y_dat.shape.component1()) { + val x = (startedData.y_dat[i, 0] * 10000).roundToInt() / 10000.0 + val y = (y_hat_after[i, 0] * 10000).roundToInt() / 10000.0 + println("$x $y") + } + + println("Сhi_sq:") + println(result.resultChiSq) + println("Number of iterations:") + println(result.iterations) +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticMiddleTest.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticMiddleTest.kt new file mode 100644 index 000000000..0659db103 --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StaticLm/staticMiddleTest.kt @@ -0,0 +1,88 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt.StaticLm + +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.component1 +import space.kscience.kmath.tensors.LevenbergMarquardt.funcMiddleForLm +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.div +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.LMInput +import space.kscience.kmath.tensors.core.levenbergMarquardt +import kotlin.math.roundToInt +fun main() { + val NData = 100 + var t_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + t_example[i, 0] = t_example[i, 0] * (i + 1) + } + + val Nparams = 20 + var p_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_example[i, 0] = p_example[i, 0] + i - 25 + } + + val exampleNumber = 1 + + var y_hat = funcMiddleForLm(t_example, p_example, exampleNumber) + + var p_init = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_init[i, 0] = (p_example[i, 0] + 0.9) + } + + var t = t_example + val y_dat = y_hat + val weight = 1.0 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var p_min = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / -50.0) + val p_max = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / 50.0) + val opts = doubleArrayOf(3.0, 7000.0, 1e-5, 1e-5, 1e-5, 1e-5, 1e-5, 11.0, 9.0, 1.0) + + val inputData = LMInput(::funcMiddleForLm, + p_init.as2D(), + t, + y_dat, + weight, + dp, + p_min.as2D(), + p_max.as2D(), + opts[1].toInt(), + doubleArrayOf(opts[2], opts[3], opts[4], opts[5]), + doubleArrayOf(opts[6], opts[7], opts[8]), + opts[9].toInt(), + 10, + 1) + + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + + println("Parameters:") + for (i in 0 until result.resultParameters.shape.component1()) { + val x = (result.resultParameters[i, 0] * 10000).roundToInt() / 10000.0 + print("$x ") + } + println() + + + var y_hat_after = funcMiddleForLm(t_example, result.resultParameters, exampleNumber) + for (i in 0 until y_hat.shape.component1()) { + val x = (y_hat[i, 0] * 10000).roundToInt() / 10000.0 + val y = (y_hat_after[i, 0] * 10000).roundToInt() / 10000.0 + println("$x $y") + } + + println("Сhi_sq:") + println(result.resultChiSq) + println("Number of iterations:") + println(result.iterations) +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamLm.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamLm.kt new file mode 100644 index 000000000..b2818ef2a --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamLm.kt @@ -0,0 +1,68 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt.StreamingLm + +import kotlinx.coroutines.delay +import kotlinx.coroutines.flow.* +import space.kscience.kmath.nd.* +import space.kscience.kmath.tensors.LevenbergMarquardt.StartDataLm +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.zeros +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.LMInput +import space.kscience.kmath.tensors.core.levenbergMarquardt +import kotlin.random.Random +import kotlin.reflect.KFunction3 + +fun streamLm(lm_func: (MutableStructure2D, MutableStructure2D, Int) -> (MutableStructure2D), + startData: StartDataLm, launchFrequencyInMs: Long, numberOfLaunches: Int): Flow> = flow{ + + var example_number = startData.example_number + var p_init = startData.p_init + var t = startData.t + var y_dat = startData.y_dat + val weight = startData.weight + val dp = startData.dp + val p_min = startData.p_min + val p_max = startData.p_max + val opts = startData.opts + + var steps = numberOfLaunches + val isEndless = (steps <= 0) + + val inputData = LMInput(lm_func, + p_init, + t, + y_dat, + weight, + dp, + p_min, + p_max, + opts[1].toInt(), + doubleArrayOf(opts[2], opts[3], opts[4], opts[5]), + doubleArrayOf(opts[6], opts[7], opts[8]), + opts[9].toInt(), + 10, + example_number) + + while (isEndless || steps > 0) { + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + emit(result.resultParameters) + delay(launchFrequencyInMs) + inputData.realValues = generateNewYDat(y_dat, 0.1) + inputData.startParameters = result.resultParameters + if (!isEndless) steps -= 1 + } +} + +fun generateNewYDat(y_dat: MutableStructure2D, delta: Double): MutableStructure2D{ + val n = y_dat.shape.component1() + val y_dat_new = zeros(ShapeND(intArrayOf(n, 1))).as2D() + for (i in 0 until n) { + val randomEps = Random.nextDouble(delta + delta) - delta + y_dat_new[i, 0] = y_dat[i, 0] + randomEps + } + return y_dat_new +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamingLmTest.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamingLmTest.kt new file mode 100644 index 000000000..c9dd5029e --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/StreamingLm/streamingLmTest.kt @@ -0,0 +1,32 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt.StreamingLm + +import space.kscience.kmath.nd.* +import space.kscience.kmath.tensors.LevenbergMarquardt.* +import kotlin.math.roundToInt + +suspend fun main(){ + val startData = getStartDataForFuncDifficult() + // Создание потока: + val lmFlow = streamLm(::funcDifficultForLm, startData, 0, 100) + var initialTime = System.currentTimeMillis() + var lastTime: Long + val launches = mutableListOf() + // Запуск потока + lmFlow.collect { parameters -> + lastTime = System.currentTimeMillis() + launches.add(lastTime - initialTime) + initialTime = lastTime + for (i in 0 until parameters.shape.component1()) { + val x = (parameters[i, 0] * 10000).roundToInt() / 10000.0 + print("$x ") + if (i == parameters.shape.component1() - 1) println() + } + } + + println("Average without first is: ${launches.subList(1, launches.size - 1).average()}") +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/functionsToOptimize.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/functionsToOptimize.kt new file mode 100644 index 000000000..7ccb37ed0 --- /dev/null +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/LevenbergMarquardt/functionsToOptimize.kt @@ -0,0 +1,222 @@ +/* + * Copyright 2018-2023 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.tensors.LevenbergMarquardt + +import space.kscience.kmath.nd.MutableStructure2D +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.component1 +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.div +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.max +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.plus +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.pow +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.times +import space.kscience.kmath.tensors.core.asDoubleTensor + +public data class StartDataLm ( + var lm_matx_y_dat: MutableStructure2D, + var example_number: Int, + var p_init: MutableStructure2D, + var t: MutableStructure2D, + var y_dat: MutableStructure2D, + var weight: Double, + var dp: MutableStructure2D, + var p_min: MutableStructure2D, + var p_max: MutableStructure2D, + var consts: MutableStructure2D, + var opts: DoubleArray +) + +fun funcEasyForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var y_hat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(m, 1))) + + if (exampleNumber == 1) { + y_hat = DoubleTensorAlgebra.exp((t.times(-1.0 / p[1, 0]))).times(p[0, 0]) + t.times(p[2, 0]).times( + DoubleTensorAlgebra.exp((t.times(-1.0 / p[3, 0]))) + ) + } + else if (exampleNumber == 2) { + val mt = t.max() + y_hat = (t.times(1.0 / mt)).times(p[0, 0]) + + (t.times(1.0 / mt)).pow(2).times(p[1, 0]) + + (t.times(1.0 / mt)).pow(3).times(p[2, 0]) + + (t.times(1.0 / mt)).pow(4).times(p[3, 0]) + } + else if (exampleNumber == 3) { + y_hat = DoubleTensorAlgebra.exp((t.times(-1.0 / p[1, 0]))) + .times(p[0, 0]) + DoubleTensorAlgebra.sin((t.times(1.0 / p[3, 0]))).times(p[2, 0]) + } + + return y_hat.as2D() +} + +fun funcMiddleForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var y_hat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf (m, 1))) + + val mt = t.max() + for(i in 0 until p.shape.component1()){ + y_hat += (t.times(1.0 / mt)).times(p[i, 0]) + } + + for(i in 0 until 5){ + y_hat = funcEasyForLm(y_hat.as2D(), p, exampleNumber).asDoubleTensor() + } + + return y_hat.as2D() +} + +fun funcDifficultForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var y_hat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf (m, 1))) + + val mt = t.max() + for(i in 0 until p.shape.component1()){ + y_hat = y_hat.plus( (t.times(1.0 / mt)).times(p[i, 0]) ) + } + + for(i in 0 until 4){ + y_hat = funcEasyForLm((y_hat.as2D() + t).as2D(), p, exampleNumber).asDoubleTensor() + } + + return y_hat.as2D() +} + + +fun getStartDataForFuncDifficult(): StartDataLm { + val NData = 200 + var t_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + t_example[i, 0] = t_example[i, 0] * (i + 1) - 104 + } + + val Nparams = 15 + var p_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_example[i, 0] = p_example[i, 0] + i - 25 + } + + val exampleNumber = 1 + + var y_hat = funcDifficultForLm(t_example, p_example, exampleNumber) + + var p_init = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_init[i, 0] = (p_example[i, 0] + 0.9) + } + + var t = t_example + val y_dat = y_hat + val weight = 1.0 / Nparams * 1.0 - 0.085 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var p_min = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / -50.0) + val p_max = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / 50.0) + val consts = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), doubleArrayOf(0.0) + ).as2D() + val opts = doubleArrayOf(3.0, 10000.0, 1e-2, 1e-3, 1e-2, 1e-2, 1e-2, 11.0, 9.0, 1.0) + + return StartDataLm(y_dat, 1, p_init, t, y_dat, weight, dp, p_min.as2D(), p_max.as2D(), consts, opts) +} + +fun getStartDataForFuncMiddle(): StartDataLm { + val NData = 100 + var t_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + t_example[i, 0] = t_example[i, 0] * (i + 1) + } + + val Nparams = 20 + var p_example = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_example[i, 0] = p_example[i, 0] + i - 25 + } + + val exampleNumber = 1 + + var y_hat = funcMiddleForLm(t_example, p_example, exampleNumber) + + var p_init = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + p_init[i, 0] = (p_example[i, 0] + 10.0) + } + var t = t_example + val y_dat = y_hat + val weight = 1.0 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var p_min = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / -50.0) + val p_max = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + p_min = p_min.div(1.0 / 50.0) + val consts = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), doubleArrayOf(0.0) + ).as2D() + val opts = doubleArrayOf(3.0, 10000.0, 1e-5, 1e-5, 1e-5, 1e-5, 1e-5, 11.0, 9.0, 1.0) + + var example_number = 1 + + return StartDataLm(y_dat, example_number, p_init, t, y_dat, weight, dp, p_min.as2D(), p_max.as2D(), consts, opts) +} + +fun getStartDataForFuncEasy(): StartDataLm { + val lm_matx_y_dat = doubleArrayOf( + 19.6594, 18.6096, 17.6792, 17.2747, 16.3065, 17.1458, 16.0467, 16.7023, 15.7809, 15.9807, + 14.7620, 15.1128, 16.0973, 15.1934, 15.8636, 15.4763, 15.6860, 15.1895, 15.3495, 16.6054, + 16.2247, 15.9854, 16.1421, 17.0960, 16.7769, 17.1997, 17.2767, 17.5882, 17.5378, 16.7894, + 17.7648, 18.2512, 18.1581, 16.7037, 17.8475, 17.9081, 18.3067, 17.9632, 18.2817, 19.1427, + 18.8130, 18.5658, 18.0056, 18.4607, 18.5918, 18.2544, 18.3731, 18.7511, 19.3181, 17.3066, + 17.9632, 19.0513, 18.7528, 18.2928, 18.5967, 17.8567, 17.7859, 18.4016, 18.9423, 18.4959, + 17.8000, 18.4251, 17.7829, 17.4645, 17.5221, 17.3517, 17.4637, 17.7563, 16.8471, 17.4558, + 17.7447, 17.1487, 17.3183, 16.8312, 17.7551, 17.0942, 15.6093, 16.4163, 15.3755, 16.6725, + 16.2332, 16.2316, 16.2236, 16.5361, 15.3721, 15.3347, 15.5815, 15.6319, 14.4538, 14.6044, + 14.7665, 13.3718, 15.0587, 13.8320, 14.7873, 13.6824, 14.2579, 14.2154, 13.5818, 13.8157 + ) + + var example_number = 1 + val p_init = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(5.0, 2.0, 0.2, 10.0) + ).as2D() + + var t = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(100, 1))).as2D() + for (i in 0 until 100) { + t[i, 0] = t[i, 0] * (i + 1) + } + + val y_dat = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(100, 1)), lm_matx_y_dat + ).as2D() + + val weight = 4.0 + + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + + val p_min = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(-50.0, -20.0, -2.0, -100.0) + ).as2D() + + val p_max = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(50.0, 20.0, 2.0, 100.0) + ).as2D() + + val consts = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), doubleArrayOf(0.0) + ).as2D() + + val opts = doubleArrayOf(3.0, 100.0, 1e-3, 1e-3, 1e-1, 1e-1, 1e-2, 11.0, 9.0, 1.0) + + return StartDataLm(y_dat, example_number, p_init, t, y_dat, weight, dp, p_min, p_max, consts, opts) +} \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/OLSWithSVD.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/OLSWithSVD.kt index b42602988..2c570ea34 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/OLSWithSVD.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/OLSWithSVD.kt @@ -1,14 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.contentEquals import space.kscience.kmath.operations.invoke import space.kscience.kmath.tensors.core.DoubleTensor import space.kscience.kmath.tensors.core.DoubleTensorAlgebra - +import space.kscience.kmath.tensors.core.randomNormal +import space.kscience.kmath.tensors.core.randomNormalLike import kotlin.math.abs // OLS estimator using SVD @@ -21,10 +24,10 @@ fun main() { DoubleTensorAlgebra { // take coefficient vector from normal distribution val alpha = randomNormal( - intArrayOf(5), + ShapeND(5), randSeed ) + fromArray( - intArrayOf(5), + ShapeND(5), doubleArrayOf(1.0, 2.5, 3.4, 5.0, 10.1) ) @@ -32,27 +35,29 @@ fun main() { // also take sample of size 20 from normal distribution for x val x = randomNormal( - intArrayOf(20, 5), + ShapeND(20, 5), randSeed ) // calculate y and add gaussian noise (N(0, 0.05)) val y = x dot alpha - y += y.randomNormalLike(randSeed) * 0.05 + y += randomNormalLike(y, randSeed) * 0.05 // now restore the coefficient vector with OSL estimator with SVD - val (u, singValues, v) = x.svd() + val (u, singValues, v) = svd(x) // we have to make sure the singular values of the matrix are not close to zero println("Singular values:\n$singValues") // inverse Sigma matrix can be restored from singular values with diagonalEmbedding function - val sigma = diagonalEmbedding(singValues.map{ if (abs(it) < 1e-3) 0.0 else 1.0/it }) + val sigma = diagonalEmbedding(singValues.map { if (abs(it) < 1e-3) 0.0 else 1.0 / it }) - val alphaOLS = v dot sigma dot u.transpose() dot y - println("Estimated alpha:\n" + - "$alphaOLS") + val alphaOLS = v dot sigma dot u.transposed() dot y + println( + "Estimated alpha:\n" + + "$alphaOLS" + ) // figure out MSE of approximation fun mse(yTrue: DoubleTensor, yPred: DoubleTensor): Double { @@ -60,7 +65,7 @@ fun main() { require(yTrue.shape contentEquals yPred.shape) val diff = yTrue - yPred - return diff.dot(diff).sqrt().value() + return sqrt(diff.dot(diff)).value() } println("MSE: ${mse(alpha, alphaOLS)}") diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/PCA.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/PCA.kt index aced0cf7d..fb774a39d 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/PCA.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/PCA.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors -import space.kscience.kmath.tensors.core.tensorAlgebra -import space.kscience.kmath.tensors.core.withBroadcast +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.tensors.core.* // simple PCA @@ -16,49 +16,49 @@ fun main(): Unit = Double.tensorAlgebra.withBroadcast { // work in context with // assume x is range from 0 until 10 val x = fromArray( - intArrayOf(10), + ShapeND(10), DoubleArray(10) { it.toDouble() } ) // take y dependent on x with noise - val y = 2.0 * x + (3.0 + x.randomNormalLike(seed) * 1.5) + val y = 2.0 * x + (3.0 + randomNormalLike(x, seed) * 1.5) println("x:\n$x") println("y:\n$y") // stack them into single dataset - val dataset = stack(listOf(x, y)).transpose() + val dataset = stack(listOf(x, y)).transposed() // normalize both x and y - val xMean = x.mean() - val yMean = y.mean() + val xMean = mean(x) + val yMean = mean(y) - val xStd = x.std() - val yStd = y.std() + val xStd = std(x) + val yStd = std(y) - val xScaled = (x - xMean) / xStd - val yScaled = (y - yMean) / yStd + val xScaled: DoubleTensor = (x - xMean) / xStd + val yScaled: DoubleTensor = (y - yMean) / yStd // save means ans standard deviations for further recovery val mean = fromArray( - intArrayOf(2), + ShapeND(2), doubleArrayOf(xMean, yMean) ) println("Means:\n$mean") val std = fromArray( - intArrayOf(2), + ShapeND(2), doubleArrayOf(xStd, yStd) ) println("Standard deviations:\n$std") // calculate the covariance matrix of scaled x and y - val covMatrix = cov(listOf(xScaled, yScaled)) + val covMatrix = covariance(listOf(xScaled.asDoubleTensor1D(), yScaled.asDoubleTensor1D())) println("Covariance matrix:\n$covMatrix") // and find out eigenvector of it - val (_, evecs) = covMatrix.symEig() - val v = evecs[0] + val (_, evecs) = symEig(covMatrix) + val v = evecs.getTensor(0) println("Eigenvector:\n$v") // reduce dimension of dataset @@ -68,7 +68,7 @@ fun main(): Unit = Double.tensorAlgebra.withBroadcast { // work in context with // we can restore original data from reduced data; // for example, find 7th element of dataset. val n = 7 - val restored = (datasetReduced[n] dot v.view(intArrayOf(1, 2))) * std + mean - println("Original value:\n${dataset[n]}") + val restored = (datasetReduced.getTensor(n) dot v.view(ShapeND(1, 2))) * std + mean + println("Original value:\n${dataset.getTensor(n)}") println("Restored value:\n$restored") } diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/dataSetNormalization.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/dataSetNormalization.kt index a436ae1c3..45c2ff120 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/dataSetNormalization.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/dataSetNormalization.kt @@ -1,10 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.tensors.core.randomNormal import space.kscience.kmath.tensors.core.tensorAlgebra import space.kscience.kmath.tensors.core.withBroadcast @@ -13,17 +15,17 @@ import space.kscience.kmath.tensors.core.withBroadcast fun main() = Double.tensorAlgebra.withBroadcast { // work in context with broadcast methods // take dataset of 5-element vectors from normal distribution - val dataset = randomNormal(intArrayOf(100, 5)) * 1.5 // all elements from N(0, 1.5) + val dataset = randomNormal(ShapeND(100, 5)) * 1.5 // all elements from N(0, 1.5) dataset += fromArray( - intArrayOf(5), + ShapeND(5), doubleArrayOf(0.0, 1.0, 1.5, 3.0, 5.0) // row means ) // find out mean and standard deviation of each column - val mean = dataset.mean(0, false) - val std = dataset.std(0, false) + val mean = mean(dataset, 0, false) + val std = std(dataset, 0, false) println("Mean:\n$mean") println("Standard deviation:\n$std") @@ -35,8 +37,8 @@ fun main() = Double.tensorAlgebra.withBroadcast { // work in context with broad // now we can scale dataset with mean normalization val datasetScaled = (dataset - mean) / std - // find out mean and std of scaled dataset + // find out mean and standardDiviation of scaled dataset - println("Mean of scaled:\n${datasetScaled.mean(0, false)}") - println("Mean of scaled:\n${datasetScaled.std(0, false)}") + println("Mean of scaled:\n${mean(datasetScaled, 0, false)}") + println("Mean of scaled:\n${std(datasetScaled, 0, false)}") } \ No newline at end of file diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/linearSystemSolvingWithLUP.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/linearSystemSolvingWithLUP.kt index f465fc424..238696cf9 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/linearSystemSolvingWithLUP.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/linearSystemSolvingWithLUP.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.tensors.core.DoubleTensor import space.kscience.kmath.tensors.core.tensorAlgebra import space.kscience.kmath.tensors.core.withBroadcast @@ -15,13 +16,13 @@ fun main() = Double.tensorAlgebra.withBroadcast {// work in context with linear // set true value of x val trueX = fromArray( - intArrayOf(4), + ShapeND(4), doubleArrayOf(-2.0, 1.5, 6.8, -2.4) ) // and A matrix val a = fromArray( - intArrayOf(4, 4), + ShapeND(4, 4), doubleArrayOf( 0.5, 10.5, 4.5, 1.0, 8.5, 0.9, 12.8, 0.1, @@ -40,7 +41,7 @@ fun main() = Double.tensorAlgebra.withBroadcast {// work in context with linear // solve `Ax = b` system using LUP decomposition // get P, L, U such that PA = LU - val (p, l, u) = a.lu() + val (p, l, u) = lu(a) // check P is permutation matrix println("P:\n$p") @@ -64,9 +65,9 @@ fun main() = Double.tensorAlgebra.withBroadcast {// work in context with linear // this function returns solution x of a system lx = b, l should be lower triangular fun solveLT(l: DoubleTensor, b: DoubleTensor): DoubleTensor { val n = l.shape[0] - val x = zeros(intArrayOf(n)) + val x = zeros(ShapeND(n)) for (i in 0 until n) { - x[intArrayOf(i)] = (b[intArrayOf(i)] - l[i].dot(x).value()) / l[intArrayOf(i, i)] + x[intArrayOf(i)] = (b[intArrayOf(i)] - l.getTensor(i).dot(x).value()) / l[intArrayOf(i, i)] } return x } @@ -75,7 +76,7 @@ fun main() = Double.tensorAlgebra.withBroadcast {// work in context with linear // solveLT(l, b) function can be easily adapted for upper triangular matrix by the permutation matrix revMat // create it by placing ones on side diagonal - val revMat = u.zeroesLike() + val revMat = zeroesLike(u) val n = revMat.shape[0] for (i in 0 until n) { revMat[intArrayOf(i, n - 1 - i)] = 1.0 diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/multik.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/multik.kt index f2d1f0b41..67e0631e7 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/multik.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/multik.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,11 +7,14 @@ package space.kscience.kmath.tensors import org.jetbrains.kotlinx.multik.api.Multik import org.jetbrains.kotlinx.multik.api.ndarray -import space.kscience.kmath.multik.multikAlgebra +import org.jetbrains.kotlinx.multik.default.DefaultEngine +import space.kscience.kmath.multik.MultikDoubleAlgebra import space.kscience.kmath.nd.one -import space.kscience.kmath.operations.DoubleField -fun main(): Unit = with(DoubleField.multikAlgebra) { + +val multikAlgebra = MultikDoubleAlgebra(DefaultEngine()) + +fun main(): Unit = with(multikAlgebra) { val a = Multik.ndarray(intArrayOf(1, 2, 3)).asType().wrap() val b = Multik.ndarray(doubleArrayOf(1.0, 2.0, 3.0)).wrap() one(a.shape) - a + b * 3.0 diff --git a/examples/src/main/kotlin/space/kscience/kmath/tensors/neuralNetwork.kt b/examples/src/main/kotlin/space/kscience/kmath/tensors/neuralNetwork.kt index 5c41ab0f1..8fd5ae5ad 100644 --- a/examples/src/main/kotlin/space/kscience/kmath/tensors/neuralNetwork.kt +++ b/examples/src/main/kotlin/space/kscience/kmath/tensors/neuralNetwork.kt @@ -1,15 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.contentEquals +import space.kscience.kmath.operations.asIterable import space.kscience.kmath.operations.invoke -import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra -import space.kscience.kmath.tensors.core.DoubleTensor -import space.kscience.kmath.tensors.core.DoubleTensorAlgebra -import space.kscience.kmath.tensors.core.copyArray +import space.kscience.kmath.tensors.core.* import kotlin.math.sqrt const val seed = 100500L @@ -48,7 +48,7 @@ fun reluDer(x: DoubleTensor): DoubleTensor = DoubleTensorAlgebra { class ReLU : Activation(::relu, ::reluDer) fun sigmoid(x: DoubleTensor): DoubleTensor = DoubleTensorAlgebra { - 1.0 / (1.0 + (-x).exp()) + 1.0 / (1.0 + exp((-x))) } fun sigmoidDer(x: DoubleTensor): DoubleTensor = DoubleTensorAlgebra { @@ -67,22 +67,22 @@ class Dense( private val weights: DoubleTensor = DoubleTensorAlgebra { randomNormal( - intArrayOf(inputUnits, outputUnits), + ShapeND(inputUnits, outputUnits), seed ) * sqrt(2.0 / (inputUnits + outputUnits)) } - private val bias: DoubleTensor = DoubleTensorAlgebra { zeros(intArrayOf(outputUnits)) } + private val bias: DoubleTensor = DoubleTensorAlgebra { zeros(ShapeND(outputUnits)) } override fun forward(input: DoubleTensor): DoubleTensor = BroadcastDoubleTensorAlgebra { (input dot weights) + bias } override fun backward(input: DoubleTensor, outputError: DoubleTensor): DoubleTensor = DoubleTensorAlgebra { - val gradInput = outputError dot weights.transpose() + val gradInput = outputError dot weights.transposed() - val gradW = input.transpose() dot outputError - val gradBias = outputError.mean(dim = 0, keepDim = false) * input.shape[0].toDouble() + val gradW = input.transposed() dot outputError + val gradBias = mean(structureND = outputError, dim = 0, keepDim = false) * input.shape[0].toDouble() weights -= learningRate * gradW bias -= learningRate * gradBias @@ -106,17 +106,16 @@ fun accuracy(yPred: DoubleTensor, yTrue: DoubleTensor): Double { } // neural network class -@OptIn(ExperimentalStdlibApi::class) class NeuralNetwork(private val layers: List) { private fun softMaxLoss(yPred: DoubleTensor, yTrue: DoubleTensor): DoubleTensor = BroadcastDoubleTensorAlgebra { - val onesForAnswers = yPred.zeroesLike() - yTrue.copyArray().forEachIndexed { index, labelDouble -> + val onesForAnswers = zeroesLike(yPred) + yTrue.source.asIterable().forEachIndexed { index, labelDouble -> val label = labelDouble.toInt() onesForAnswers[intArrayOf(index, label)] = 1.0 } - val softmaxValue = yPred.exp() / yPred.exp().sum(dim = 1, keepDim = true) + val softmaxValue = exp(yPred) / exp(yPred).sum(dim = 1, keepDim = true) (-onesForAnswers + softmaxValue) / (yPred.shape[0].toDouble()) } @@ -163,7 +162,7 @@ class NeuralNetwork(private val layers: List) { for ((xBatch, yBatch) in iterBatch(xTrain, yTrain)) { train(xBatch, yBatch) } - println("Accuracy:${accuracy(yTrain, predict(xTrain).argMax(1, true).asDouble())}") + println("Accuracy:${accuracy(yTrain, predict(xTrain).argMax(1, true).toDoubleTensor())}") } } @@ -174,7 +173,6 @@ class NeuralNetwork(private val layers: List) { } -@OptIn(ExperimentalStdlibApi::class) fun main() = BroadcastDoubleTensorAlgebra { val features = 5 val sampleSize = 250 @@ -182,19 +180,19 @@ fun main() = BroadcastDoubleTensorAlgebra { //val testSize = sampleSize - trainSize // take sample of features from normal distribution - val x = randomNormal(intArrayOf(sampleSize, features), seed) * 2.5 + val x = randomNormal(ShapeND(sampleSize, features), seed) * 2.5 x += fromArray( - intArrayOf(5), + ShapeND(5), doubleArrayOf(0.0, -1.0, -2.5, -3.0, 5.5) // row means ) // define class like '1' if the sum of features > 0 and '0' otherwise val y = fromArray( - intArrayOf(sampleSize, 1), + ShapeND(sampleSize, 1), DoubleArray(sampleSize) { i -> - if (x[i].sum() > 0.0) { + if (x.getTensor(i).sum() > 0.0) { 1.0 } else { 0.0 @@ -230,7 +228,7 @@ fun main() = BroadcastDoubleTensorAlgebra { val prediction = model.predict(xTest) // process raw prediction via argMax - val predictionLabels = prediction.argMax(1, true).asDouble() + val predictionLabels = prediction.argMax(1, true).toDoubleTensor() // find out accuracy val acc = accuracy(yTest, predictionLabels) diff --git a/gradle.properties b/gradle.properties index 6b45ee49f..fee75d428 100644 --- a/gradle.properties +++ b/gradle.properties @@ -3,13 +3,14 @@ # 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.incremental.js.ir=true org.gradle.configureondemand=true -org.gradle.parallel=true org.gradle.jvmargs=-Xmx4096m -toolsVersion=0.11.8-kotlin-1.7.10 +toolsVersion=0.14.8-kotlin-1.8.20 + + +org.gradle.parallel=true +org.gradle.workers.max=4 diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index aa991fcea..fae08049a 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.4.2-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.1.1-bin.zip zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/kmath-ast/README.md b/kmath-ast/README.md index c6da64982..d85a18e1c 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-ast:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -20,7 +20,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-ast:0.3.1-dev-1' + implementation 'space.kscience:kmath-ast:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -31,7 +31,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ast:0.3.1-dev-1") + implementation("space.kscience:kmath-ast:0.4.0-dev-1") } ``` diff --git a/kmath-ast/build.gradle.kts b/kmath-ast/build.gradle.kts index f49c2767a..7cdb745f0 100644 --- a/kmath-ast/build.gradle.kts +++ b/kmath-ast/build.gradle.kts @@ -1,67 +1,63 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.mpp") } -kotlin.js { - nodejs { - testTask { - useMocha().timeout = "0" - } - } +kscience{ + jvm() + js() + native() - browser { - testTask { - useMocha().timeout = "0" - } + dependencies { + api(projects.kmathCore) + api("com.github.h0tk3y.betterParse:better-parse:0.4.4") } -} -kotlin.sourceSets { - filter { it.name.contains("test", true) } - .map(org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet::languageSettings) - .forEach { it.optIn("space.kscience.kmath.misc.UnstableKMathAPI") } + testDependencies { + implementation(projects.kmathComplex) + } - commonMain { - dependencies { - api("com.github.h0tk3y.betterParse:better-parse:0.4.4") - api(project(":kmath-core")) - } + dependencies(jsMain) { + implementation(npm("astring", "1.7.5")) + implementation(npm("binaryen", "101.0.0")) + implementation(npm("js-base64", "3.6.1")) } - commonTest { - dependencies { - implementation(project(":kmath-complex")) - } + dependencies(jvmMain){ + implementation("org.ow2.asm:asm-commons:9.2") } - jsMain { - dependencies { - implementation(npm("astring", "1.7.5")) - implementation(npm("binaryen", "101.0.0")) - implementation(npm("js-base64", "3.6.1")) +} + +kotlin { + js { + nodejs { + testTask { + useMocha().timeout = "0" + } } - } - jvmMain { - dependencies { - implementation("org.ow2.asm:asm-commons:9.2") + browser { + testTask { + useMocha().timeout = "0" + } } } -} -//Workaround for https://github.com/Kotlin/dokka/issues/1455 -tasks.dokkaHtml { - dependsOn(tasks.build) + sourceSets { + filter { it.name.contains("test", true) } + .map(org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet::languageSettings) + .forEach { it.optIn("space.kscience.kmath.UnstableKMathAPI") } + } } -if (System.getProperty("space.kscience.kmath.ast.dump.generated.classes") == "1") - tasks.jvmTest { +if (System.getProperty("space.kscience.kmath.ast.dump.generated.classes") == "1") { + tasks.withType { jvmArgs("-Dspace.kscience.kmath.ast.dump.generated.classes=1") } +} readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( 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 index 8a8b8797d..e82f7a3ab 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/TypedMst.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,7 +7,6 @@ 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 @@ -16,7 +15,6 @@ import space.kscience.kmath.operations.NumericAlgebra * * @param T the type. */ -@UnstableKMathAPI public sealed interface TypedMst { /** * A node containing a unary operation. @@ -133,7 +131,6 @@ public sealed interface TypedMst { /** * 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)) @@ -158,7 +155,6 @@ public fun TypedMst.interpret(algebra: Algebra, arguments: Map TypedMst.interpret(algebra: Algebra, vararg arguments: Pair): T = interpret( algebra, when (arguments.size) { @@ -171,7 +167,6 @@ public fun TypedMst.interpret(algebra: Algebra, vararg arguments: Pair /** * 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 index 71fb154c9..8fc5a6aaf 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/evaluateConstants.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,7 +7,6 @@ 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 @@ -15,7 +14,6 @@ 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"), diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/parser.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/parser.kt index 012a6e65f..2c9a2a9ad 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/parser.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/parser.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/LatexSyntaxRenderer.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/LatexSyntaxRenderer.kt index 2df3d3cc7..5a338afed 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/LatexSyntaxRenderer.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/LatexSyntaxRenderer.kt @@ -1,12 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering -import space.kscience.kmath.misc.UnstableKMathAPI - /** * [SyntaxRenderer] implementation for LaTeX. * @@ -25,7 +23,6 @@ import space.kscience.kmath.misc.UnstableKMathAPI * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public object LatexSyntaxRenderer : SyntaxRenderer { override fun render(node: MathSyntax, output: Appendable): Unit = output.run { fun render(syntax: MathSyntax) = render(syntax, output) diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathMLSyntaxRenderer.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathMLSyntaxRenderer.kt index 8b5819b84..bfd9aeef9 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathMLSyntaxRenderer.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathMLSyntaxRenderer.kt @@ -1,12 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering -import space.kscience.kmath.misc.UnstableKMathAPI - /** * [SyntaxRenderer] implementation for MathML. * @@ -14,7 +12,6 @@ import space.kscience.kmath.misc.UnstableKMathAPI * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public object MathMLSyntaxRenderer : SyntaxRenderer { override fun render(node: MathSyntax, output: Appendable) { output.append("") diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathRenderer.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathRenderer.kt index fdef35ebd..f88a5b319 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathRenderer.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathRenderer.kt @@ -1,19 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering import space.kscience.kmath.expressions.MST -import space.kscience.kmath.misc.UnstableKMathAPI /** * Renders [MST] to [MathSyntax]. * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public fun interface MathRenderer { /** * Renders [MST] to [MathSyntax]. @@ -27,7 +25,6 @@ public fun interface MathRenderer { * @property features The applied features. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public open class FeaturedMathRenderer(public val features: List) : MathRenderer { override fun render(mst: MST): MathSyntax { for (feature in features) feature.render(this, mst)?.let { return it } @@ -51,7 +48,6 @@ public open class FeaturedMathRenderer(public val features: List) * @property stages The applied stages. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public open class FeaturedMathRendererWithPostProcess( features: List, public val stages: List, diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathSyntax.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathSyntax.kt index ee23ab408..0196be3b6 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathSyntax.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/MathSyntax.kt @@ -1,18 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering -import space.kscience.kmath.misc.UnstableKMathAPI - /** * Syntax node for mathematical typography. * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public sealed class MathSyntax { /** * The parent node of this syntax node. @@ -25,7 +22,6 @@ public sealed class MathSyntax { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public sealed class TerminalSyntax : MathSyntax() /** @@ -33,7 +29,6 @@ public sealed class TerminalSyntax : MathSyntax() * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public sealed class OperationSyntax : MathSyntax() { /** * The operation token. @@ -46,7 +41,6 @@ public sealed class OperationSyntax : MathSyntax() { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public sealed class UnarySyntax : OperationSyntax() { /** * The operand of this node. @@ -59,7 +53,6 @@ public sealed class UnarySyntax : OperationSyntax() { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public sealed class BinarySyntax : OperationSyntax() { /** * The left-hand side operand. @@ -78,7 +71,6 @@ public sealed class BinarySyntax : OperationSyntax() { * @property string The digits of number. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class NumberSyntax(public var string: String) : TerminalSyntax() /** @@ -87,7 +79,6 @@ public data class NumberSyntax(public var string: String) : TerminalSyntax() * @property string The symbol. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class SymbolSyntax(public var string: String) : TerminalSyntax() /** @@ -98,7 +89,6 @@ public data class SymbolSyntax(public var string: String) : TerminalSyntax() * @see UnaryOperatorSyntax * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class OperatorNameSyntax(public var name: String) : TerminalSyntax() /** @@ -107,7 +97,6 @@ public data class OperatorNameSyntax(public var name: String) : TerminalSyntax() * @property kind The kind of symbol. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class SpecialSymbolSyntax(public var kind: Kind) : TerminalSyntax() { /** * The kind of symbol. @@ -132,7 +121,6 @@ public data class SpecialSymbolSyntax(public var kind: Kind) : TerminalSyntax() * @property parentheses Whether the operand should be wrapped with parentheses. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class OperandSyntax( public val operand: MathSyntax, public var parentheses: Boolean, @@ -148,7 +136,6 @@ public data class OperandSyntax( * @property prefix The prefix. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class UnaryOperatorSyntax( override val operation: String, public var prefix: MathSyntax, @@ -164,7 +151,6 @@ public data class UnaryOperatorSyntax( * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class UnaryPlusSyntax( override val operation: String, override val operand: OperandSyntax, @@ -179,7 +165,6 @@ public data class UnaryPlusSyntax( * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class UnaryMinusSyntax( override val operation: String, override val operand: OperandSyntax, @@ -195,7 +180,6 @@ public data class UnaryMinusSyntax( * @property operand The radicand. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class RadicalSyntax( override val operation: String, override val operand: MathSyntax, @@ -213,7 +197,6 @@ public data class RadicalSyntax( * (*ex*). * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class ExponentSyntax( override val operation: String, override val operand: OperandSyntax, @@ -231,7 +214,6 @@ public data class ExponentSyntax( * @property right The superscript. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class SuperscriptSyntax( override val operation: String, override val left: MathSyntax, @@ -250,7 +232,6 @@ public data class SuperscriptSyntax( * @property right The subscript. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class SubscriptSyntax( override val operation: String, override val left: MathSyntax, @@ -268,7 +249,6 @@ public data class SubscriptSyntax( * @property prefix The prefix. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class BinaryOperatorSyntax( override val operation: String, public var prefix: MathSyntax, @@ -288,7 +268,6 @@ public data class BinaryOperatorSyntax( * @param right The addend. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class BinaryPlusSyntax( override val operation: String, override val left: OperandSyntax, @@ -307,7 +286,6 @@ public data class BinaryPlusSyntax( * @param right The subtrahend. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class BinaryMinusSyntax( override val operation: String, override val left: OperandSyntax, @@ -327,7 +305,6 @@ public data class BinaryMinusSyntax( * @property infix Whether infix (*1 / 2*) or normal (*½*) fraction should be made. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class FractionSyntax( override val operation: String, override val left: OperandSyntax, @@ -347,7 +324,6 @@ public data class FractionSyntax( * @property right The radicand. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class RadicalWithIndexSyntax( override val operation: String, override val left: MathSyntax, @@ -367,7 +343,6 @@ public data class RadicalWithIndexSyntax( * @property times Whether the times (×) symbol should be used. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public data class MultiplicationSyntax( override val operation: String, override val left: OperandSyntax, diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/SyntaxRenderer.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/SyntaxRenderer.kt index 362c07d72..16957bdd2 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/SyntaxRenderer.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/SyntaxRenderer.kt @@ -1,19 +1,16 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering -import space.kscience.kmath.misc.UnstableKMathAPI - /** * Abstraction of writing [MathSyntax] as a string of an actual markup language. Typical implementation should * involve traversal of MathSyntax with handling each subtype. * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public fun interface SyntaxRenderer { /** * Renders the [MathSyntax] to [output]. @@ -26,7 +23,6 @@ public fun interface SyntaxRenderer { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public fun SyntaxRenderer.renderWithStringBuilder(node: MathSyntax): String { val sb = StringBuilder() render(node, sb) diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/features.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/features.kt index 90f78a152..4deffc83c 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/features.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/features.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,7 +8,6 @@ package space.kscience.kmath.ast.rendering import space.kscience.kmath.ast.rendering.FeaturedMathRenderer.RenderFeature import space.kscience.kmath.expressions.MST import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import kotlin.reflect.KClass @@ -17,7 +16,6 @@ import kotlin.reflect.KClass * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public val PrintSymbol: RenderFeature = RenderFeature { _, node -> if (node !is Symbol) null else SymbolSyntax(string = node.identity) @@ -28,7 +26,6 @@ public val PrintSymbol: RenderFeature = RenderFeature { _, node -> * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public val PrintNumeric: RenderFeature = RenderFeature { _, node -> if (node !is MST.Numeric) null @@ -36,7 +33,6 @@ public val PrintNumeric: RenderFeature = RenderFeature { _, node -> NumberSyntax(string = node.value.toString()) } -@UnstableKMathAPI private fun printSignedNumberString(s: String): MathSyntax = if (s.startsWith('-')) UnaryMinusSyntax( operation = GroupOps.MINUS_OPERATION, @@ -55,7 +51,6 @@ else * @property types The suitable types. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class PrettyPrintFloats(public val types: Set>) : RenderFeature { override fun render(renderer: FeaturedMathRenderer, node: MST): MathSyntax? { if (node !is MST.Numeric || node.value::class !in types) return null @@ -115,7 +110,6 @@ public class PrettyPrintFloats(public val types: Set>) : Rend * @property types The suitable types. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class PrettyPrintIntegers(public val types: Set>) : RenderFeature { override fun render(renderer: FeaturedMathRenderer, node: MST): MathSyntax? = if (node !is MST.Numeric || node.value::class !in types) @@ -138,7 +132,6 @@ public class PrettyPrintIntegers(public val types: Set>) : Re * @property symbols The allowed symbols. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class PrettyPrintPi(public val symbols: Set) : RenderFeature { override fun render(renderer: FeaturedMathRenderer, node: MST): MathSyntax? = if (node !is Symbol || node.identity !in symbols) @@ -161,7 +154,6 @@ public class PrettyPrintPi(public val symbols: Set) : RenderFeature { * @param operations the allowed operations. If `null`, any operation is accepted. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public abstract class Unary(public val operations: Collection?) : RenderFeature { /** * The actual render function specialized for [MST.Unary]. @@ -182,7 +174,6 @@ public abstract class Unary(public val operations: Collection?) : Render * @property operations the allowed operations. If `null`, any operation is accepted. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public abstract class Binary(public val operations: Collection?) : RenderFeature { /** * The actual render function specialized for [MST.Binary]. @@ -200,7 +191,6 @@ public abstract class Binary(public val operations: Collection?) : Rende * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class BinaryPlus(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = BinaryPlusSyntax( @@ -222,7 +212,6 @@ public class BinaryPlus(operations: Collection?) : Binary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class BinaryMinus(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = BinaryMinusSyntax( @@ -244,7 +233,6 @@ public class BinaryMinus(operations: Collection?) : Binary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class UnaryPlus(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = UnaryPlusSyntax( operation = node.operation, @@ -264,7 +252,6 @@ public class UnaryPlus(operations: Collection?) : Unary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class UnaryMinus(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = UnaryMinusSyntax( operation = node.operation, @@ -284,7 +271,6 @@ public class UnaryMinus(operations: Collection?) : Unary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class Fraction(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = FractionSyntax( operation = node.operation, @@ -306,7 +292,6 @@ public class Fraction(operations: Collection?) : Binary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class BinaryOperator(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = BinaryOperatorSyntax( @@ -329,7 +314,6 @@ public class BinaryOperator(operations: Collection?) : Binary(operations * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class UnaryOperator(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = UnaryOperatorSyntax( @@ -351,7 +335,6 @@ public class UnaryOperator(operations: Collection?) : Unary(operations) * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class Power(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = SuperscriptSyntax( @@ -371,7 +354,6 @@ public class Power(operations: Collection?) : Binary(operations) { /** * Handles binary nodes by producing [RadicalSyntax] with no index. */ -@UnstableKMathAPI public class SquareRoot(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = RadicalSyntax(operation = node.operation, operand = parent.render(node.value)) @@ -389,7 +371,6 @@ public class SquareRoot(operations: Collection?) : Unary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class Exponent(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = ExponentSyntax( operation = node.operation, @@ -410,7 +391,6 @@ public class Exponent(operations: Collection?) : Unary(operations) { * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class Multiplication(operations: Collection?) : Binary(operations) { override fun renderBinary(parent: FeaturedMathRenderer, node: MST.Binary): MathSyntax = MultiplicationSyntax( @@ -433,7 +413,6 @@ public class Multiplication(operations: Collection?) : Binary(operations * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class InverseTrigonometricOperations(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = UnaryOperatorSyntax( @@ -460,7 +439,6 @@ public class InverseTrigonometricOperations(operations: Collection?) : U * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class InverseHyperbolicOperations(operations: Collection?) : Unary(operations) { override fun renderUnary(parent: FeaturedMathRenderer, node: MST.Unary): MathSyntax = UnaryOperatorSyntax( diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt index 291399cee..dce99cc5a 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/phases.kt b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/phases.kt index c0271fbb5..0d26621d3 100644 --- a/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/phases.kt +++ b/kmath-ast/src/commonMain/kotlin/space/kscience/kmath/ast/rendering/phases.kt @@ -1,12 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.rendering import space.kscience.kmath.ast.rendering.FeaturedMathRendererWithPostProcess.PostProcessPhase -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.FieldOps import space.kscience.kmath.operations.GroupOps import space.kscience.kmath.operations.PowerOperations @@ -17,7 +16,6 @@ import space.kscience.kmath.operations.RingOps * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public val BetterMultiplication: PostProcessPhase = PostProcessPhase { node -> fun perform(node: MathSyntax): Unit = when (node) { is NumberSyntax -> Unit @@ -91,7 +89,6 @@ public val BetterMultiplication: PostProcessPhase = PostProcessPhase { node -> * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public val BetterFraction: PostProcessPhase = PostProcessPhase { node -> fun perform(node: MathSyntax, infix: Boolean = false): Unit = when (node) { is NumberSyntax -> Unit @@ -162,7 +159,6 @@ public val BetterFraction: PostProcessPhase = PostProcessPhase { node -> * * @author Iaroslav Postovalov */ -@UnstableKMathAPI public val BetterExponent: PostProcessPhase = PostProcessPhase { node -> fun perform(node: MathSyntax): Boolean { return when (node) { @@ -202,7 +198,6 @@ public val BetterExponent: PostProcessPhase = PostProcessPhase { node -> * @property precedenceFunction Returns the precedence number for syntax node. Higher number is lower priority. * @author Iaroslav Postovalov */ -@UnstableKMathAPI public class SimplifyParentheses(public val precedenceFunction: (MathSyntax) -> Int) : PostProcessPhase { override fun perform(node: MathSyntax): Unit = when (node) { diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerConsistencyWithInterpreter.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerConsistencyWithInterpreter.kt index 1edb5923e..3400db0f8 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerConsistencyWithInterpreter.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerConsistencyWithInterpreter.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerOperations.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerOperations.kt index be8a92f3e..bf56b80a6 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerOperations.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerOperations.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerVariables.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerVariables.kt index 93ef97b0f..f23d36240 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerVariables.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestCompilerVariables.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 index 954a0f330..95b804455 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestFolding.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParser.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParser.kt index d0c3a789e..d3c203903 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParser.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParser.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParserPrecedence.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParserPrecedence.kt index 42cf5ce58..4b3631663 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParserPrecedence.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/TestParserPrecedence.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestFeatures.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestFeatures.kt index a40c785b9..7b5ec5765 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestFeatures.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestFeatures.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestLatex.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestLatex.kt index 43f31baba..66c0ae1ae 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestLatex.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestLatex.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestMathML.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestMathML.kt index 145055494..8bc014c54 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestMathML.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestMathML.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestStages.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestStages.kt index 09ec127c7..306538d5d 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestStages.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestStages.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestUtils.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestUtils.kt index bf87b6fd0..79f178eef 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestUtils.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/rendering/TestUtils.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/utils.kt b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/utils.kt index ec7436188..fe035c69f 100644 --- a/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/utils.kt +++ b/kmath-ast/src/commonTest/kotlin/space/kscience/kmath/ast/utils.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt index 521907d2c..f6411334c 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 240acf1d7..87c2df2d2 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 @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.estree +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.ast.TypedMst import space.kscience.kmath.ast.evaluateConstants import space.kscience.kmath.estree.internal.ESTreeBuilder @@ -13,7 +14,6 @@ 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 /** 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 16a59d273..1517cdef2 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/astring/astring.typealises.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/astring/astring.typealises.kt index eb5c1e3dd..2434788ec 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/astring/astring.typealises.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/estree/internal/astring/astring.typealises.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.kt index cca2d83af..cc4360f8d 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.typealises.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.typealises.kt index 93b4f6ce6..a17726c9d 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.typealises.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/astring/astring.typealises.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/base64/base64.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/base64/base64.kt index 86e0cede7..8ea699837 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/base64/base64.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/base64/base64.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.kt index 42b6ac7d8..d907a12c9 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.typealiases.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.typealiases.kt index 523b13b40..eebfeb6ef 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.typealiases.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/binaryen/index.binaryen.typealiases.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/emitter/emitter.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/emitter/emitter.kt index 1f7b09af8..a2a04da79 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/emitter/emitter.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/emitter/emitter.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 5b1ce914e..2dd2c08cd 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.kt index b62b8c06c..bf4a25367 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/estree/estree.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/stream/stream.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/stream/stream.kt index 52be5530f..ced165a3a 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/stream/stream.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/stream/stream.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es2015.iterable.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es2015.iterable.kt index 9c012e3a3..2c0dc9de1 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es2015.iterable.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es2015.iterable.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es5.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es5.kt index 0cd395f2c..f20e2d865 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es5.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/tsstdlib/lib.es5.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/lib.dom.WebAssembly.module_dukat.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/lib.dom.WebAssembly.module_dukat.kt index 90690abed..873a5e1d2 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/lib.dom.WebAssembly.module_dukat.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/lib.dom.WebAssembly.module_dukat.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/nonDeclarations.WebAssembly.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/nonDeclarations.WebAssembly.kt index c5023c384..ba86e977b 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/nonDeclarations.WebAssembly.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/internal/webassembly/nonDeclarations.WebAssembly.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 878919d8d..1908f0659 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 @@ -1,15 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.wasm.internal +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.ast.TypedMst import space.kscience.kmath.expressions.* import space.kscience.kmath.internal.binaryen.* import space.kscience.kmath.internal.webassembly.Instance -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.internal.binaryen.Module as BinaryenModule import space.kscience.kmath.internal.webassembly.Module as WasmModule diff --git a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/f64StandardFunctions.kt b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/f64StandardFunctions.kt index 21a88b5d0..d60f24247 100644 --- a/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/f64StandardFunctions.kt +++ b/kmath-ast/src/jsMain/kotlin/space/kscience/kmath/wasm/internal/f64StandardFunctions.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 f9540f9db..acb26f918 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,10 +7,10 @@ package space.kscience.kmath.wasm +import space.kscience.kmath.UnstableKMathAPI 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 import space.kscience.kmath.operations.IntRing import space.kscience.kmath.wasm.internal.DoubleWasmBuilder diff --git a/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/ast/utils.kt b/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/ast/utils.kt index 0d896c6f6..7c397d5a0 100644 --- a/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/ast/utils.kt +++ b/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/ast/utils.kt @@ -1,10 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.ast +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Expression import space.kscience.kmath.expressions.MST import space.kscience.kmath.expressions.Symbol diff --git a/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/wasm/TestWasmSpecific.kt b/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/wasm/TestWasmSpecific.kt index 8ae5fcb36..132f9f1bd 100644 --- a/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/wasm/TestWasmSpecific.kt +++ b/kmath-ast/src/jsTest/kotlin/space/kscience/kmath/wasm/TestWasmSpecific.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.wasm +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.MstExtendedField import space.kscience.kmath.expressions.MstRing import space.kscience.kmath.expressions.invoke @@ -15,6 +16,7 @@ import space.kscience.kmath.operations.invoke import kotlin.test.Test import kotlin.test.assertEquals +@OptIn(UnstableKMathAPI::class) internal class TestWasmSpecific { @Test fun int() { 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 73b9c97a7..7094d0442 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,11 +7,11 @@ package space.kscience.kmath.asm +import space.kscience.kmath.UnstableKMathAPI 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.misc.UnstableKMathAPI import space.kscience.kmath.operations.Algebra import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.IntRing 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 a76b47ecc..e1fd455fd 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 6cf3d8721..acae45d87 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 01bad83e5..a3e5b7522 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -11,9 +11,9 @@ 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.UnstableKMathAPI import space.kscience.kmath.ast.TypedMst import space.kscience.kmath.expressions.* -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import java.lang.invoke.MethodHandles import java.lang.invoke.MethodType 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 9e880f4fc..b3ccfdc0c 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/mapIntrinsics.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/mapIntrinsics.kt index 3a5ef74f7..6459f4dcf 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/mapIntrinsics.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/asm/internal/mapIntrinsics.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt index 556adbe7d..ec66be830 100644 --- a/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt +++ b/kmath-ast/src/jvmMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ast/src/jvmTest/kotlin/space/kscience/kmath/ast/utils.kt b/kmath-ast/src/jvmTest/kotlin/space/kscience/kmath/ast/utils.kt index 47f1cc476..be890273d 100644 --- a/kmath-ast/src/jvmTest/kotlin/space/kscience/kmath/ast/utils.kt +++ b/kmath-ast/src/jvmTest/kotlin/space/kscience/kmath/ast/utils.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.UnstableKMathAPI import space.kscience.kmath.expressions.Expression import space.kscience.kmath.expressions.MST import space.kscience.kmath.expressions.Symbol @@ -30,6 +31,7 @@ private object GenericAsmCompilerTestContext : CompilerTestContext { asmCompile(algebra as Algebra, arguments) } +@OptIn(UnstableKMathAPI::class) private object PrimitiveAsmCompilerTestContext : CompilerTestContext { override fun MST.compileToExpression(algebra: IntRing): Expression = asmCompileToExpression(algebra) override fun MST.compile(algebra: IntRing, arguments: Map): Int = asmCompile(algebra, arguments) diff --git a/kmath-ast/src/nativeMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt b/kmath-ast/src/nativeMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt new file mode 100644 index 000000000..ec66be830 --- /dev/null +++ b/kmath-ast/src/nativeMain/kotlin/space/kscience/kmath/ast/rendering/multiplatformToString.kt @@ -0,0 +1,9 @@ +/* + * Copyright 2018-2022 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.rendering + +internal actual fun Double.multiplatformToString(): String = toString() +internal actual fun Float.multiplatformToString(): String = toString() diff --git a/kmath-ast/src/nativeTest/kotlin/space/kscience/kmath/ast/runCompilerTest.kt b/kmath-ast/src/nativeTest/kotlin/space/kscience/kmath/ast/runCompilerTest.kt new file mode 100644 index 000000000..0674b0492 --- /dev/null +++ b/kmath-ast/src/nativeTest/kotlin/space/kscience/kmath/ast/runCompilerTest.kt @@ -0,0 +1,10 @@ +/* + * Copyright 2018-2022 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 + +internal actual inline fun runCompilerTest(action: CompilerTestContext.() -> Unit) { + //doNothing +} \ No newline at end of file diff --git a/kmath-commons/README.md b/kmath-commons/README.md index 89f1f6c9f..47b61c409 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-commons:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-commons:0.3.1-dev-1' + implementation 'space.kscience:kmath-commons:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-commons:0.3.1-dev-1") + implementation("space.kscience:kmath-commons:0.4.0-dev-1") } ``` diff --git a/kmath-commons/build.gradle.kts b/kmath-commons/build.gradle.kts index 96c17a215..50fef7ac8 100644 --- a/kmath-commons/build.gradle.kts +++ b/kmath-commons/build.gradle.kts @@ -1,6 +1,5 @@ plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } description = "Commons math binding for kmath" @@ -16,5 +15,5 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } \ No newline at end of file diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpression.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/CmDsExpression.kt similarity index 89% rename from kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpression.kt rename to kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/CmDsExpression.kt index 82694d95a..38eaf8868 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpression.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/expressions/CmDsExpression.kt @@ -1,13 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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:Suppress("DEPRECATION") + package space.kscience.kmath.commons.expressions import org.apache.commons.math3.analysis.differentiation.DerivativeStructure +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.* -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.ExtendedField import space.kscience.kmath.operations.NumbersAddOps @@ -18,7 +20,8 @@ import space.kscience.kmath.operations.NumbersAddOps * @param bindings The map of bindings values. All bindings are considered free parameters */ @OptIn(UnstableKMathAPI::class) -public class DerivativeStructureField( +@Deprecated("Use generic DSAlgebra from the core") +public class CmDsField( public val order: Int, bindings: Map, ) : ExtendedField, ExpressionAlgebra, @@ -108,25 +111,27 @@ public class DerivativeStructureField( /** * Auto-diff processor based on Commons-math [DerivativeStructure] */ -public object DSProcessor : AutoDiffProcessor { +@Deprecated("Use generic DSAlgebra from the core") +public object CmDsProcessor : AutoDiffProcessor { override fun differentiate( - function: DerivativeStructureField.() -> DerivativeStructure, - ): DerivativeStructureExpression = DerivativeStructureExpression(function) + function: CmDsField.() -> DerivativeStructure, + ): CmDsExpression = CmDsExpression(function) } /** * A constructs that creates a derivative structure with required order on-demand */ -public class DerivativeStructureExpression( - public val function: DerivativeStructureField.() -> DerivativeStructure, +@Deprecated("Use generic DSAlgebra from the core") +public class CmDsExpression( + public val function: CmDsField.() -> DerivativeStructure, ) : DifferentiableExpression { override operator fun invoke(arguments: Map): Double = - DerivativeStructureField(0, arguments).function().value + CmDsField(0, arguments).function().value /** * Get the derivative expression with given orders */ override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> - with(DerivativeStructureField(symbols.size, arguments)) { function().derivative(symbols) } + with(CmDsField(symbols.size, arguments)) { function().derivative(symbols) } } } diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMGaussRuleIntegrator.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMGaussRuleIntegrator.kt index e0a2f4931..263463d37 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMGaussRuleIntegrator.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMGaussRuleIntegrator.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.commons.integration diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMIntegrator.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMIntegrator.kt index 257429fa7..c3e581d31 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMIntegrator.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/integration/CMIntegrator.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,8 +7,8 @@ package space.kscience.kmath.commons.integration import org.apache.commons.math3.analysis.integration.IterativeLegendreGaussIntegrator import org.apache.commons.math3.analysis.integration.SimpsonIntegrator +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.integration.* -import space.kscience.kmath.misc.UnstableKMathAPI /** * Integration wrapper for Common-maths UnivariateIntegrator diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMMatrix.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMMatrix.kt index aa7e0a638..d19bd1be0 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMMatrix.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMMatrix.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.commons.linear import org.apache.commons.math3.linear.* +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.* -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.StructureFeature import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.structures.Buffer diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMSolver.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMSolver.kt index 9bb5deffd..19799aab3 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMSolver.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/linear/CMSolver.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/optimization/CMOptimizer.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/optimization/CMOptimizer.kt index 11eb6fba8..c4dafb6a6 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/optimization/CMOptimizer.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/optimization/CMOptimizer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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) @@ -13,11 +13,11 @@ import org.apache.commons.math3.optim.nonlinear.scalar.ObjectiveFunctionGradient import org.apache.commons.math3.optim.nonlinear.scalar.gradient.NonLinearConjugateGradientOptimizer import org.apache.commons.math3.optim.nonlinear.scalar.noderiv.NelderMeadSimplex import org.apache.commons.math3.optim.nonlinear.scalar.noderiv.SimplexOptimizer +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol import space.kscience.kmath.expressions.SymbolIndexer import space.kscience.kmath.expressions.derivative import space.kscience.kmath.expressions.withSymbols -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.misc.log import space.kscience.kmath.optimization.* import kotlin.collections.set diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/random/CMRandomGeneratorWrapper.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/random/CMRandomGeneratorWrapper.kt index 194be6002..32962659f 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/random/CMRandomGeneratorWrapper.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/random/CMRandomGeneratorWrapper.kt @@ -1,17 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.commons.random import kotlinx.coroutines.runBlocking -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.samplers.GaussianSampler import space.kscience.kmath.misc.toIntExact -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.samplers.GaussianSampler import space.kscience.kmath.stat.next + public class CMRandomGeneratorWrapper( public val factory: (IntArray) -> RandomGenerator, ) : org.apache.commons.math3.random.RandomGenerator { diff --git a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/transform/Transformations.kt b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/transform/Transformations.kt index 40168971e..a77da2d2f 100644 --- a/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/transform/Transformations.kt +++ b/kmath-commons/src/main/kotlin/space/kscience/kmath/commons/transform/Transformations.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,28 +10,18 @@ import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.map import org.apache.commons.math3.transform.* import space.kscience.kmath.complex.Complex -import space.kscience.kmath.operations.SuspendBufferTransform +import space.kscience.kmath.operations.BufferTransform import space.kscience.kmath.streaming.chunked import space.kscience.kmath.streaming.spread -import space.kscience.kmath.structures.Buffer -import space.kscience.kmath.structures.DoubleBuffer -import space.kscience.kmath.structures.VirtualBuffer -import space.kscience.kmath.structures.asBuffer - +import space.kscience.kmath.structures.* /** - * Streaming and buffer transformations + * Streaming and buffer transformations with Commons-math algorithms */ public object Transformations { - private fun Buffer.toArray(): Array = + private fun Buffer.toCmComplexArray(): Array = Array(size) { org.apache.commons.math3.complex.Complex(get(it).re, get(it).im) } - private fun Buffer.asArray() = if (this is DoubleBuffer) { - array - } else { - DoubleArray(size) { i -> get(i) } - } - /** * Create a virtual buffer on top of array */ @@ -43,70 +33,67 @@ public object Transformations { public fun fourier( normalization: DftNormalization = DftNormalization.STANDARD, direction: TransformType = TransformType.FORWARD, - ): SuspendBufferTransform = { - FastFourierTransformer(normalization).transform(it.toArray(), direction).asBuffer() + ): BufferTransform = BufferTransform { + FastFourierTransformer(normalization).transform(it.toCmComplexArray(), direction).asBuffer() } public fun realFourier( normalization: DftNormalization = DftNormalization.STANDARD, direction: TransformType = TransformType.FORWARD, - ): SuspendBufferTransform = { - FastFourierTransformer(normalization).transform(it.asArray(), direction).asBuffer() + ): BufferTransform = BufferTransform { + FastFourierTransformer(normalization).transform(it.toDoubleArray(), direction).asBuffer() } public fun sine( normalization: DstNormalization = DstNormalization.STANDARD_DST_I, direction: TransformType = TransformType.FORWARD, - ): SuspendBufferTransform = { - FastSineTransformer(normalization).transform(it.asArray(), direction).asBuffer() + ): BufferTransform = DoubleBufferTransform { + FastSineTransformer(normalization).transform(it.array, direction).asBuffer() } public fun cosine( normalization: DctNormalization = DctNormalization.STANDARD_DCT_I, direction: TransformType = TransformType.FORWARD, - ): SuspendBufferTransform = { - FastCosineTransformer(normalization).transform(it.asArray(), direction).asBuffer() + ): BufferTransform = BufferTransform { + FastCosineTransformer(normalization).transform(it.toDoubleArray(), direction).asBuffer() } public fun hadamard( direction: TransformType = TransformType.FORWARD, - ): SuspendBufferTransform = { - FastHadamardTransformer().transform(it.asArray(), direction).asBuffer() + ): BufferTransform = DoubleBufferTransform { + FastHadamardTransformer().transform(it.array, direction).asBuffer() } } /** * Process given [Flow] with commons-math fft transformation */ -@FlowPreview -public fun Flow>.FFT( +public fun Flow>.fft( normalization: DftNormalization = DftNormalization.STANDARD, direction: TransformType = TransformType.FORWARD, ): Flow> { val transform = Transformations.fourier(normalization, direction) - return map { transform(it) } + return map(transform::transform) } -@FlowPreview @JvmName("realFFT") -public fun Flow>.FFT( +public fun Flow>.fft( normalization: DftNormalization = DftNormalization.STANDARD, direction: TransformType = TransformType.FORWARD, ): Flow> { val transform = Transformations.realFourier(normalization, direction) - return map(transform) + return map(transform::transform) } /** * Process a continuous flow of real numbers in FFT splitting it in chunks of [bufferSize]. */ -@FlowPreview @JvmName("realFFT") -public fun Flow.FFT( +public fun Flow.fft( bufferSize: Int = Int.MAX_VALUE, normalization: DftNormalization = DftNormalization.STANDARD, direction: TransformType = TransformType.FORWARD, -): Flow = chunked(bufferSize).FFT(normalization, direction).spread() +): Flow = chunked(bufferSize).fft(normalization, direction).spread() /** * Map a complex flow into real flow by taking real part of each number diff --git a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpressionTest.kt b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpressionTest.kt index 56252ab34..7c3c086ed 100644 --- a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpressionTest.kt +++ b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/expressions/DerivativeStructureExpressionTest.kt @@ -1,8 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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:Suppress("DEPRECATION") + package space.kscience.kmath.commons.expressions import space.kscience.kmath.expressions.* @@ -15,10 +17,10 @@ import kotlin.test.assertFails internal inline fun diff( order: Int, vararg parameters: Pair, - block: DerivativeStructureField.() -> Unit, + block: CmDsField.() -> Unit, ) { contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - DerivativeStructureField(order, mapOf(*parameters)).run(block) + CmDsField(order, mapOf(*parameters)).run(block) } internal class AutoDiffTest { @@ -41,7 +43,7 @@ internal class AutoDiffTest { @Test fun autoDifTest() { - val f = DerivativeStructureExpression { + val f = CmDsExpression { val x by binding val y by binding x.pow(2) + 2 * x * y + y.pow(2) + 1 diff --git a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/integration/IntegrationTest.kt b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/integration/IntegrationTest.kt index c5573fef1..6541736ce 100644 --- a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/integration/IntegrationTest.kt +++ b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/integration/IntegrationTest.kt @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.commons.integration import org.junit.jupiter.api.Test +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.integration.integrate import space.kscience.kmath.integration.value -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField.sin import kotlin.math.PI import kotlin.math.abs diff --git a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/optimization/OptimizeTest.kt b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/optimization/OptimizeTest.kt index 0977dc247..d2e86bb40 100644 --- a/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/optimization/OptimizeTest.kt +++ b/kmath-commons/src/test/kotlin/space/kscience/kmath/commons/optimization/OptimizeTest.kt @@ -1,28 +1,30 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.commons.optimization import kotlinx.coroutines.runBlocking -import space.kscience.kmath.commons.expressions.DSProcessor -import space.kscience.kmath.commons.expressions.DerivativeStructureExpression +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.distributions.NormalDistribution +import space.kscience.kmath.expressions.DSFieldExpression import space.kscience.kmath.expressions.Symbol.Companion.x import space.kscience.kmath.expressions.Symbol.Companion.y -import space.kscience.kmath.expressions.chiSquaredExpression +import space.kscience.kmath.expressions.autodiff import space.kscience.kmath.expressions.symbol -import space.kscience.kmath.operations.map +import space.kscience.kmath.operations.DoubleBufferOps.Companion.map +import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.optimization.* -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.stat.chiSquaredExpression import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.asBuffer -import kotlin.math.pow import kotlin.test.Test +@OptIn(UnstableKMathAPI::class) internal class OptimizeTest { - val normal = DerivativeStructureExpression { + val normal = DSFieldExpression(DoubleField) { exp(-bindSymbol(x).pow(2) / 2) + exp(-bindSymbol(y).pow(2) / 2) } @@ -61,7 +63,7 @@ internal class OptimizeTest { val yErr = DoubleBuffer(x.size) { sigma } - val chi2 = DSProcessor.chiSquaredExpression( + val chi2 = Double.autodiff.chiSquaredExpression( x, y, yErr ) { arg -> val cWithDefault = bindSymbolOrNull(c) ?: one diff --git a/kmath-complex/README.md b/kmath-complex/README.md index f00952065..4e800b7ac 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-complex:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -18,7 +18,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-complex:0.3.1-dev-1' + implementation 'space.kscience:kmath-complex:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-complex:0.3.1-dev-1") + implementation("space.kscience:kmath-complex:0.4.0-dev-1") } ``` diff --git a/kmath-complex/build.gradle.kts b/kmath-complex/build.gradle.kts index f0ce631a5..2f8c320cf 100644 --- a/kmath-complex/build.gradle.kts +++ b/kmath-complex/build.gradle.kts @@ -1,33 +1,39 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets { - commonMain { - dependencies { - api(project(":kmath-core")) - } +kscience { + jvm() + js() + native() + + wasm() + + dependencies { + api(projects.kmathCore) + } + + testDependencies { + implementation(projects.testUtils) } } readme { description = "Complex numbers and quaternions." - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( id = "complex", ref = "src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt" - ){ + ) { "Complex numbers operations" } feature( id = "quaternion", 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/Complex.kt b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt index f56fb0f6e..b5f1aabe7 100644 --- a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt +++ b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/Complex.kt @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.complex +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.memory.MemoryReader import space.kscience.kmath.memory.MemorySpec import space.kscience.kmath.memory.MemoryWriter -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.* import kotlin.math.* @@ -80,6 +80,8 @@ public object ComplexField : override fun add(left: Complex, right: Complex): Complex = Complex(left.re + right.re, left.im + right.im) // override fun multiply(a: Complex, k: Number): Complex = Complex(a.re * k.toDouble(), a.im * k.toDouble()) +// override fun Complex.minus(arg: Complex): Complex = Complex(re - arg.re, im - arg.im) + override fun multiply(left: Complex, right: Complex): Complex = Complex(left.re * right.re - left.im * right.im, left.re * right.im + left.im * right.re) @@ -193,7 +195,6 @@ public object ComplexField : * @property re The real part. * @property im The imaginary part. */ -@OptIn(UnstableKMathAPI::class) public data class Complex(val re: Double, val im: Double) { public constructor(re: Number, im: Number) : this(re.toDouble(), im.toDouble()) public constructor(re: Number) : this(re.toDouble(), 0.0) diff --git a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/ComplexFieldND.kt b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/ComplexFieldND.kt index 65943f421..90a6b3253 100644 --- a/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/ComplexFieldND.kt +++ b/kmath-complex/src/commonMain/kotlin/space/kscience/kmath/complex/ComplexFieldND.kt @@ -1,11 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.complex -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.* import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer @@ -20,6 +21,7 @@ import kotlin.contracts.contract public sealed class ComplexFieldOpsND : BufferedFieldOpsND(ComplexField.bufferAlgebra), ScaleOperations>, ExtendedFieldOps>, PowerOperations> { + @OptIn(PerformancePitfall::class) override fun StructureND.toBufferND(): BufferND = when (this) { is BufferND -> this else -> { @@ -57,7 +59,7 @@ public sealed class ComplexFieldOpsND : BufferedFieldOpsND, NumbersAddOps> { @@ -69,12 +71,12 @@ public class ComplexFieldND(override val shape: Shape) : public val ComplexField.ndAlgebra: ComplexFieldOpsND get() = ComplexFieldOpsND -public fun ComplexField.ndAlgebra(vararg shape: Int): ComplexFieldND = ComplexFieldND(shape) +public fun ComplexField.ndAlgebra(vararg shape: Int): ComplexFieldND = ComplexFieldND(ShapeND(shape)) /** * Produce a context for n-dimensional operations inside this real field */ public inline fun ComplexField.withNdAlgebra(vararg shape: Int, action: ComplexFieldND.() -> R): R { contract { callsInPlace(action, InvocationKind.EXACTLY_ONCE) } - return ComplexFieldND(shape).action() + return ComplexFieldND(ShapeND(shape)).action() } 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 0305bfc88..d4259c4dc 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 @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.complex +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.memory.MemoryReader import space.kscience.kmath.memory.MemorySpec import space.kscience.kmath.memory.MemoryWriter -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.MemoryBuffer @@ -117,6 +117,11 @@ public val Quaternion.reciprocal: Quaternion return Quaternion(w / norm2, -x / norm2, -y / norm2, -z / norm2) } + +//TODO consider adding a-priory normalized quaternions +/** + * Produce a normalized version of this quaternion + */ public fun Quaternion.normalized(): Quaternion = with(QuaternionField){ this@normalized / norm(this@normalized) } /** diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexBufferSpecTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexBufferSpecTest.kt index 17a077ea7..ca3f8f43f 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexBufferSpecTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexBufferSpecTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexFieldTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexFieldTest.kt index cbaaa815b..e11f1c1ea 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexFieldTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexFieldTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexTest.kt index 7ad7f883d..1a35d1dd8 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ComplexTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ExpressionFieldForComplexTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ExpressionFieldForComplexTest.kt index 4279471d4..767406e0b 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ExpressionFieldForComplexTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/ExpressionFieldForComplexTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt index fd4df736c..fd0fd46a7 100644 --- a/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt +++ b/kmath-complex/src/commonTest/kotlin/space/kscience/kmath/complex/QuaternionTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/README.md b/kmath-core/README.md index e84ca38d7..b58105d2f 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-core:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -25,7 +25,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-core:0.3.1-dev-1' + implementation 'space.kscience:kmath-core:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -36,6 +36,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-core:0.3.1-dev-1") + implementation("space.kscience:kmath-core:0.4.0-dev-1") } ``` diff --git a/kmath-core/api/kmath-core.api b/kmath-core/api/kmath-core.api index 737d33f1c..42d8277bd 100644 --- a/kmath-core/api/kmath-core.api +++ b/kmath-core/api/kmath-core.api @@ -1,12 +1,10 @@ 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 { @@ -19,7 +17,6 @@ public abstract interface class space/kscience/kmath/domains/Domain { } 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 { @@ -31,6 +28,19 @@ public class space/kscience/kmath/expressions/AutoDiffValue { public final fun getValue ()Ljava/lang/Object; } +public final class space/kscience/kmath/expressions/DSAlgebraKt { +} + +public final class space/kscience/kmath/expressions/DSCompiler { + public final fun getAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public final fun getFreeParameters ()I + public final fun getOrder ()I + public final fun getPartialDerivativeIndex ([I)I + public final fun getPartialDerivativeOrders (I)[I + public final fun getSize ()I + public final fun getSizes ()[[I +} + public final class space/kscience/kmath/expressions/DerivationResult { public fun (Ljava/lang/Object;Ljava/util/Map;Lspace/kscience/kmath/operations/Field;)V public final fun derivative (Lspace/kscience/kmath/expressions/Symbol;)Ljava/lang/Object; @@ -39,6 +49,12 @@ public final class space/kscience/kmath/expressions/DerivationResult { public final fun getValue ()Ljava/lang/Object; } +public final class space/kscience/kmath/expressions/DiffExpressionWithDefault : space/kscience/kmath/expressions/DifferentiableExpression { + public fun (Lspace/kscience/kmath/expressions/DifferentiableExpression;Ljava/util/Map;)V + public fun derivativeOrNull (Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; + public fun invoke (Ljava/util/Map;)Ljava/lang/Object; +} + public abstract interface class space/kscience/kmath/expressions/DifferentiableExpression : space/kscience/kmath/expressions/Expression { public abstract fun derivativeOrNull (Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; } @@ -52,6 +68,9 @@ public final class space/kscience/kmath/expressions/DifferentiableExpressionKt { public static final fun derivative (Lspace/kscience/kmath/expressions/SpecialDifferentiableExpression;[Lspace/kscience/kmath/expressions/Symbol;)Lspace/kscience/kmath/expressions/Expression; } +public final class space/kscience/kmath/expressions/DoubleExpression$Companion { +} + public abstract interface class space/kscience/kmath/expressions/Expression { public abstract fun invoke (Ljava/util/Map;)Ljava/lang/Object; } @@ -67,6 +86,16 @@ public final class space/kscience/kmath/expressions/ExpressionKt { public static final fun invoke (Lspace/kscience/kmath/expressions/Expression;)Ljava/lang/Object; } +public final class space/kscience/kmath/expressions/ExpressionWithDefault : space/kscience/kmath/expressions/Expression { + public fun (Lspace/kscience/kmath/expressions/Expression;Ljava/util/Map;)V + public fun invoke (Ljava/util/Map;)Ljava/lang/Object; +} + +public final class space/kscience/kmath/expressions/ExpressionWithDefaultKt { + public static final fun withDefaultArgs (Lspace/kscience/kmath/expressions/DifferentiableExpression;Ljava/util/Map;)Lspace/kscience/kmath/expressions/DiffExpressionWithDefault; + public static final fun withDefaultArgs (Lspace/kscience/kmath/expressions/Expression;Ljava/util/Map;)Lspace/kscience/kmath/expressions/ExpressionWithDefault; +} + public abstract class space/kscience/kmath/expressions/FirstDerivativeExpression : space/kscience/kmath/expressions/DifferentiableExpression { public fun ()V public final fun derivativeOrNull (Ljava/util/List;)Lspace/kscience/kmath/expressions/Expression; @@ -160,6 +189,12 @@ public class space/kscience/kmath/expressions/FunctionalExpressionRing : space/k public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } +public final class space/kscience/kmath/expressions/IntExpression$Companion { +} + +public final class space/kscience/kmath/expressions/LongExpression$Companion { +} + public abstract interface class space/kscience/kmath/expressions/MST { } @@ -356,6 +391,35 @@ public final class space/kscience/kmath/expressions/MstRing : space/kscience/kma public fun unaryPlus (Lspace/kscience/kmath/expressions/MST;)Lspace/kscience/kmath/expressions/MST$Unary; } +public final class space/kscience/kmath/expressions/NamedMatrix : space/kscience/kmath/nd/Structure2D { + public static final field Companion Lspace/kscience/kmath/expressions/NamedMatrix$Companion; + public fun (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/expressions/SymbolIndexer;)V + public fun elements ()Lkotlin/sequences/Sequence; + public fun get (II)Ljava/lang/Object; + public final fun get (Lspace/kscience/kmath/expressions/Symbol;Lspace/kscience/kmath/expressions/Symbol;)Ljava/lang/Object; + public fun get ([I)Ljava/lang/Object; + public fun getColNum ()I + public fun getColumns ()Ljava/util/List; + 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 final fun getIndexer ()Lspace/kscience/kmath/expressions/SymbolIndexer; + public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; + public fun getRowNum ()I + public fun getRows ()Ljava/util/List; + public fun getShape-IIYLAfE ()[I + public final fun getValues ()Lspace/kscience/kmath/nd/Structure2D; +} + +public final class space/kscience/kmath/expressions/NamedMatrix$Companion { + public final fun toStringWithSymbols (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/expressions/SymbolIndexer;)Ljava/lang/String; +} + +public final class space/kscience/kmath/expressions/NamedMatrixKt { + public static final fun named (Lspace/kscience/kmath/nd/Structure2D;Ljava/util/List;)Lspace/kscience/kmath/expressions/NamedMatrix; + public static final fun named (Lspace/kscience/kmath/nd/Structure2D;Lspace/kscience/kmath/expressions/SymbolIndexer;)Lspace/kscience/kmath/expressions/NamedMatrix; +} + public final class space/kscience/kmath/expressions/SimpleAutoDiffExpression : space/kscience/kmath/expressions/FirstDerivativeExpression { public fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function1;)V public fun derivativeOrNull (Lspace/kscience/kmath/expressions/Symbol;)Lspace/kscience/kmath/expressions/Expression; @@ -465,11 +529,6 @@ public abstract interface class space/kscience/kmath/expressions/SpecialDifferen 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 { public static final field Companion Lspace/kscience/kmath/expressions/Symbol$Companion; public abstract fun getIdentity ()Ljava/lang/String; @@ -510,7 +569,7 @@ public final class space/kscience/kmath/linear/BufferedLinearSpace : space/kscie } 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 static final fun getLinearSpace (Lspace/kscience/kmath/operations/Ring;)Lspace/kscience/kmath/linear/BufferedLinearSpace; } public abstract interface class space/kscience/kmath/linear/CholeskyDecompositionFeature : space/kscience/kmath/linear/MatrixFeature { @@ -597,9 +656,7 @@ 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 getDouble ()Lspace/kscience/kmath/linear/LinearSpace; + public final fun buffered (Lspace/kscience/kmath/operations/Ring;)Lspace/kscience/kmath/linear/LinearSpace; } public final class space/kscience/kmath/linear/LinearSpaceKt { @@ -628,11 +685,11 @@ 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 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;D)Lspace/kscience/kmath/linear/LupDecomposition; + public static final fun lup (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/structures/MutableBufferFactory;Lspace/kscience/kmath/nd/Structure2D;Lkotlin/jvm/functions/Function1;)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 final fun lupSolver (Lspace/kscience/kmath/linear/LinearSpace;Lspace/kscience/kmath/structures/MutableBufferFactory;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; } @@ -673,12 +730,11 @@ public final class space/kscience/kmath/linear/MatrixWrapper : space/kscience/km public final fun getOrigin ()Lspace/kscience/kmath/nd/Structure2D; public fun getRowNum ()I public fun getRows ()Ljava/util/List; - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I public fun toString ()Ljava/lang/String; } 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;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; @@ -726,7 +782,7 @@ public final class space/kscience/kmath/linear/VirtualMatrix : space/kscience/km public fun getColNum ()I public final fun getGenerator ()Lkotlin/jvm/functions/Function2; public fun getRowNum ()I - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I } public final class space/kscience/kmath/linear/VirtualMatrixKt { @@ -737,6 +793,11 @@ public final class space/kscience/kmath/linear/ZeroFeature : space/kscience/kmat public static final field INSTANCE Lspace/kscience/kmath/linear/ZeroFeature; } +public final class space/kscience/kmath/misc/CollectionsKt { + public static final fun zipWithNextCircular (Ljava/util/List;)Ljava/util/List; + public static final fun zipWithNextCircular (Ljava/util/List;Lkotlin/jvm/functions/Function2;)Ljava/util/List; +} + public final class space/kscience/kmath/misc/CumulativeKt { public static final fun cumulative (Ljava/lang/Iterable;Ljava/lang/Object;Lkotlin/jvm/functions/Function2;)Ljava/lang/Iterable; public static final fun cumulative (Ljava/util/Iterator;Ljava/lang/Object;Lkotlin/jvm/functions/Function2;)Ljava/util/Iterator; @@ -745,6 +806,7 @@ public final class space/kscience/kmath/misc/CumulativeKt { public static final fun cumulativeSum (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Ring;)Ljava/lang/Iterable; public static final fun cumulativeSum (Ljava/util/List;Lspace/kscience/kmath/operations/Ring;)Ljava/util/List; public static final fun cumulativeSum (Lkotlin/sequences/Sequence;Lspace/kscience/kmath/operations/Ring;)Lkotlin/sequences/Sequence; + public static final fun cumulativeSum (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/operations/Ring;)Lspace/kscience/kmath/structures/Buffer; public static final fun cumulativeSumOfDouble (Ljava/lang/Iterable;)Ljava/lang/Iterable; public static final fun cumulativeSumOfDouble (Ljava/util/List;)Ljava/util/List; public static final fun cumulativeSumOfDouble (Lkotlin/sequences/Sequence;)Lkotlin/sequences/Sequence; @@ -811,10 +873,6 @@ 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; @@ -823,16 +881,13 @@ public final class space/kscience/kmath/misc/SortingKt { 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 : space/kscience/kmath/operations/Algebra { public static final field Companion Lspace/kscience/kmath/nd/AlgebraND$Companion; 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 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 abstract fun structureND-qL90JFI ([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; } @@ -840,17 +895,13 @@ 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 one-waz_sdI (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 zero-waz_sdI (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 static final field Companion Lspace/kscience/kmath/nd/BufferAlgebraND$Companion; public abstract fun getBufferAlgebra ()Lspace/kscience/kmath/operations/BufferAlgebra; @@ -860,8 +911,8 @@ public abstract interface class space/kscience/kmath/nd/BufferAlgebraND : space/ 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 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 structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public synthetic fun structureND-qL90JFI ([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; @@ -885,19 +936,22 @@ public class space/kscience/kmath/nd/BufferND : space/kscience/kmath/nd/Structur public fun get ([I)Ljava/lang/Object; public fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I public fun toString ()Ljava/lang/String; } 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 static final fun BufferND-bYNkpeI ([ILspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; + public static synthetic fun BufferND-bYNkpeI$default ([ILspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/BufferND; + public static final fun MutableBufferND-bYNkpeI ([ILspace/kscience/kmath/structures/MutableBufferFactory;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/MutableBufferND; + public static synthetic fun MutableBufferND-bYNkpeI$default ([ILspace/kscience/kmath/structures/MutableBufferFactory;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/MutableBufferND; } 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 fun (Lspace/kscience/kmath/operations/Field;Lkotlin/jvm/functions/Function1;)V + public synthetic fun (Lspace/kscience/kmath/operations/Field;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; } @@ -916,29 +970,30 @@ public class space/kscience/kmath/nd/BufferedRingOpsND : space/kscience/kmath/nd 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 { - public static final field Companion Lspace/kscience/kmath/nd/DefaultStrides$Companion; +public final class space/kscience/kmath/nd/ColumnStrides : space/kscience/kmath/nd/Strides { + public static final field Companion Lspace/kscience/kmath/nd/ColumnStrides$Companion; public synthetic fun ([ILkotlin/jvm/internal/DefaultConstructorMarker;)V public fun equals (Ljava/lang/Object;)Z public fun getLinearSize ()I - public fun getShape ()[I - public fun getStrides ()[I + public fun getShape-IIYLAfE ()[I public fun hashCode ()I public fun index (I)[I } -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/ColumnStrides$Companion { } -public final class space/kscience/kmath/nd/DoubleBufferND : space/kscience/kmath/nd/BufferND { +public final class space/kscience/kmath/nd/DoubleBufferND : space/kscience/kmath/nd/MutableBufferND, space/kscience/kmath/nd/MutableStructureNDOfDouble { public synthetic fun (Lspace/kscience/kmath/nd/ShapeIndexer;[DLkotlin/jvm/internal/DefaultConstructorMarker;)V public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/MutableBuffer; public fun getBuffer-Dv3HvWU ()[D + public fun getDouble ([I)D + public fun setDouble ([ID)V } 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 ([ILkotlin/jvm/internal/DefaultConstructorMarker;)V 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 asinh (Ljava/lang/Object;)Ljava/lang/Object; @@ -947,13 +1002,14 @@ public final class space/kscience/kmath/nd/DoubleFieldND : space/kscience/kmath/ 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/DoubleBufferND; - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; 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;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 (Lspace/kscience/kmath/nd/StructureND;Ljava/lang/Number;)Lspace/kscience/kmath/nd/StructureND; 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; @@ -965,6 +1021,7 @@ public final class space/kscience/kmath/nd/DoubleFieldND : space/kscience/kmath/ public final class space/kscience/kmath/nd/DoubleFieldNDKt { 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 static final fun ndAlgebra-waz_sdI (Lspace/kscience/kmath/operations/DoubleField;[I)Lspace/kscience/kmath/nd/DoubleFieldND; } public abstract class space/kscience/kmath/nd/DoubleFieldOpsND : space/kscience/kmath/nd/BufferedFieldOpsND, space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/ScaleOperations { @@ -1021,6 +1078,8 @@ public abstract class space/kscience/kmath/nd/DoubleFieldOpsND : space/kscience/ 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 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/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/DoubleBufferND; public synthetic fun scale (Lspace/kscience/kmath/nd/StructureND;D)Lspace/kscience/kmath/nd/StructureND; @@ -1028,9 +1087,9 @@ public abstract class space/kscience/kmath/nd/DoubleFieldOpsND : space/kscience/ 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 structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public fun structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/DoubleBufferND; + public synthetic fun structureND-qL90JFI ([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; @@ -1087,7 +1146,41 @@ public abstract interface class space/kscience/kmath/nd/GroupOpsND : space/kscie 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 final class space/kscience/kmath/nd/IndexOutOfShapeException : java/lang/RuntimeException { + public synthetic fun ([I[ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public final fun getIndex ()[I + public final fun getShape-IIYLAfE ()[I +} + +public final class space/kscience/kmath/nd/IntBufferND : space/kscience/kmath/nd/MutableBufferND { + public synthetic fun (Lspace/kscience/kmath/nd/ShapeIndexer;[ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/Buffer; + public synthetic fun getBuffer ()Lspace/kscience/kmath/structures/MutableBuffer; + public fun getBuffer-ir4F4A8 ()[I +} + +public final class space/kscience/kmath/nd/IntRingND : space/kscience/kmath/nd/IntRingOpsND, space/kscience/kmath/nd/RingND, space/kscience/kmath/operations/NumbersAddOps { + public synthetic fun ([ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun getShape-IIYLAfE ()[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/IntRingNDKt { + public static final fun withNdAlgebra (Lspace/kscience/kmath/operations/IntRing;[ILkotlin/jvm/functions/Function1;)Ljava/lang/Object; +} + +public abstract class space/kscience/kmath/nd/IntRingOpsND : space/kscience/kmath/nd/BufferedRingOpsND { + public static final field Companion Lspace/kscience/kmath/nd/IntRingOpsND$Companion; + public synthetic fun structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/BufferND; + public fun structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/IntBufferND; + public synthetic fun structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; +} + +public final class space/kscience/kmath/nd/IntRingOpsND$Companion : space/kscience/kmath/nd/IntRingOpsND { +} + +public class space/kscience/kmath/nd/MutableBufferND : space/kscience/kmath/nd/BufferND, space/kscience/kmath/nd/MutableStructureND { 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; @@ -1108,6 +1201,46 @@ 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/MutableStructureNDOfDouble : space/kscience/kmath/nd/MutableStructureND, space/kscience/kmath/nd/StructureNDOfDouble { + public abstract fun setDouble ([ID)V +} + +public final class space/kscience/kmath/nd/OperationsNDKt { + public static final fun roll (Lspace/kscience/kmath/nd/StructureND;II)Lspace/kscience/kmath/nd/StructureND; + public static final fun roll (Lspace/kscience/kmath/nd/StructureND;Lkotlin/Pair;[Lkotlin/Pair;)Lspace/kscience/kmath/nd/StructureND; + public static synthetic fun roll$default (Lspace/kscience/kmath/nd/StructureND;IIILjava/lang/Object;)Lspace/kscience/kmath/nd/StructureND; +} + +public final class space/kscience/kmath/nd/PermutedMutableStructureND : space/kscience/kmath/nd/MutableStructureND { + public synthetic fun (Lspace/kscience/kmath/nd/MutableStructureND;[ILkotlin/jvm/functions/Function1;ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public synthetic fun (Lspace/kscience/kmath/nd/MutableStructureND;[ILkotlin/jvm/functions/Function1;Lkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun get ([I)Ljava/lang/Object; + public final fun getOrigin ()Lspace/kscience/kmath/nd/MutableStructureND; + public final fun getPermutation ()Lkotlin/jvm/functions/Function1; + public fun getShape-IIYLAfE ()[I + public fun set ([ILjava/lang/Object;)V +} + +public final class space/kscience/kmath/nd/PermutedStructureND : space/kscience/kmath/nd/StructureND { + public fun (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function1;)V + public fun get ([I)Ljava/lang/Object; + public final fun getOrigin ()Lspace/kscience/kmath/nd/StructureND; + public final fun getPermutation ()Lkotlin/jvm/functions/Function1; + public fun getShape-IIYLAfE ()[I +} + +public final class space/kscience/kmath/nd/PermutedStructureNDKt { + public static final fun permute (Lspace/kscience/kmath/nd/StructureND;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/PermutedStructureND; + public static final fun permute-_A0By-k (Lspace/kscience/kmath/nd/MutableStructureND;[ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/PermutedMutableStructureND; + public static synthetic fun permute-_A0By-k$default (Lspace/kscience/kmath/nd/MutableStructureND;[ILkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/PermutedMutableStructureND; +} + +public final class space/kscience/kmath/nd/PrimitiveStructureNDKt { + public static final fun getDouble (Lspace/kscience/kmath/nd/MutableStructureND;[I)D + public static final fun getDouble (Lspace/kscience/kmath/nd/StructureND;[I)D + public static final fun getInt (Lspace/kscience/kmath/nd/StructureND;[I)I +} + 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; @@ -1124,26 +1257,84 @@ public abstract interface class space/kscience/kmath/nd/RingOpsND : space/kscien public final class space/kscience/kmath/nd/RingOpsND$Companion { } +public final class space/kscience/kmath/nd/RowStrides : space/kscience/kmath/nd/Strides { + public static final field Companion Lspace/kscience/kmath/nd/RowStrides$Companion; + public synthetic fun ([ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun equals (Ljava/lang/Object;)Z + public fun getLinearSize ()I + public fun getShape-IIYLAfE ()[I + public fun hashCode ()I + public fun index (I)[I +} + +public final class space/kscience/kmath/nd/RowStrides$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 getShape-IIYLAfE ()[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/ShapeIndicesKt { + public static final fun Strides-dNlrn20 ([I)Lspace/kscience/kmath/nd/Strides; +} + public final class space/kscience/kmath/nd/ShapeMismatchException : java/lang/RuntimeException { - public fun ([I[I)V - public final fun getActual ()[I - public final fun getExpected ()[I + public synthetic fun ([I[ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public final fun getActual-IIYLAfE ()[I + public final fun getExpected-IIYLAfE ()[I +} + +public final class space/kscience/kmath/nd/ShapeND { + public static final synthetic fun box-impl ([I)Lspace/kscience/kmath/nd/ShapeND; + public static fun constructor-impl ([I)[I + public fun equals (Ljava/lang/Object;)Z + public static fun equals-impl ([ILjava/lang/Object;)Z + public static final fun equals-impl0 ([I[I)Z + public static final fun get-impl ([II)I + public static final fun getSize-impl ([I)I + public fun hashCode ()I + public static fun hashCode-impl ([I)I + public fun toString ()Ljava/lang/String; + public static fun toString-impl ([I)Ljava/lang/String; + public final synthetic fun unbox-impl ()[I +} + +public final class space/kscience/kmath/nd/ShapeNDKt { + public static final fun ShapeND (I[I)[I + public static final fun asArray-dNlrn20 ([I)[I + public static final fun asList-dNlrn20 ([I)Ljava/util/List; + public static final fun component1-dNlrn20 ([I)I + public static final fun component2-dNlrn20 ([I)I + public static final fun component3-dNlrn20 ([I)I + public static final fun contentEquals-9Nqdy04 ([I[I)Z + public static final fun contentHashCode-dNlrn20 ([I)I + public static final fun first-dNlrn20 ([I)I + public static final fun first-qL90JFI ([II)[I + public static final fun forEach-qL90JFI ([ILkotlin/jvm/functions/Function1;)V + public static final fun forEachIndexed-qL90JFI ([ILkotlin/jvm/functions/Function2;)V + public static final fun getIndices-dNlrn20 ([I)Lkotlin/ranges/IntRange; + public static final fun getLinearSize-dNlrn20 ([I)I + public static final fun isEmpty-dNlrn20 ([I)Z + public static final fun isNotEmpty-dNlrn20 ([I)Z + public static final fun last-dNlrn20 ([I)I + public static final fun last-qL90JFI ([II)[I + public static final fun plus-9Nqdy04 ([I[I)[I + public static final fun plus-qL90JFI ([I[I)[I + public static final fun slice-qL90JFI ([ILkotlin/ranges/IntRange;)[I + public static final fun toArray-dNlrn20 ([I)[I + public static final fun transposed-bYNkpeI ([III)[I } 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 fun getShape ()[I + public synthetic fun ([ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun getShape-IIYLAfE ()[I public synthetic fun number (Ljava/lang/Number;)Ljava/lang/Object; public fun number (Ljava/lang/Number;)Lspace/kscience/kmath/nd/BufferND; } @@ -1162,7 +1353,6 @@ public final class space/kscience/kmath/nd/ShortRingOpsND$Companion : space/ksci 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 fun offset ([I)I } @@ -1191,7 +1381,7 @@ public abstract interface class space/kscience/kmath/nd/Structure2D : space/ksci public fun getColumns ()Ljava/util/List; public abstract fun getRowNum ()I public fun getRows ()Ljava/util/List; - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I } public final class space/kscience/kmath/nd/Structure2D$Companion { @@ -1212,16 +1402,16 @@ public abstract interface class space/kscience/kmath/nd/StructureND : space/ksci 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 + public abstract fun getShape-IIYLAfE ()[I } public final class space/kscience/kmath/nd/StructureND$Companion { public final fun auto (Lkotlin/reflect/KClass;Lspace/kscience/kmath/nd/Strides;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; public final fun auto (Lkotlin/reflect/KClass;[ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; - public final fun buffered (Lspace/kscience/kmath/nd/Strides;Lkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; - public final fun buffered ([ILkotlin/jvm/functions/Function2;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; - 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 buffered (Lspace/kscience/kmath/nd/Strides;Lspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; + public static synthetic fun buffered$default (Lspace/kscience/kmath/nd/StructureND$Companion;Lspace/kscience/kmath/nd/Strides;Lspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lspace/kscience/kmath/nd/BufferND; + public final fun buffered-bYNkpeI ([ILspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/nd/BufferND; + public static synthetic fun buffered-bYNkpeI$default (Lspace/kscience/kmath/nd/StructureND$Companion;[ILspace/kscience/kmath/structures/BufferFactory;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 @@ -1233,13 +1423,30 @@ 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;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)D + public static final fun get (Lspace/kscience/kmath/nd/StructureND;[I)I 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 static final fun set (Lspace/kscience/kmath/nd/MutableStructureND;[ILjava/lang/Object;)V +} + +public abstract interface class space/kscience/kmath/nd/StructureNDOfDouble : space/kscience/kmath/nd/StructureND { + public abstract fun getDouble ([I)D +} + +public abstract interface class space/kscience/kmath/nd/StructureNDOfInt : space/kscience/kmath/nd/StructureND { + public abstract fun getInt ([I)I +} + +public class space/kscience/kmath/nd/VirtualStructureND : space/kscience/kmath/nd/StructureND { + public synthetic fun ([ILkotlin/jvm/functions/Function1;Lkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun get ([I)Ljava/lang/Object; + public final fun getProducer ()Lkotlin/jvm/functions/Function1; + public fun getShape-IIYLAfE ()[I } public abstract interface class space/kscience/kmath/nd/WithShape { public fun getIndices ()Lspace/kscience/kmath/nd/ShapeIndexer; - public abstract fun getShape ()[I + public abstract fun getShape-IIYLAfE ()[I } public abstract interface class space/kscience/kmath/operations/Algebra { @@ -1247,6 +1454,7 @@ public abstract interface class space/kscience/kmath/operations/Algebra { public fun binaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function2; public fun bindSymbol (Ljava/lang/String;)Ljava/lang/Object; public fun bindSymbolOrNull (Ljava/lang/String;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun unaryOperation (Ljava/lang/String;Ljava/lang/Object;)Ljava/lang/Object; public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } @@ -1255,12 +1463,15 @@ public final class space/kscience/kmath/operations/AlgebraExtensionsKt { 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 average (Lspace/kscience/kmath/operations/Group;Lspace/kscience/kmath/structures/Buffer;)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 sum (Lspace/kscience/kmath/operations/Group;Lspace/kscience/kmath/structures/Buffer;)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 static final fun sumWithGroupOf (Ljava/lang/Iterable;Lspace/kscience/kmath/operations/Group;Lkotlin/jvm/functions/Function1;)Ljava/lang/Object; } public final class space/kscience/kmath/operations/AlgebraKt { @@ -1327,12 +1538,10 @@ 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/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 mutableBuffer (Lspace/kscience/kmath/operations/BigInt$Companion;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; @@ -1344,8 +1553,8 @@ public final class space/kscience/kmath/operations/BigIntKt { 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 getElementBufferFactory ()Lspace/kscience/kmath/structures/BufferFactory; 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; @@ -1362,11 +1571,11 @@ public final class space/kscience/kmath/operations/BufferAlgebraKt { 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/Field;)Lspace/kscience/kmath/operations/BufferFieldOps; + public static final fun getBufferAlgebra (Lspace/kscience/kmath/operations/IntRing;)Lspace/kscience/kmath/operations/BufferRingOps; 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; @@ -1377,8 +1586,19 @@ public final class space/kscience/kmath/operations/BufferAlgebraKt { public static final fun withSize (Lspace/kscience/kmath/operations/BufferFieldOps;I)Lspace/kscience/kmath/operations/BufferField; } +public final class space/kscience/kmath/operations/BufferExtensionsKt { + 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 foldIndexed (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;Lkotlin/jvm/functions/Function3;)Ljava/lang/Object; + public static final fun mapIndexedToBuffer (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/structures/Buffer; + public static final fun mapToBuffer (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/BufferFactory;Lkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; + public static final fun reduce (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)Ljava/lang/Object; + public static final fun toList (Lspace/kscience/kmath/structures/Buffer;)Ljava/util/List; +} + 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 fun (Lspace/kscience/kmath/operations/Field;I)V public synthetic fun getOne ()Ljava/lang/Object; public fun getOne ()Lspace/kscience/kmath/structures/Buffer; public fun getSize ()I @@ -1387,7 +1607,7 @@ public final class space/kscience/kmath/operations/BufferField : space/kscience/ } 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 (Lspace/kscience/kmath/operations/Field;)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; @@ -1397,20 +1617,11 @@ public class space/kscience/kmath/operations/BufferFieldOps : space/kscience/kma 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 fun (Lspace/kscience/kmath/operations/Ring;)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; @@ -1420,10 +1631,15 @@ public class space/kscience/kmath/operations/BufferRingOps : space/kscience/kmat public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } +public abstract interface class space/kscience/kmath/operations/BufferTransform { + public abstract fun transform (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; +} + 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; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun getOne ()Ljava/lang/Byte; public synthetic fun getOne ()Ljava/lang/Object; public fun getZero ()Ljava/lang/Byte; @@ -1460,6 +1676,7 @@ public final class space/kscience/kmath/operations/DoubleBufferField : space/ksc 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 synthetic fun power (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)Lspace/kscience/kmath/structures/Buffer; 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 @@ -1494,21 +1711,25 @@ public abstract class space/kscience/kmath/operations/DoubleBufferOps : space/ks 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 getElementBufferFactory ()Lspace/kscience/kmath/structures/BufferFactory; + public fun getElementBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; 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 final fun map-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function2;)[D + public synthetic fun mapIndexed (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/structures/Buffer; + public final fun mapIndexed-CZ9oacQ (Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)[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 power (Ljava/lang/Object;Ljava/lang/Number;)Ljava/lang/Object; + public fun power (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Number;)Lspace/kscience/kmath/structures/Buffer; 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; @@ -1522,10 +1743,21 @@ public abstract class space/kscience/kmath/operations/DoubleBufferOps : space/ks 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 synthetic fun zip (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)Lspace/kscience/kmath/structures/Buffer; + public final fun zip-XquIszc (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function3;)[D } 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/DoubleBufferOpsKt { + public static final fun average (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;)D + public static final fun averageOf (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;Lkotlin/jvm/functions/Function1;)D + public static final fun covariance (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;)D + public static final fun dispersion (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;)D + public static final fun std (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;)D + public static final fun sum (Lspace/kscience/kmath/operations/DoubleBufferOps;Lspace/kscience/kmath/structures/Buffer;)D + public static final fun sumOf (Lspace/kscience/kmath/operations/DoubleBufferOps;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 { @@ -1555,6 +1787,7 @@ public final class space/kscience/kmath/operations/DoubleField : space/kscience/ public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun exp (D)Ljava/lang/Double; public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun getOne ()Ljava/lang/Double; public synthetic fun getOne ()Ljava/lang/Object; public fun getZero ()Ljava/lang/Double; @@ -1628,7 +1861,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/ExtendedFieldOps, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumericAlgebra, space/kscience/kmath/operations/PowerOperations { +public abstract interface class space/kscience/kmath/operations/ExtendedField : space/kscience/kmath/operations/ExtendedFieldOps, space/kscience/kmath/operations/Field, space/kscience/kmath/operations/NumericAlgebra { 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; @@ -1639,7 +1872,7 @@ public abstract interface class space/kscience/kmath/operations/ExtendedField : public fun unaryOperationFunction (Ljava/lang/String;)Lkotlin/jvm/functions/Function1; } -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 abstract interface class space/kscience/kmath/operations/ExtendedFieldOps : space/kscience/kmath/operations/ExponentialOperations, space/kscience/kmath/operations/FieldOps, space/kscience/kmath/operations/PowerOperations, 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; @@ -1693,6 +1926,7 @@ public final class space/kscience/kmath/operations/FloatField : space/kscience/k public synthetic fun divide (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun exp (F)Ljava/lang/Float; public synthetic fun exp (Ljava/lang/Object;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun getOne ()Ljava/lang/Float; public synthetic fun getOne ()Ljava/lang/Object; public fun getZero ()Ljava/lang/Float; @@ -1755,6 +1989,7 @@ public final class space/kscience/kmath/operations/IntRing : space/kscience/kmat public static final field INSTANCE Lspace/kscience/kmath/operations/IntRing; public fun add (II)Ljava/lang/Integer; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun getOne ()Ljava/lang/Integer; public synthetic fun getOne ()Ljava/lang/Object; public fun getZero ()Ljava/lang/Integer; @@ -1833,9 +2068,6 @@ public final class space/kscience/kmath/operations/JBigIntegerField : space/ksci public fun unaryMinus (Ljava/math/BigInteger;)Ljava/math/BigInteger; } -public abstract interface annotation class space/kscience/kmath/operations/KMathContext : java/lang/annotation/Annotation { -} - public final class space/kscience/kmath/operations/LogicAlgebra$Companion { public final fun getFALSE ()Lspace/kscience/kmath/expressions/Symbol; public final fun getTRUE ()Lspace/kscience/kmath/expressions/Symbol; @@ -1845,6 +2077,7 @@ public final class space/kscience/kmath/operations/LongRing : space/kscience/kma public static final field INSTANCE Lspace/kscience/kmath/operations/LongRing; public fun add (JJ)Ljava/lang/Long; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public fun getOne ()Ljava/lang/Long; public synthetic fun getOne ()Ljava/lang/Object; public fun getZero ()Ljava/lang/Long; @@ -1938,6 +2171,7 @@ public final class space/kscience/kmath/operations/ShortRing : space/kscience/km public static final field INSTANCE Lspace/kscience/kmath/operations/ShortRing; public synthetic fun add (Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object; public fun add (SS)Ljava/lang/Short; + public fun getBufferFactory ()Lspace/kscience/kmath/structures/MutableBufferFactory; public synthetic fun getOne ()Ljava/lang/Object; public fun getOne ()Ljava/lang/Short; public synthetic fun getZero ()Ljava/lang/Object; @@ -2001,11 +2235,11 @@ 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 { +public abstract interface class space/kscience/kmath/structures/Buffer : space/kscience/kmath/operations/WithSize { public static final field Companion Lspace/kscience/kmath/structures/Buffer$Companion; public abstract fun get (I)Ljava/lang/Object; public abstract fun getSize ()I - public abstract fun iterator ()Ljava/util/Iterator; + public fun iterator ()Ljava/util/Iterator; public abstract fun toString ()Ljava/lang/String; } @@ -2016,14 +2250,95 @@ public final class space/kscience/kmath/structures/Buffer$Companion { public final fun toString (Lspace/kscience/kmath/structures/Buffer;)Ljava/lang/String; } +public final class space/kscience/kmath/structures/BufferExpanded : space/kscience/kmath/structures/BufferView { + public fun (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;II)V + public synthetic fun (Lspace/kscience/kmath/structures/Buffer;Ljava/lang/Object;IIILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun get (I)Ljava/lang/Object; + public final fun getOffset ()I + public fun getOrigin ()Lspace/kscience/kmath/structures/Buffer; + public fun getSize ()I + public fun toString ()Ljava/lang/String; +} + +public abstract interface class space/kscience/kmath/structures/BufferFactory { + public static final field Companion Lspace/kscience/kmath/structures/BufferFactory$Companion; + public abstract fun invoke (ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/Buffer; +} + +public final class space/kscience/kmath/structures/BufferFactory$Companion { + public final fun boxing ()Lspace/kscience/kmath/structures/BufferFactory; +} + public final class space/kscience/kmath/structures/BufferKt { 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 get-Qn1smSk (Lspace/kscience/kmath/structures/Buffer;I)Ljava/lang/Object; public static final fun getIndices (Lspace/kscience/kmath/structures/Buffer;)Lkotlin/ranges/IntRange; + public static final fun getOrNull (Lspace/kscience/kmath/structures/Buffer;I)Ljava/lang/Object; 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 final class space/kscience/kmath/structures/BufferPrimitiveAccessKt { +} + +public final class space/kscience/kmath/structures/BufferSlice : space/kscience/kmath/structures/BufferView { + public fun (Lspace/kscience/kmath/structures/Buffer;II)V + public synthetic fun (Lspace/kscience/kmath/structures/Buffer;IIILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun get (I)Ljava/lang/Object; + public final fun getOffset ()I + public fun getOrigin ()Lspace/kscience/kmath/structures/Buffer; + public fun getSize ()I + public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; +} + +public abstract interface class space/kscience/kmath/structures/BufferView : space/kscience/kmath/structures/Buffer { + public fun get (I)Ljava/lang/Object; + public abstract fun getOrigin ()Lspace/kscience/kmath/structures/Buffer; +} + +public final class space/kscience/kmath/structures/BufferViewKt { + public static final fun expand (Lspace/kscience/kmath/structures/Buffer;Lkotlin/ranges/IntRange;Ljava/lang/Object;)Lspace/kscience/kmath/structures/BufferView; + public static final fun permute (Lspace/kscience/kmath/structures/Buffer;[I)Lspace/kscience/kmath/structures/PermutedBuffer; + public static final fun permute (Lspace/kscience/kmath/structures/MutableBuffer;[I)Lspace/kscience/kmath/structures/PermutedMutableBuffer; + public static final fun slice (Lspace/kscience/kmath/structures/Buffer;Lkotlin/ranges/IntRange;)Lspace/kscience/kmath/structures/BufferView; +} + +public final class space/kscience/kmath/structures/ByteBuffer : space/kscience/kmath/structures/MutableBuffer { + public static final synthetic fun box-impl ([B)Lspace/kscience/kmath/structures/ByteBuffer; + public static fun constructor-impl ([B)[B + public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; + public static fun copy-impl ([B)Lspace/kscience/kmath/structures/MutableBuffer; + public fun equals (Ljava/lang/Object;)Z + public static fun equals-impl ([BLjava/lang/Object;)Z + public static final fun equals-impl0 ([B[B)Z + public fun get (I)Ljava/lang/Byte; + public synthetic fun get (I)Ljava/lang/Object; + public static fun get-impl ([BI)Ljava/lang/Byte; + public final fun getArray ()[B + public fun getSize ()I + public static fun getSize-impl ([B)I + public fun hashCode ()I + public static fun hashCode-impl ([B)I + public synthetic fun iterator ()Ljava/util/Iterator; + public fun iterator ()Lkotlin/collections/ByteIterator; + public static fun iterator-impl ([B)Lkotlin/collections/ByteIterator; + public fun set (IB)V + public synthetic fun set (ILjava/lang/Object;)V + public static fun set-impl ([BIB)V + public fun toString ()Ljava/lang/String; + public static fun toString-impl ([B)Ljava/lang/String; + public final synthetic fun unbox-impl ()[B +} + +public final class space/kscience/kmath/structures/ByteBufferKt { + public static final fun ByteBuffer (ILkotlin/jvm/functions/Function1;)[B + public static final fun ByteBuffer ([B)[B + public static final fun asBuffer ([B)[B + public static final fun toByteArray (Lspace/kscience/kmath/structures/Buffer;)[B +} + +public final class space/kscience/kmath/structures/DoubleBuffer : space/kscience/kmath/structures/PrimitiveBuffer { 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 @@ -2060,8 +2375,14 @@ public final class space/kscience/kmath/structures/DoubleBufferKt { public static final fun DoubleBuffer (ILkotlin/jvm/functions/Function1;)[D public static final fun DoubleBuffer ([D)[D public static final fun asBuffer ([D)[D - public static final fun contentEquals-2c9zdjM ([D[D)Z public static final fun toDoubleArray (Lspace/kscience/kmath/structures/Buffer;)[D + public static final fun toDoubleBuffer (Lspace/kscience/kmath/structures/Buffer;)[D +} + +public abstract interface class space/kscience/kmath/structures/DoubleBufferTransform : space/kscience/kmath/operations/BufferTransform { + public synthetic fun transform (Lspace/kscience/kmath/structures/Buffer;)Lspace/kscience/kmath/structures/Buffer; + public abstract fun transform-7Zdoou4 ([D)[D + public fun transform-Udx-57Q (Lspace/kscience/kmath/structures/Buffer;)[D } public abstract interface class space/kscience/kmath/structures/FlaggedBuffer : space/kscience/kmath/structures/Buffer { @@ -2087,7 +2408,7 @@ public final class space/kscience/kmath/structures/FlaggedDoubleBuffer : space/k public fun toString ()Ljava/lang/String; } -public final class space/kscience/kmath/structures/FloatBuffer : space/kscience/kmath/structures/MutableBuffer { +public final class space/kscience/kmath/structures/FloatBuffer : space/kscience/kmath/structures/PrimitiveBuffer { public static final synthetic fun box-impl ([F)Lspace/kscience/kmath/structures/FloatBuffer; public static fun constructor-impl ([F)[F public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; @@ -2121,11 +2442,12 @@ public final class space/kscience/kmath/structures/FloatBufferKt { public static final fun toFloatArray (Lspace/kscience/kmath/structures/Buffer;)[F } -public final class space/kscience/kmath/structures/IntBuffer : space/kscience/kmath/structures/MutableBuffer { +public final class space/kscience/kmath/structures/IntBuffer : space/kscience/kmath/structures/PrimitiveBuffer { public static final synthetic fun box-impl ([I)Lspace/kscience/kmath/structures/IntBuffer; public static fun constructor-impl ([I)[I - public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; - public static fun copy-impl ([I)Lspace/kscience/kmath/structures/MutableBuffer; + public synthetic fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; + public fun copy-ir4F4A8 ()[I + public static fun copy-ir4F4A8 ([I)[I public fun equals (Ljava/lang/Object;)Z public static fun equals-impl ([ILjava/lang/Object;)Z public static final fun equals-impl0 ([I[I)Z @@ -2170,7 +2492,7 @@ public final class space/kscience/kmath/structures/ListBufferKt { public static final fun asMutableBuffer (Ljava/util/List;)Ljava/util/List; } -public final class space/kscience/kmath/structures/LongBuffer : space/kscience/kmath/structures/MutableBuffer { +public final class space/kscience/kmath/structures/LongBuffer : space/kscience/kmath/structures/PrimitiveBuffer { public static final synthetic fun box-impl ([J)Lspace/kscience/kmath/structures/LongBuffer; public static fun constructor-impl ([J)[J public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; @@ -2236,6 +2558,15 @@ public final class space/kscience/kmath/structures/MutableBuffer$Companion { public final fun short-1yRgbGw (ILkotlin/jvm/functions/Function1;)[S } +public abstract interface class space/kscience/kmath/structures/MutableBufferFactory : space/kscience/kmath/structures/BufferFactory { + public static final field Companion Lspace/kscience/kmath/structures/MutableBufferFactory$Companion; + public abstract fun invoke (ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/MutableBuffer; +} + +public final class space/kscience/kmath/structures/MutableBufferFactory$Companion { + public final fun boxing ()Lspace/kscience/kmath/structures/MutableBufferFactory; +} + public final class space/kscience/kmath/structures/MutableListBuffer : space/kscience/kmath/structures/MutableBuffer { public static final synthetic fun box-impl (Ljava/util/List;)Lspace/kscience/kmath/structures/MutableListBuffer; public static fun constructor-impl (ILkotlin/jvm/functions/Function1;)Ljava/util/List; @@ -2273,6 +2604,30 @@ public final class space/kscience/kmath/structures/MutableMemoryBuffer$Companion public final fun create (Lspace/kscience/kmath/memory/MemorySpec;ILkotlin/jvm/functions/Function1;)Lspace/kscience/kmath/structures/MutableMemoryBuffer; } +public final class space/kscience/kmath/structures/PermutedBuffer : space/kscience/kmath/structures/BufferView { + public fun (Lspace/kscience/kmath/structures/Buffer;[I)V + public fun get (I)Ljava/lang/Object; + public fun getOrigin ()Lspace/kscience/kmath/structures/Buffer; + public fun getSize ()I + public fun iterator ()Ljava/util/Iterator; + public fun toString ()Ljava/lang/String; +} + +public final class space/kscience/kmath/structures/PermutedMutableBuffer : space/kscience/kmath/structures/BufferView, space/kscience/kmath/structures/MutableBuffer { + public fun (Lspace/kscience/kmath/structures/MutableBuffer;[I)V + public fun copy ()Lspace/kscience/kmath/structures/MutableBuffer; + public fun get (I)Ljava/lang/Object; + public synthetic fun getOrigin ()Lspace/kscience/kmath/structures/Buffer; + public fun getOrigin ()Lspace/kscience/kmath/structures/MutableBuffer; + public fun getSize ()I + public fun iterator ()Ljava/util/Iterator; + public fun set (ILjava/lang/Object;)V + public fun toString ()Ljava/lang/String; +} + +public abstract interface class space/kscience/kmath/structures/PrimitiveBuffer : space/kscience/kmath/structures/MutableBuffer { +} + public final class space/kscience/kmath/structures/ReadOnlyBuffer : space/kscience/kmath/structures/Buffer { public static final synthetic fun box-impl (Lspace/kscience/kmath/structures/MutableBuffer;)Lspace/kscience/kmath/structures/ReadOnlyBuffer; public static fun constructor-impl (Lspace/kscience/kmath/structures/MutableBuffer;)Lspace/kscience/kmath/structures/MutableBuffer; diff --git a/kmath-core/build.gradle.kts b/kmath-core/build.gradle.kts index 052924ce8..2088e0159 100644 --- a/kmath-core/build.gradle.kts +++ b/kmath-core/build.gradle.kts @@ -1,32 +1,25 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets { - filter { it.name.contains("test", true) } - .map(org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet::languageSettings) - .forEach { - it.optIn("space.kscience.kmath.misc.PerformancePitfall") - it.optIn("space.kscience.kmath.misc.UnstableKMathAPI") - } +kscience{ + jvm() + js() + native() + wasm() - commonMain { - dependencies { - api(project(":kmath-memory")) - } + dependencies { + api(projects.kmathMemory) } -} -//generateUml { -// classTree { -// -// } -//} + testDependencies { + implementation(projects.testUtils) + } +} readme { description = "Core classes, algebra definitions, basic linear algebra" - maturity = ru.mipt.npm.gradle.Maturity.DEVELOPMENT + maturity = space.kscience.gradle.Maturity.DEVELOPMENT propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/ColumnarData.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/ColumnarData.kt index e06b774fd..49e2ee8d0 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/ColumnarData.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/ColumnarData.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.data +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.structures.Buffer diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYColumnarData.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYColumnarData.kt index 2fce772cc..de7e6f79b 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYColumnarData.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYColumnarData.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.data +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.structures.Buffer import kotlin.math.max diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYErrorColumnarData.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYErrorColumnarData.kt index 8ddd6406f..797a25443 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYErrorColumnarData.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYErrorColumnarData.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.data +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYZColumnarData.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYZColumnarData.kt index e99ae0698..846bbad62 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYZColumnarData.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/data/XYZColumnarData.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.data +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer /** diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain.kt index b5a84cf6c..eecdcebad 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/Domain.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 3d531349c..d619883b4 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.domains +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI @UnstableKMathAPI public abstract class Domain1D>(public val range: ClosedRange) : Domain { diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/DoubleDomain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/DoubleDomain.kt index ee1bebde0..e56173624 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/DoubleDomain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/DoubleDomain.kt @@ -1,10 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.domains -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI /** * n-dimensional volume 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 485416a69..1049a251a 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 @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.domains +import space.kscience.kmath.UnstableKMathAPI 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 diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnconstrainedDomain.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnconstrainedDomain.kt index 32a5fc56c..5351a295d 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnconstrainedDomain.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/domains/UnconstrainedDomain.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.domains +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI @UnstableKMathAPI public class UnconstrainedDomain(override val dimension: Int) : DoubleDomain { 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 c55e41bb2..8c7cb0cf1 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 @@ -1,11 +1,11 @@ /* - * 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. + * Copyright 2018-2022 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.expressions -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.MutableBuffer @@ -80,7 +80,6 @@ public abstract class DSAlgebra>( public val algebra: A, public val order: Int, bindings: Map, - public val valueBufferFactory: MutableBufferFactory = algebra.bufferFactory, ) : ExpressionAlgebra>, SymbolIndexer { /** @@ -116,7 +115,6 @@ public abstract class DSAlgebra>( newCache[p][o] = DSCompiler( algebra, - valueBufferFactory, p, o, valueCompiler, @@ -141,7 +139,7 @@ public abstract class DSAlgebra>( override val symbols: List = bindings.map { it.key } private fun bufferForVariable(index: Int, value: T): Buffer { - val buffer = valueBufferFactory(compiler.size) { algebra.zero } + val buffer = algebra.bufferFactory(compiler.size) { algebra.zero } buffer[0] = value if (compiler.order > 0) { // the derivative of the variable with respect to itself is 1. @@ -207,7 +205,7 @@ public abstract class DSAlgebra>( } public override fun const(value: T): DS { - val buffer = valueBufferFactory(compiler.size) { algebra.zero } + val buffer = algebra.bufferFactory(compiler.size) { algebra.zero } buffer[0] = value return DS(buffer) @@ -245,11 +243,14 @@ public open class DSRing( algebra: A, order: Int, bindings: Map, - valueBufferFactory: MutableBufferFactory, -) : DSAlgebra(algebra, order, bindings, valueBufferFactory), - Ring>, ScaleOperations>, +) : DSAlgebra(algebra, order, bindings), + Ring>, + ScaleOperations>, NumericAlgebra>, - NumbersAddOps> where A : Ring, A : NumericAlgebra, A : ScaleOperations { + NumbersAddOps> + where A : Ring, A : NumericAlgebra, A : ScaleOperations { + + public val elementBufferFactory: MutableBufferFactory = algebra.bufferFactory override fun bindSymbolOrNull(value: String): DSSymbol? = super.bindSymbolOrNull(value) @@ -261,14 +262,14 @@ public open class DSRing( */ 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 = valueBufferFactory(compiler.size) { data[it] } + val newData = elementBufferFactory(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(valueBufferFactory) { + val newData: Buffer = data.mapToBuffer(elementBufferFactory) { algebra.block(it) } return DS(newData) @@ -276,7 +277,7 @@ public open class DSRing( 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(valueBufferFactory, block) + val newData: Buffer = data.mapIndexedToBuffer(elementBufferFactory, block) return DS(newData) } @@ -329,22 +330,21 @@ public class DerivativeStructureRingExpression( public val function: DSRing.() -> DS, ) : DifferentiableExpression where A : Ring, A : ScaleOperations, A : NumericAlgebra { override operator fun invoke(arguments: Map): T = - DSRing(algebra, 0, arguments, elementBufferFactory).function().value + DSRing(algebra, 0, arguments).function().value override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> with( DSRing( algebra, symbols.size, - arguments, - elementBufferFactory + arguments ) ) { function().derivative(symbols) } } } /** - * A field over commons-math [DerivativeStructure]. + * A field over [DS]. * * @property order The derivation order. * @param bindings The map of bindings values. All bindings are considered free parameters. @@ -354,8 +354,7 @@ public class DSField>( algebra: A, order: Int, bindings: Map, - valueBufferFactory: MutableBufferFactory, -) : DSRing(algebra, order, bindings, valueBufferFactory), ExtendedField> { +) : DSRing(algebra, order, bindings), ExtendedField> { override fun number(value: Number): DS = const(algebra.number(value)) override fun divide(left: DS, right: DS): DS = left.transformDataBuffer { result -> @@ -414,6 +413,7 @@ public class DSField>( 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) } @@ -439,18 +439,29 @@ public class DSField>( @UnstableKMathAPI public class DSFieldExpression>( public val algebra: A, - private val valueBufferFactory: MutableBufferFactory = algebra.bufferFactory, public val function: DSField.() -> DS, ) : DifferentiableExpression { override operator fun invoke(arguments: Map): T = - DSField(algebra, 0, arguments, valueBufferFactory).function().value + DSField(algebra, 0, arguments).function().value override fun derivativeOrNull(symbols: List): Expression = Expression { arguments -> DSField( algebra, symbols.size, arguments, - valueBufferFactory, ).run { function().derivative(symbols) } } } + + +@UnstableKMathAPI +public class DSFieldProcessor>( + public val algebra: A, +) : AutoDiffProcessor, DSField> { + override fun differentiate( + function: DSField.() -> DS, + ): DifferentiableExpression = DSFieldExpression(algebra, function) +} + +@UnstableKMathAPI +public val Double.Companion.autodiff: DSFieldProcessor get() = DSFieldProcessor(DoubleField) \ No newline at end of file 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 b5b2988a3..1da151d46 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 @@ -1,6 +1,6 @@ /* - * 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. + * Copyright 2018-2022 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.expressions @@ -9,7 +9,6 @@ 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.min internal fun MutableBuffer.fill(element: T, fromIndex: Int = 0, toIndex: Int = size) { @@ -56,7 +55,6 @@ internal fun MutableBuffer.fill(element: T, fromIndex: Int = 0, toIndex: */ public class DSCompiler> internal constructor( public val algebra: A, - public val bufferFactory: MutableBufferFactory, public val freeParameters: Int, public val order: Int, valueCompiler: DSCompiler?, diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DifferentiableExpression.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DifferentiableExpression.kt index 12b7df0ea..7c8a957c7 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DifferentiableExpression.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/DifferentiableExpression.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Expression.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Expression.kt index 5ba32f190..f350303bc 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Expression.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Expression.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.expressions -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.Algebra import kotlin.jvm.JvmName import kotlin.properties.ReadOnlyProperty @@ -48,6 +48,10 @@ public interface DoubleExpression : Expression { * @return the value. */ public operator fun invoke(arguments: DoubleArray): Double + + public companion object{ + internal val EMPTY_DOUBLE_ARRAY = DoubleArray(0) + } } /** @@ -73,6 +77,10 @@ public interface IntExpression : Expression { * @return the value. */ public operator fun invoke(arguments: IntArray): Int + + public companion object{ + internal val EMPTY_INT_ARRAY = IntArray(0) + } } /** @@ -98,6 +106,10 @@ public interface LongExpression : Expression { * @return the value. */ public operator fun invoke(arguments: LongArray): Long + + public companion object{ + internal val EMPTY_LONG_ARRAY = LongArray(0) + } } /** @@ -145,7 +157,7 @@ public operator fun Expression.invoke(vararg pairs: Pair): T = } ) -private val EMPTY_DOUBLE_ARRAY = DoubleArray(0) + /** * Calls this expression without providing any arguments. @@ -153,7 +165,7 @@ private val EMPTY_DOUBLE_ARRAY = DoubleArray(0) * @return a value. */ @UnstableKMathAPI -public operator fun DoubleExpression.invoke(): Double = this(EMPTY_DOUBLE_ARRAY) +public operator fun DoubleExpression.invoke(): Double = this(DoubleExpression.EMPTY_DOUBLE_ARRAY) /** * Calls this expression from arguments. @@ -164,15 +176,13 @@ public operator fun DoubleExpression.invoke(): Double = this(EMPTY_DOUBLE_ARRAY) @UnstableKMathAPI public operator fun DoubleExpression.invoke(vararg arguments: Double): Double = this(arguments) -private val EMPTY_INT_ARRAY = IntArray(0) - /** * Calls this expression without providing any arguments. * * @return a value. */ @UnstableKMathAPI -public operator fun IntExpression.invoke(): Int = this(EMPTY_INT_ARRAY) +public operator fun IntExpression.invoke(): Int = this(IntExpression.EMPTY_INT_ARRAY) /** * Calls this expression from arguments. @@ -183,15 +193,13 @@ public operator fun IntExpression.invoke(): Int = this(EMPTY_INT_ARRAY) @UnstableKMathAPI public operator fun IntExpression.invoke(vararg arguments: Int): Int = this(arguments) -private val EMPTY_LONG_ARRAY = LongArray(0) - /** * Calls this expression without providing any arguments. * * @return a value. */ @UnstableKMathAPI -public operator fun LongExpression.invoke(): Long = this(EMPTY_LONG_ARRAY) +public operator fun LongExpression.invoke(): Long = this(LongExpression.EMPTY_LONG_ARRAY) /** * Calls this expression from arguments. diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/ExpressionWithDefault.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/ExpressionWithDefault.kt new file mode 100644 index 000000000..c802fe04c --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/ExpressionWithDefault.kt @@ -0,0 +1,31 @@ +/* + * Copyright 2018-2023 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.expressions + +public class ExpressionWithDefault( + private val origin: Expression, + private val defaultArgs: Map, +) : Expression { + override fun invoke(arguments: Map): T = origin.invoke(defaultArgs + arguments) +} + +public fun Expression.withDefaultArgs(defaultArgs: Map): ExpressionWithDefault = + ExpressionWithDefault(this, defaultArgs) + + +public class DiffExpressionWithDefault( + private val origin: DifferentiableExpression, + private val defaultArgs: Map, +) : DifferentiableExpression { + + override fun invoke(arguments: Map): T = origin.invoke(defaultArgs + arguments) + + override fun derivativeOrNull(symbols: List): Expression? = + origin.derivativeOrNull(symbols)?.withDefaultArgs(defaultArgs) +} + +public fun DifferentiableExpression.withDefaultArgs(defaultArgs: Map): DiffExpressionWithDefault = + DiffExpressionWithDefault(this, defaultArgs) \ No newline at end of file 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 68cc8e791..1054d1aa1 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 18226119b..9705a3f03 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MstAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MstAlgebra.kt index 4bd2a6c53..c894cf00a 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MstAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/MstAlgebra.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.expressions -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* /** diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/NamedMatrix.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/NamedMatrix.kt new file mode 100644 index 000000000..5d047d5b7 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/NamedMatrix.kt @@ -0,0 +1,39 @@ +/* + * Copyright 2018-2023 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.expressions + +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.linear.Matrix +import space.kscience.kmath.structures.getOrNull + +public class NamedMatrix(public val values: Matrix, public val indexer: SymbolIndexer) : Matrix by values { + public operator fun get(i: Symbol, j: Symbol): T = get(indexer.indexOf(i), indexer.indexOf(j)) + + public companion object { + + @OptIn(PerformancePitfall::class) + public fun toStringWithSymbols(values: Matrix<*>, indexer: SymbolIndexer): String = buildString { + appendLine(indexer.symbols.joinToString(separator = "\t", prefix = "\t\t")) + indexer.symbols.forEach { i -> + append(i.identity + "\t") + values.rows.getOrNull(indexer.indexOf(i))?.let { row -> + indexer.symbols.forEach { j -> + append(row.getOrNull(indexer.indexOf(j)).toString()) + append("\t") + } + appendLine() + } + } + } + } +} + +public fun Matrix.named(indexer: SymbolIndexer): NamedMatrix = NamedMatrix(this, indexer) + +public fun Matrix.named(symbols: List): NamedMatrix = named(SimpleSymbolIndexer(symbols)) \ No newline at end of file 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 ac8c44446..2bb5043b7 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.expressions +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.asBuffer import kotlin.contracts.InvocationKind diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Symbol.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Symbol.kt index 8ab2bec31..c57ce69ab 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Symbol.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/Symbol.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SymbolIndexer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SymbolIndexer.kt index bf37e9615..7112e921a 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SymbolIndexer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/SymbolIndexer.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.expressions +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.DoubleBuffer diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/BufferedLinearSpace.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/BufferedLinearSpace.kt index 8f7569699..4bba47a91 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/BufferedLinearSpace.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/BufferedLinearSpace.kt @@ -1,14 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.BufferedRingOpsND -import space.kscience.kmath.nd.as2D -import space.kscience.kmath.nd.asND +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.VirtualBuffer @@ -23,7 +21,7 @@ public class BufferedLinearSpace>( private val ndAlgebra = BufferedRingOpsND(bufferAlgebra) override fun buildMatrix(rows: Int, columns: Int, initializer: A.(i: Int, j: Int) -> T): Matrix = - ndAlgebra.structureND(intArrayOf(rows, columns)) { (i, j) -> elementAlgebra.initializer(i, j) }.as2D() + ndAlgebra.structureND(ShapeND(rows, columns)) { (i, j) -> elementAlgebra.initializer(i, j) }.as2D() override fun buildVector(size: Int, initializer: A.(Int) -> T): Point = bufferAlgebra.buffer(size) { elementAlgebra.initializer(it) } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/DoubleLinearSpace.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/DoubleLinearSpace.kt index 4e6debc60..940af4a86 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/DoubleLinearSpace.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/DoubleLinearSpace.kt @@ -1,14 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DoubleFieldOpsND -import space.kscience.kmath.nd.as2D -import space.kscience.kmath.nd.asND +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleBufferOps import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.invoke @@ -23,7 +21,7 @@ public object DoubleLinearSpace : LinearSpace { rows: Int, columns: Int, initializer: DoubleField.(i: Int, j: Int) -> Double - ): Matrix = DoubleFieldOpsND.structureND(intArrayOf(rows, columns)) { (i, j) -> + ): Matrix = DoubleFieldOpsND.structureND(ShapeND(rows, columns)) { (i, j) -> DoubleField.initializer(i, j) }.as2D() diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSolver.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSolver.kt index fae9e7c91..af9ebb463 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSolver.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LinearSolver.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 d437070c9..a82bafe57 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 @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.MutableStructure2D import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.nd.StructureFeature diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LupDecomposition.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LupDecomposition.kt index fb57f2343..650e7be5c 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LupDecomposition.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/LupDecomposition.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.BufferAccessor2D import space.kscience.kmath.structures.DoubleBuffer diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixBuilder.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixBuilder.kt index 029612bc5..4d2f01e68 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixBuilder.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixBuilder.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.Ring import space.kscience.kmath.structures.BufferAccessor2D import space.kscience.kmath.structures.MutableBuffer diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixFeatures.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixFeatures.kt index b70e9d8a9..ce7acdcba 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixFeatures.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixFeatures.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixWrapper.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixWrapper.kt index b1812f49d..46454a584 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixWrapper.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/MatrixWrapper.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.misc.FeatureSet -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.StructureFeature import space.kscience.kmath.operations.Ring import kotlin.reflect.KClass diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/VirtualMatrix.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/VirtualMatrix.kt index fb2b1e547..55b970f4a 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/VirtualMatrix.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/linear/VirtualMatrix.kt @@ -1,10 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear +import space.kscience.kmath.nd.ShapeND + + /** * The matrix where each element is evaluated each time when is being accessed. * @@ -16,7 +19,7 @@ public class VirtualMatrix( public val generator: (i: Int, j: Int) -> T, ) : Matrix { - override val shape: IntArray get() = intArrayOf(rowNum, colNum) + override val shape: ShapeND get() = ShapeND(rowNum, colNum) override operator fun get(i: Int, j: Int): T = generator(i, j) } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/Featured.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/Featured.kt index 29b7caec6..bdda674dc 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/Featured.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/Featured.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -9,7 +9,7 @@ import kotlin.jvm.JvmInline import kotlin.reflect.KClass /** - * A entity that contains a set of features defined by their types + * An entity that contains a set of features defined by their types */ public interface Featured { public fun getFeature(type: FeatureKey): T? diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/collections.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/collections.kt new file mode 100644 index 000000000..f630055fa --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/collections.kt @@ -0,0 +1,22 @@ +/* + * Copyright 2018-2023 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.misc + +/** + * The same as [zipWithNext], but includes link between last and first element + */ +public inline fun List.zipWithNextCircular(transform: (a: T, b: T) -> R): List { + if (size < 2) return emptyList() + return indices.map { i -> + if (i == size - 1) { + transform(last(), first()) + } else { + transform(get(i), get(i + 1)) + } + } +} + +public fun List.zipWithNextCircular(): List> = zipWithNextCircular { l, r -> l to r } \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/cumulative.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/cumulative.kt index ee7f1d8be..c05f1a6a9 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/cumulative.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/cumulative.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,6 +7,7 @@ package space.kscience.kmath.misc import space.kscience.kmath.operations.Ring import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.Buffer import kotlin.jvm.JvmName /** @@ -42,8 +43,8 @@ public inline fun List.cumulative(initial: R, crossinline operation: ( /** * Cumulative sum with custom space */ -public fun Iterable.cumulativeSum(group: Ring): Iterable = - group { cumulative(zero) { element: T, sum: T -> sum + element } } +public fun Iterable.cumulativeSum(ring: Ring): Iterable = + ring { cumulative(zero) { element: T, sum: T -> sum + element } } @JvmName("cumulativeSumOfDouble") public fun Iterable.cumulativeSum(): Iterable = cumulative(0.0) { element, sum -> sum + element } @@ -54,8 +55,8 @@ public fun Iterable.cumulativeSum(): Iterable = cumulative(0) { elemen @JvmName("cumulativeSumOfLong") public fun Iterable.cumulativeSum(): Iterable = cumulative(0L) { element, sum -> sum + element } -public fun Sequence.cumulativeSum(group: Ring): Sequence = - group { cumulative(zero) { element: T, sum: T -> sum + element } } +public fun Sequence.cumulativeSum(ring: Ring): Sequence = + ring { cumulative(zero) { element: T, sum: T -> sum + element } } @JvmName("cumulativeSumOfDouble") public fun Sequence.cumulativeSum(): Sequence = cumulative(0.0) { element, sum -> sum + element } @@ -77,3 +78,12 @@ public fun List.cumulativeSum(): List = cumulative(0) { element, sum - @JvmName("cumulativeSumOfLong") public fun List.cumulativeSum(): List = cumulative(0L) { element, sum -> sum + element } + + +public fun Buffer.cumulativeSum(ring: Ring): Buffer = with(ring) { + var accumulator: T = zero + return bufferFactory(size) { + accumulator += get(it) + accumulator + } +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/logging.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/logging.kt index 9dfc564c3..c7886469f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/logging.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/logging.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/numbers.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/numbers.kt index f879a06d5..77ef07ea8 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/numbers.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/numbers.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 dc5421136..31b8c0037 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 @@ -1,11 +1,12 @@ /* - * 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. + * Copyright 2018-2022 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.misc +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.VirtualBuffer 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 ad291cf7f..91e26cc1b 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* import kotlin.reflect.KClass @@ -25,7 +25,7 @@ public interface AlgebraND>: Algebra> { /** * Produces a new [StructureND] using given initializer function. */ - public fun structureND(shape: Shape, initializer: C.(IntArray) -> T): StructureND + public fun structureND(shape: ShapeND, initializer: C.(IntArray) -> T): StructureND /** * Maps elements from one structure to another one by applying [transform] to them. 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 8c5eef3d0..74c63e6e2 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,16 +7,16 @@ package space.kscience.kmath.nd -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* public interface BufferAlgebraND> : AlgebraND { - public val indexerBuilder: (IntArray) -> ShapeIndexer + public val indexerBuilder: (ShapeND) -> ShapeIndexer public val bufferAlgebra: BufferAlgebra override val elementAlgebra: A get() = bufferAlgebra.elementAlgebra - override fun structureND(shape: Shape, initializer: A.(IntArray) -> T): BufferND { + override fun structureND(shape: ShapeND, initializer: A.(IntArray) -> T): BufferND { val indexer = indexerBuilder(shape) return BufferND( indexer, @@ -26,6 +26,7 @@ public interface BufferAlgebraND> : AlgebraND { ) } + @OptIn(PerformancePitfall::class) public fun StructureND.toBufferND(): BufferND = when (this) { is BufferND -> this else -> { @@ -46,7 +47,7 @@ public interface BufferAlgebraND> : AlgebraND { zipInline(left.toBufferND(), right.toBufferND(), transform) public companion object { - public val defaultIndexerBuilder: (IntArray) -> ShapeIndexer = ::Strides + public val defaultIndexerBuilder: (ShapeND) -> ShapeIndexer = ::Strides } } @@ -98,24 +99,24 @@ internal inline fun > BufferAlgebraND.zipInline( @OptIn(PerformancePitfall::class) public open class BufferedGroupNDOps>( override val bufferAlgebra: BufferAlgebra, - override val indexerBuilder: (IntArray) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, + override val indexerBuilder: (ShapeND) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, ) : GroupOpsND, BufferAlgebraND { override fun StructureND.unaryMinus(): StructureND = map { -it } } public open class BufferedRingOpsND>( bufferAlgebra: BufferAlgebra, - indexerBuilder: (IntArray) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, + indexerBuilder: (ShapeND) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, ) : BufferedGroupNDOps(bufferAlgebra, indexerBuilder), RingOpsND public open class BufferedFieldOpsND>( bufferAlgebra: BufferAlgebra, - indexerBuilder: (IntArray) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, + indexerBuilder: (ShapeND) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, ) : BufferedRingOpsND(bufferAlgebra, indexerBuilder), FieldOpsND { public constructor( elementAlgebra: A, - indexerBuilder: (IntArray) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, + indexerBuilder: (ShapeND) -> ShapeIndexer = BufferAlgebraND.defaultIndexerBuilder, ) : this(BufferFieldOps(elementAlgebra), indexerBuilder) @OptIn(PerformancePitfall::class) @@ -130,7 +131,7 @@ public val > BufferAlgebra.nd: BufferedFieldOpsND ge public fun > BufferAlgebraND.structureND( vararg shape: Int, initializer: A.(IntArray) -> T, -): BufferND = structureND(shape, initializer) +): BufferND = structureND(ShapeND(shape), initializer) public fun , A> A.structureND( initializer: EA.(IntArray) -> T, 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 8175bd65e..9217f6fdc 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 @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.PerformancePitfall import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.MutableBuffer @@ -22,32 +23,45 @@ public open class BufferND( public open val buffer: Buffer, ) : StructureND { + @PerformancePitfall override operator fun get(index: IntArray): T = buffer[indices.offset(index)] - override val shape: IntArray get() = indices.shape + override val shape: ShapeND get() = indices.shape override fun toString(): String = StructureND.toString(this) } /** - * Transform structure to a new structure using provided [BufferFactory] and optimizing if argument is [BufferND] + * Create a generic [BufferND] using provided [initializer] */ -public inline fun StructureND.mapToBuffer( - factory: BufferFactory, - crossinline transform: (T) -> R, -): 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))) }) +public fun BufferND( + shape: ShapeND, + bufferFactory: BufferFactory = BufferFactory.boxing(), + initializer: (IntArray) -> T, +): BufferND { + val strides = Strides(shape) + return BufferND(strides, bufferFactory(strides.linearSize) { initializer(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) +///** +// * Transform structure to a new structure using provided [BufferFactory] and optimizing if argument is [BufferND] +// */ +//public inline fun StructureND.mapToBuffer( +// factory: BufferFactory, +// crossinline transform: (T) -> R, +//): BufferND = if (this is BufferND) +// BufferND(this.indices, factory.invoke(indices.linearSize) { transform(buffer[it]) }) +//else { +// val strides = ColumnStrides(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]. @@ -56,26 +70,40 @@ public inline fun StructureND.mapToBuffer( * @param strides The strides to access elements of [MutableBuffer] by linear indices. * @param buffer The underlying buffer. */ -public class MutableBufferND( +public open class MutableBufferND( strides: ShapeIndexer, override val buffer: MutableBuffer, ) : MutableStructureND, BufferND(strides, buffer) { + + @PerformancePitfall override fun set(index: IntArray, value: T) { buffer[indices.offset(index)] = value } } /** - * Transform structure to a new structure using provided [MutableBufferFactory] and optimizing if argument is [MutableBufferND] + * Create a generic [BufferND] using provided [initializer] */ -public inline fun MutableStructureND.mapToMutableBuffer( - factory: MutableBufferFactory = MutableBufferFactory(MutableBuffer.Companion::auto), - crossinline transform: (T) -> R, -): MutableBufferND { - return if (this is MutableBufferND) - MutableBufferND(this.indices, factory.invoke(indices.linearSize) { transform(buffer[it]) }) - else { - val strides = DefaultStrides(shape) - MutableBufferND(strides, factory.invoke(strides.linearSize) { transform(get(strides.index(it))) }) - } -} \ No newline at end of file +public fun MutableBufferND( + shape: ShapeND, + bufferFactory: MutableBufferFactory = MutableBufferFactory.boxing(), + initializer: (IntArray) -> T, +): MutableBufferND { + val strides = Strides(shape) + return MutableBufferND(strides, bufferFactory(strides.linearSize) { initializer(strides.index(it)) }) +} + +///** +// * Transform structure to a new structure using provided [MutableBufferFactory] and optimizing if argument is [MutableBufferND] +// */ +//public inline fun MutableStructureND.mapToMutableBuffer( +// factory: MutableBufferFactory = MutableBufferFactory(MutableBuffer.Companion::auto), +// crossinline transform: (T) -> R, +//): MutableBufferND { +// return if (this is MutableBufferND) +// MutableBufferND(this.indices, factory.invoke(indices.linearSize) { transform(buffer[it]) }) +// else { +// val strides = ColumnStrides(shape) +// MutableBufferND(strides, factory.invoke(strides.linearSize) { transform(get(strides.index(it))) }) +// } +//} \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/DoubleFieldND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/DoubleFieldND.kt index d01a8ee95..265d1eec8 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/DoubleFieldND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/DoubleFieldND.kt @@ -1,27 +1,38 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.DoubleBuffer import kotlin.contracts.InvocationKind import kotlin.contracts.contract +import kotlin.math.pow import kotlin.math.pow as kpow +/** + * A simple mutable [StructureND] of doubles + */ public class DoubleBufferND( indexes: ShapeIndexer, override val buffer: DoubleBuffer, -) : BufferND(indexes, buffer) +) : MutableBufferND(indexes, buffer), MutableStructureNDOfDouble{ + override fun getDouble(index: IntArray): Double = buffer[indices.offset(index)] + + override fun setDouble(index: IntArray, value: Double) { + buffer[indices.offset(index)] = value + } +} public sealed class DoubleFieldOpsND : BufferedFieldOpsND(DoubleField.bufferAlgebra), ScaleOperations>, ExtendedFieldOps> { + @OptIn(PerformancePitfall::class) override fun StructureND.toBufferND(): DoubleBufferND = when (this) { is DoubleBufferND -> this else -> { @@ -63,7 +74,7 @@ public sealed class DoubleFieldOpsND : BufferedFieldOpsND(D transform: DoubleField.(Double, Double) -> Double, ): BufferND = zipInline(left.toBufferND(), right.toBufferND()) { l, r -> DoubleField.transform(l, r) } - override fun structureND(shape: Shape, initializer: DoubleField.(IntArray) -> Double): DoubleBufferND { + override fun structureND(shape: ShapeND, initializer: DoubleField.(IntArray) -> Double): DoubleBufferND { val indexer = indexerBuilder(shape) return DoubleBufferND( indexer, @@ -165,11 +176,20 @@ public sealed class DoubleFieldOpsND : BufferedFieldOpsND(D override fun atanh(arg: StructureND): DoubleBufferND = mapInline(arg.toBufferND()) { kotlin.math.atanh(it) } + override fun power( + arg: StructureND, + pow: Number, + ): StructureND = if (pow is Int) { + mapInline(arg.toBufferND()) { it.pow(pow) } + } else { + mapInline(arg.toBufferND()) { it.pow(pow.toDouble()) } + } + public companion object : DoubleFieldOpsND() } @OptIn(UnstableKMathAPI::class) -public class DoubleFieldND(override val shape: Shape) : +public class DoubleFieldND(override val shape: ShapeND) : DoubleFieldOpsND(), FieldND, NumbersAddOps>, ExtendedField> { @@ -181,7 +201,7 @@ public class DoubleFieldND(override val shape: Shape) : it.kpow(pow) } - override fun power(arg: StructureND, pow: Number): DoubleBufferND = if(pow.isInteger()){ + override fun power(arg: StructureND, pow: Number): DoubleBufferND = if (pow.isInteger()) { power(arg, pow.toInt()) } else { val dpow = pow.toDouble() @@ -211,7 +231,8 @@ public class DoubleFieldND(override val shape: Shape) : public val DoubleField.ndAlgebra: DoubleFieldOpsND get() = DoubleFieldOpsND -public fun DoubleField.ndAlgebra(vararg shape: Int): DoubleFieldND = DoubleFieldND(shape) +public fun DoubleField.ndAlgebra(vararg shape: Int): DoubleFieldND = DoubleFieldND(ShapeND(shape)) +public fun DoubleField.ndAlgebra(shape: ShapeND): DoubleFieldND = DoubleFieldND(shape) /** * Produce a context for n-dimensional operations inside this real field @@ -219,5 +240,5 @@ public fun DoubleField.ndAlgebra(vararg shape: Int): DoubleFieldND = DoubleField @UnstableKMathAPI public inline fun DoubleField.withNdAlgebra(vararg shape: Int, action: DoubleFieldND.() -> R): R { contract { callsInPlace(action, InvocationKind.EXACTLY_ONCE) } - return DoubleFieldND(shape).run(action) + return DoubleFieldND(ShapeND(shape)).run(action) } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/IntRingND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/IntRingND.kt new file mode 100644 index 000000000..1491950d6 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/IntRingND.kt @@ -0,0 +1,50 @@ +/* + * Copyright 2018-2022 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.UnstableKMathAPI +import space.kscience.kmath.operations.IntRing +import space.kscience.kmath.operations.NumbersAddOps +import space.kscience.kmath.operations.bufferAlgebra +import space.kscience.kmath.structures.IntBuffer +import kotlin.contracts.InvocationKind +import kotlin.contracts.contract + +public class IntBufferND( + indexes: ShapeIndexer, + override val buffer: IntBuffer, +) : MutableBufferND(indexes, buffer) + +public sealed class IntRingOpsND : BufferedRingOpsND(IntRing.bufferAlgebra) { + + override fun structureND(shape: ShapeND, initializer: IntRing.(IntArray) -> Int): IntBufferND { + val indexer = indexerBuilder(shape) + return IntBufferND( + indexer, + IntBuffer(indexer.linearSize) { offset -> + elementAlgebra.initializer(indexer.index(offset)) + } + ) + } + + public companion object : IntRingOpsND() +} + +@OptIn(UnstableKMathAPI::class) +public class IntRingND( + override val shape: ShapeND +) : IntRingOpsND(), RingND, NumbersAddOps> { + + override fun number(value: Number): BufferND { + val int = value.toInt() // minimize conversions + return structureND(shape) { int } + } +} + +public inline fun IntRing.withNdAlgebra(vararg shape: Int, action: IntRingND.() -> R): R { + contract { callsInPlace(action, InvocationKind.EXACTLY_ONCE) } + return IntRingND(ShapeND(shape)).run(action) +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/PermutedStructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/PermutedStructureND.kt new file mode 100644 index 000000000..6c35e2f44 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/PermutedStructureND.kt @@ -0,0 +1,50 @@ +/* + * Copyright 2018-2022 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.PerformancePitfall + + +public class PermutedStructureND( + public val origin: StructureND, + public val permutation: (IntArray) -> IntArray, +) : StructureND { + + override val shape: ShapeND + get() = origin.shape + + @OptIn(PerformancePitfall::class) + override fun get(index: IntArray): T { + return origin[permutation(index)] + } +} + +public fun StructureND.permute( + permutation: (IntArray) -> IntArray, +): PermutedStructureND = PermutedStructureND(this, permutation) + +public class PermutedMutableStructureND( + public val origin: MutableStructureND, + override val shape: ShapeND = origin.shape, + public val permutation: (IntArray) -> IntArray, +) : MutableStructureND { + + + @OptIn(PerformancePitfall::class) + override fun set(index: IntArray, value: T) { + origin[permutation(index)] = value + } + + @OptIn(PerformancePitfall::class) + override fun get(index: IntArray): T { + return origin[permutation(index)] + } +} + +public fun MutableStructureND.permute( + newShape: ShapeND = shape, + permutation: (IntArray) -> IntArray, +): PermutedMutableStructureND = PermutedMutableStructureND(this, newShape, permutation) \ No newline at end of file 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 deleted file mode 100644 index d682d5e69..000000000 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Shape.kt +++ /dev/null @@ -1,35 +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.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 deleted file mode 100644 index 29701425f..000000000 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndexer.kt +++ /dev/null @@ -1,127 +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.nd - -import kotlin.native.concurrent.ThreadLocal - -/** - * A converter from linear index to multivariate index - */ -public interface ShapeIndexer : Iterable { - public val shape: Shape - - /** - * Get linear index from multidimensional index - */ - public fun offset(index: IntArray): Int - - /** - * Get multidimensional from linear - */ - public fun index(offset: Int): IntArray - - /** - * The size of linear buffer to accommodate all elements of ND-structure corresponding to strides - */ - public val linearSize: Int - - // TODO introduce a fast way to calculate index of the next element? - - /** - * Iterate over ND indices in a natural order - */ - public fun asSequence(): Sequence - - override fun iterator(): Iterator = asSequence().iterator() - - override fun equals(other: Any?): Boolean - override fun hashCode(): Int -} - -/** - * Linear transformation of indexes - */ -public abstract class Strides : ShapeIndexer { - /** - * Array strides - */ - public abstract val strides: IntArray - - public override fun offset(index: IntArray): Int = index.mapIndexed { i, value -> - if (value < 0 || value >= shape[i]) throw IndexOutOfBoundsException("Index $value out of shape bounds: (0,${this.shape[i]})") - value * strides[i] - }.sum() - - // TODO introduce a fast way to calculate index of the next element? - - /** - * Iterate over ND indices in a natural order - */ - public override fun asSequence(): Sequence = (0 until linearSize).asSequence().map(::index) -} - -/** - * Simple implementation of [Strides]. - */ -public class DefaultStrides(override val shape: IntArray) : Strides() { - override val linearSize: Int get() = strides[shape.size] - - /** - * Strides for memory access - */ - override val strides: IntArray by lazy { - sequence { - var current = 1 - yield(1) - - shape.forEach { - current *= it - yield(current) - } - }.toList().toIntArray() - } - - override fun index(offset: Int): IntArray { - val res = IntArray(shape.size) - var current = offset - var strideIndex = strides.size - 2 - - while (strideIndex >= 0) { - res[strideIndex] = (current / strides[strideIndex]) - current %= strides[strideIndex] - strideIndex-- - } - - return res - } - - override fun equals(other: Any?): Boolean { - if (this === other) return true - if (other !is DefaultStrides) return false - if (!shape.contentEquals(other.shape)) return false - return true - } - - override fun hashCode(): Int = shape.contentHashCode() - - - public companion object { - /** - * 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() - -/** - * 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/ShapeIndices.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndices.kt new file mode 100644 index 000000000..3a27614c5 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeIndices.kt @@ -0,0 +1,174 @@ +/* + * Copyright 2018-2022 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 kotlin.math.max +import kotlin.native.concurrent.ThreadLocal + +/** + * A converter from linear index to multivariate index + */ +public interface ShapeIndexer : Iterable { + public val shape: ShapeND + + /** + * Get linear index from multidimensional index + */ + public fun offset(index: IntArray): Int + + /** + * Get multidimensional from linear + */ + public fun index(offset: Int): IntArray + + /** + * The size of linear buffer to accommodate all elements of ND-structure corresponding to strides + */ + public val linearSize: Int + + // TODO introduce a fast way to calculate index of the next element? + + /** + * Iterate over ND indices in a natural order + */ + public fun asSequence(): Sequence + + override fun iterator(): Iterator = asSequence().iterator() + + override fun equals(other: Any?): Boolean + override fun hashCode(): Int +} + +/** + * Linear transformation of indexes + */ +public abstract class Strides : ShapeIndexer { + /** + * Array strides + */ + internal abstract val strides: IntArray + + public override fun offset(index: IntArray): Int { + var res = 0 + index.forEachIndexed { i, value -> + if (value !in 0 until shape[i]) throw IndexOutOfBoundsException("Index $value out of shape bounds: (0, ${this.shape[i]})") + res += value * strides[i] + + } + return res + } + + // TODO introduce a fast way to calculate index of the next element? + + /** + * Iterate over ND indices in a natural order + */ + public override fun asSequence(): Sequence = (0 until linearSize).asSequence().map(::index) + +} + +/** + * Column-first [Strides]. Columns are represented as continuous arrays + */ +public class ColumnStrides(override val shape: ShapeND) : Strides() { + override val linearSize: Int get() = strides[shape.size] + + /** + * Strides for memory access + */ + override val strides: IntArray = sequence { + var current = 1 + yield(1) + + shape.forEach { + current *= it + yield(current) + } + }.toList().toIntArray() + + override fun index(offset: Int): IntArray { + val res = IntArray(shape.size) + var current = offset + var strideIndex = strides.size - 2 + + while (strideIndex >= 0) { + res[strideIndex] = (current / strides[strideIndex]) + current %= strides[strideIndex] + strideIndex-- + } + + return res + } + + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other !is ColumnStrides) return false + return shape.contentEquals(other.shape) + } + + override fun hashCode(): Int = shape.contentHashCode() + + + public companion object +} + +/** + * This [Strides] implementation follows the last dimension first convention + * For more information: https://numpy.org/doc/stable/reference/generated/numpy.ndarray.strides.html + * + * @param shape the shape of the tensor. + */ +public class RowStrides(override val shape: ShapeND) : Strides() { + + override val strides: IntArray = run { + val nDim = shape.size + val res = IntArray(nDim) + if (nDim == 0) return@run res + + var current = nDim - 1 + res[current] = 1 + + while (current > 0) { + res[current - 1] = max(1, shape[current]) * res[current] + current-- + } + res + } + + override fun index(offset: Int): IntArray { + val res = IntArray(shape.size) + var current = offset + var strideIndex = 0 + + while (strideIndex < shape.size) { + res[strideIndex] = (current / strides[strideIndex]) + current %= strides[strideIndex] + strideIndex++ + } + return res + } + + override val linearSize: Int get() = shape.linearSize + + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other !is RowStrides) return false + return shape.contentEquals(other.shape) + } + + override fun hashCode(): Int = shape.contentHashCode() + + public companion object + +} + +@ThreadLocal +private val defaultStridesCache = HashMap() + +/** + * Cached builder for default strides + */ +public fun Strides(shape: ShapeND): Strides = defaultStridesCache.getOrPut(shape) { RowStrides(shape) } \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeND.kt new file mode 100644 index 000000000..d43ebaf1c --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShapeND.kt @@ -0,0 +1,102 @@ +/* + * Copyright 2018-2022 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.UnsafeKMathAPI +import kotlin.jvm.JvmInline + +/** + * A read-only ND shape + */ +@JvmInline +public value class ShapeND(@PublishedApi internal val array: IntArray) { + public val size: Int get() = array.size + public operator fun get(index: Int): Int = array[index] + override fun toString(): String = array.contentToString() +} + +public inline fun ShapeND.forEach(block: (value: Int) -> Unit): Unit = array.forEach(block) + +public inline fun ShapeND.forEachIndexed(block: (index: Int, value: Int) -> Unit): Unit = array.forEachIndexed(block) + +public infix fun ShapeND.contentEquals(other: ShapeND): Boolean = array.contentEquals(other.array) + +public fun ShapeND.contentHashCode(): Int = array.contentHashCode() + +public val ShapeND.indices: IntRange get() = array.indices +public val ShapeND.linearSize: Int get() = array.reduce(Int::times) + +public fun ShapeND.slice(range: IntRange): ShapeND = ShapeND(array.sliceArray(range)) + +public fun ShapeND.last(): Int = array.last() + +/** + * A shape including last [n] dimensions of this shape + */ +public fun ShapeND.last(n: Int): ShapeND = ShapeND(array.copyOfRange(size - n, size)) + +public fun ShapeND.first(): Int = array.first() + +/** + * A shape including first [n] dimensions of this shape + */ +public fun ShapeND.first(n: Int): ShapeND = ShapeND(array.copyOfRange(0, n)) + +public operator fun ShapeND.plus(add: IntArray): ShapeND = ShapeND(array + add) + +public operator fun ShapeND.plus(add: ShapeND): ShapeND = ShapeND(array + add.array) + +public fun ShapeND.isEmpty(): Boolean = size == 0 +public fun ShapeND.isNotEmpty(): Boolean = size > 0 + +public fun ShapeND.transposed(i: Int, j: Int): ShapeND = ShapeND(array.copyOf().apply { + val ith = get(i) + val jth = get(j) + set(i, jth) + set(j, ith) +}) + +public operator fun ShapeND.component1(): Int = get(0) +public operator fun ShapeND.component2(): Int = get(1) +public operator fun ShapeND.component3(): Int = get(2) + +/** + * Convert to array with protective copy + */ +public fun ShapeND.toArray(): IntArray = array.copyOf() + +@UnsafeKMathAPI +public fun ShapeND.asArray(): IntArray = array + +public fun ShapeND.asList(): List = array.asList() + + +/** + * 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: ShapeND, public val actual: ShapeND) : + RuntimeException("Shape $actual doesn't fit in expected shape ${expected}.") + +public class IndexOutOfShapeException(public val shape: ShapeND, public val index: IntArray) : + RuntimeException("Index ${index.contentToString()} is out of shape ${shape}") + +public fun ShapeND(shapeFirst: Int, vararg shapeRest: Int): ShapeND = ShapeND(intArrayOf(shapeFirst, *shapeRest)) + +public interface WithShape { + public val shape: ShapeND + + public val indices: ShapeIndexer get() = ColumnStrides(shape) +} + +internal fun requireIndexInShape(index: IntArray, shape: ShapeND) { + if (index.size != shape.size) throw IndexOutOfShapeException(shape, index) + shape.forEachIndexed { axis, axisShape -> + if (index[axis] !in 0 until axisShape) throw IndexOutOfShapeException(shape, index) + } +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShortRingND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShortRingND.kt index 8152adaa5..1b4647146 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShortRingND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/ShortRingND.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.NumbersAddOps import space.kscience.kmath.operations.ShortRing import space.kscience.kmath.operations.bufferAlgebra @@ -18,16 +18,17 @@ public sealed class ShortRingOpsND : BufferedRingOpsND(ShortRi @OptIn(UnstableKMathAPI::class) public class ShortRingND( - override val shape: Shape + override val shape: ShapeND ) : ShortRingOpsND(), RingND, NumbersAddOps> { override fun number(value: Number): BufferND { - val d = value.toShort() // minimize conversions - return structureND(shape) { d } + val short + = value.toShort() // minimize conversions + return structureND(shape) { short } } } public inline fun ShortRing.withNdAlgebra(vararg shape: Int, action: ShortRingND.() -> R): R { contract { callsInPlace(action, InvocationKind.EXACTLY_ONCE) } - return ShortRingND(shape).run(action) + return ShortRingND(ShapeND(shape)).run(action) } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure1D.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure1D.kt index 4ccb15eef..984b5ad0f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure1D.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/Structure1D.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.operations.asSequence import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.MutableBuffer @@ -18,6 +18,7 @@ import kotlin.jvm.JvmInline public interface Structure1D : StructureND, Buffer { override val dimension: Int get() = 1 + @PerformancePitfall override operator fun get(index: IntArray): T { require(index.size == 1) { "Index dimension mismatch. Expected 1 but found ${index.size}" } return get(index[0]) @@ -32,6 +33,8 @@ public interface Structure1D : StructureND, Buffer { * A mutable structure that is guaranteed to be one-dimensional */ public interface MutableStructure1D : Structure1D, MutableStructureND, MutableBuffer { + + @PerformancePitfall override operator fun set(index: IntArray, value: T) { require(index.size == 1) { "Index dimension mismatch. Expected 1 but found ${index.size}" } set(index[0], value) @@ -43,9 +46,10 @@ public interface MutableStructure1D : Structure1D, MutableStructureND, */ @JvmInline private value class Structure1DWrapper(val structure: StructureND) : Structure1D { - override val shape: IntArray get() = structure.shape + override val shape: ShapeND get() = structure.shape override val size: Int get() = structure.shape[0] + @PerformancePitfall override operator fun get(index: Int): T = structure[index] @PerformancePitfall @@ -56,13 +60,16 @@ private value class Structure1DWrapper(val structure: StructureND) : S * A 1D wrapper for a mutable nd-structure */ private class MutableStructure1DWrapper(val structure: MutableStructureND) : MutableStructure1D { - override val shape: IntArray get() = structure.shape + override val shape: ShapeND get() = structure.shape override val size: Int get() = structure.shape[0] @PerformancePitfall override fun elements(): Sequence> = structure.elements() + @PerformancePitfall override fun get(index: Int): T = structure[index] + + @PerformancePitfall override fun set(index: Int, value: T) { structure[intArrayOf(index)] = value } @@ -83,7 +90,7 @@ private class MutableStructure1DWrapper(val structure: MutableStructureND) */ @JvmInline private value class Buffer1DWrapper(val buffer: Buffer) : Structure1D { - override val shape: IntArray get() = intArrayOf(buffer.size) + override val shape: ShapeND get() = ShapeND(buffer.size) override val size: Int get() = buffer.size @PerformancePitfall @@ -95,7 +102,7 @@ private value class Buffer1DWrapper(val buffer: Buffer) : Structure1D< } internal class MutableBuffer1DWrapper(val buffer: MutableBuffer) : MutableStructure1D { - override val shape: IntArray get() = intArrayOf(buffer.size) + override val shape: ShapeND get() = ShapeND(buffer.size) override val size: Int get() = buffer.size @PerformancePitfall 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 a2fd83474..e006d09eb 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 @@ -1,12 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.structures.MutableListBuffer import space.kscience.kmath.structures.VirtualBuffer import kotlin.jvm.JvmInline @@ -28,7 +29,7 @@ public interface Structure2D : StructureND { */ public val colNum: Int - override val shape: IntArray get() = intArrayOf(rowNum, colNum) + override val shape: ShapeND get() = ShapeND(rowNum, colNum) /** * The buffer of rows of this structure. It gets elements from the structure dynamically. @@ -53,6 +54,7 @@ public interface Structure2D : StructureND { */ public operator fun get(i: Int, j: Int): T + @PerformancePitfall override operator fun get(index: IntArray): T { require(index.size == 2) { "Index dimension mismatch. Expected 2 but found ${index.size}" } return get(index[0], index[1]) @@ -84,15 +86,15 @@ public interface MutableStructure2D : Structure2D, MutableStructureND { * The buffer of rows of this structure. It gets elements from the structure dynamically. */ @PerformancePitfall - override val rows: List> - get() = List(rowNum) { i -> MutableBuffer1DWrapper(MutableListBuffer(colNum) { j -> get(i, j) }) } + override val rows: List> + get() = List(rowNum) { i -> MutableListBuffer(colNum) { j -> get(i, j) } } /** * The buffer of columns of this structure. It gets elements from the structure dynamically. */ @PerformancePitfall - override val columns: List> - get() = List(colNum) { j -> MutableBuffer1DWrapper(MutableListBuffer(rowNum) { i -> get(i, j) }) } + override val columns: List> + get() = List(colNum) { j -> MutableListBuffer(rowNum) { i -> get(i, j) } } } /** @@ -100,11 +102,12 @@ public interface MutableStructure2D : Structure2D, MutableStructureND { */ @JvmInline private value class Structure2DWrapper(val structure: StructureND) : Structure2D { - override val shape: Shape get() = structure.shape + override val shape: ShapeND get() = structure.shape override val rowNum: Int get() = shape[0] override val colNum: Int get() = shape[1] + @PerformancePitfall override operator fun get(i: Int, j: Int): T = structure[i, j] override fun getFeature(type: KClass): F? = structure.getFeature(type) @@ -117,17 +120,20 @@ private value class Structure2DWrapper(val structure: StructureND) : S * A 2D wrapper for a mutable nd-structure */ private class MutableStructure2DWrapper(val structure: MutableStructureND) : MutableStructure2D { - override val shape: Shape get() = structure.shape + override val shape: ShapeND get() = structure.shape override val rowNum: Int get() = shape[0] override val colNum: Int get() = shape[1] + @PerformancePitfall override operator fun get(i: Int, j: Int): T = structure[i, j] + @PerformancePitfall override fun set(index: IntArray, value: T) { structure[index] = value } + @PerformancePitfall override operator fun set(i: Int, j: Int, value: T) { structure[intArrayOf(i, j)] = value } 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 e14b8bf9d..e643186ba 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 @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.PerformancePitfall import space.kscience.kmath.linear.LinearSpace import space.kscience.kmath.misc.Feature import space.kscience.kmath.misc.Featured -import space.kscience.kmath.misc.PerformancePitfall import space.kscience.kmath.operations.Ring import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer @@ -33,7 +33,7 @@ public interface StructureND : Featured, WithShape { * The shape of structure i.e., non-empty sequence of non-negative integers that specify sizes of dimensions of * this structure. */ - override val shape: Shape + override val shape: ShapeND /** * The count of dimensions in this structure. It should be equal to size of [shape]. @@ -46,6 +46,7 @@ public interface StructureND : Featured, WithShape { * @param index the indices. * @return the value. */ + @PerformancePitfall public operator fun get(index: IntArray): T /** @@ -82,7 +83,7 @@ public interface StructureND : Featured, WithShape { public fun contentEquals( st1: StructureND, st2: StructureND, - tolerance: Double = 1e-11 + tolerance: Double = 1e-11, ): Boolean { if (st1 === st2) return true @@ -97,20 +98,27 @@ public interface StructureND : Featured, WithShape { /** * Debug output to string */ + @OptIn(PerformancePitfall::class) public fun toString(structure: StructureND<*>): String { 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 = "[\n", postfix = "\n]", separator = ",\n") { i -> + + 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() } } + else -> "..." } val className = structure::class.simpleName ?: "StructureND" - return "$className(shape=${structure.shape.contentToString()}, buffer=$bufferRepr)" + return "$className(shape=${structure.shape}, buffer=$bufferRepr)" } /** @@ -139,28 +147,28 @@ public interface StructureND : Featured, WithShape { ): BufferND = BufferND(strides, Buffer.auto(type, strides.linearSize) { i -> initializer(strides.index(i)) }) public fun buffered( - shape: IntArray, + shape: ShapeND, bufferFactory: BufferFactory = BufferFactory.boxing(), initializer: (IntArray) -> T, - ): BufferND = buffered(DefaultStrides(shape), bufferFactory, initializer) + ): BufferND = buffered(ColumnStrides(shape), bufferFactory, initializer) public inline fun auto( - shape: IntArray, + shape: ShapeND, crossinline initializer: (IntArray) -> T, - ): BufferND = auto(DefaultStrides(shape), initializer) + ): BufferND = auto(ColumnStrides(shape), initializer) @JvmName("autoVarArg") public inline fun auto( vararg shape: Int, crossinline initializer: (IntArray) -> T, ): BufferND = - auto(DefaultStrides(shape), initializer) + auto(ColumnStrides(ShapeND(shape)), initializer) public inline fun auto( type: KClass, vararg shape: Int, crossinline initializer: (IntArray) -> T, - ): BufferND = auto(type, DefaultStrides(shape), initializer) + ): BufferND = auto(type, ColumnStrides(ShapeND(shape)), initializer) } } @@ -208,8 +216,13 @@ public fun > LinearSpace>.contentEquals( * @param index the indices. * @return the value. */ +@PerformancePitfall public operator fun StructureND.get(vararg index: Int): T = get(index) +public operator fun StructureND.get(vararg index: Int): Double = getDouble(index) + +public operator fun StructureND.get(vararg index: Int): Int = getInt(index) + //@UnstableKMathAPI //public inline fun StructureND<*>.getFeature(): T? = getFeature(T::class) @@ -223,20 +236,14 @@ public interface MutableStructureND : StructureND { * @param index the indices. * @param value the value. */ + @PerformancePitfall public operator fun set(index: IntArray, value: T) } /** - * Transform a structure element-by element in place. + * Set value at specified indices */ -@OptIn(PerformancePitfall::class) -public inline fun MutableStructureND.mapInPlace(action: (index: IntArray, t: T) -> T): Unit = - elements().forEach { (index, oldValue) -> this[index] = action(index, oldValue) } - -public inline fun StructureND.zip( - struct: StructureND, - crossinline block: (T, T) -> T, -): StructureND { - require(shape.contentEquals(struct.shape)) { "Shape mismatch in structure combination" } - return StructureND.auto(shape) { block(this[it], struct[it]) } -} +@PerformancePitfall +public operator fun MutableStructureND.set(vararg index: Int, value: T) { + set(index, value) +} \ No newline at end of file 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 7e86ea73d..606b9a631 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 @@ -1,16 +1,19 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI public open class VirtualStructureND( - override val shape: Shape, + override val shape: ShapeND, public val producer: (IntArray) -> T, ) : StructureND { + + @PerformancePitfall override fun get(index: IntArray): T { requireIndexInShape(index, shape) return producer(index) @@ -19,12 +22,12 @@ public open class VirtualStructureND( @UnstableKMathAPI public class VirtualDoubleStructureND( - shape: Shape, + shape: ShapeND, producer: (IntArray) -> Double, ) : VirtualStructureND(shape, producer) @UnstableKMathAPI public class VirtualIntStructureND( - shape: Shape, + shape: ShapeND, producer: (IntArray) -> Int, ) : VirtualStructureND(shape, producer) \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/algebraNDExtentions.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/algebraNDExtentions.kt index 53f946fbd..f0d4bd7f5 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/algebraNDExtentions.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/algebraNDExtentions.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -15,9 +15,9 @@ public fun > AlgebraND.structureND( shapeFirst: Int, vararg shapeRest: Int, initializer: A.(IntArray) -> T -): StructureND = structureND(Shape(shapeFirst, *shapeRest), initializer) +): StructureND = structureND(ShapeND(shapeFirst, *shapeRest), initializer) -public fun > AlgebraND.zero(shape: Shape): StructureND = structureND(shape) { zero } +public fun > AlgebraND.zero(shape: ShapeND): StructureND = structureND(shape) { zero } @JvmName("zeroVarArg") public fun > AlgebraND.zero( @@ -25,7 +25,7 @@ public fun > AlgebraND.zero( vararg shapeRest: Int, ): StructureND = structureND(shapeFirst, *shapeRest) { zero } -public fun > AlgebraND.one(shape: Shape): StructureND = structureND(shape) { one } +public fun > AlgebraND.one(shape: ShapeND): StructureND = structureND(shape) { one } @JvmName("oneVarArg") public fun > AlgebraND.one( 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 index c9624dc4e..40db5187f 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/operationsND.kt @@ -1,10 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.PerformancePitfall + +@OptIn(PerformancePitfall::class) 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 -> @@ -19,6 +22,7 @@ public fun StructureND.roll(axis: Int, step: Int = 1): StructureND { } } +@OptIn(PerformancePitfall::class) 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})" } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/primitiveStructureND.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/primitiveStructureND.kt new file mode 100644 index 000000000..28e32363f --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/nd/primitiveStructureND.kt @@ -0,0 +1,45 @@ +/* + * Copyright 2018-2022 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.PerformancePitfall + +public interface StructureNDOfDouble : StructureND { + /** + * Guaranteed non-blocking access to content + */ + public fun getDouble(index: IntArray): Double +} + +/** + * Optimized method to access primitive without boxing if possible + */ +@OptIn(PerformancePitfall::class) +public fun StructureND.getDouble(index: IntArray): Double = + if (this is StructureNDOfDouble) getDouble(index) else get(index) + +public interface MutableStructureNDOfDouble : StructureNDOfDouble, MutableStructureND { + /** + * Guaranteed non-blocking access to content + */ + public fun setDouble(index: IntArray, value: Double) +} + +@OptIn(PerformancePitfall::class) +public fun MutableStructureND.getDouble(index: IntArray): Double = + if (this is StructureNDOfDouble) getDouble(index) else get(index) + + +public interface StructureNDOfInt : StructureND { + /** + * Guaranteed non-blocking access to content + */ + public fun getInt(index: IntArray): Int +} + +@OptIn(PerformancePitfall::class) +public fun StructureND.getInt(index: IntArray): Int = + if (this is StructureNDOfInt) getInt(index) else get(index) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/Algebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/Algebra.kt index a93b4365e..0960ab023 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/Algebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/Algebra.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Ring.Companion.optimizedPower import space.kscience.kmath.structures.MutableBufferFactory diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BigInt.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BigInt.kt index 9b6911f73..34a6d4a80 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BigInt.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/BigInt.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.BufferedRingOpsND import space.kscience.kmath.operations.BigInt.Companion.BASE import space.kscience.kmath.operations.BigInt.Companion.BASE_SIZE 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 a256fe7d1..af0bc4d9b 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -142,6 +142,9 @@ public open class BufferRingOps>( super.binaryOperationFunction(operation) } +public val IntRing.bufferAlgebra: BufferRingOps + get() = BufferRingOps(IntRing) + public val ShortRing.bufferAlgebra: BufferRingOps get() = BufferRingOps(ShortRing) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferField.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferField.kt index f2f7326aa..2e6b63a92 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferField.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/DoubleBufferField.kt @@ -1,12 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.DoubleField.pow import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer @@ -32,9 +30,9 @@ public class DoubleBufferField(public val size: Int) : ExtendedField): DoubleBuffer = super.atanh(arg) override fun power(arg: Buffer, pow: Number): DoubleBuffer = if (pow.isInteger()) { - arg.mapInline { it.pow(pow.toInt()) } + arg.map { it.pow(pow.toInt()) } } else { - arg.mapInline { + arg.map { if(it<0) throw IllegalArgumentException("Negative argument $it could not be raised to the fractional power") it.pow(pow.toDouble()) } @@ -42,103 +40,4 @@ public class DoubleBufferField(public val size: Int) : ExtendedField) -> Buffer = super.unaryOperationFunction(operation) - - // override fun number(value: Number): Buffer = DoubleBuffer(size) { value.toDouble() } -// -// override fun Buffer.unaryMinus(): Buffer = DoubleBufferOperations.run { -// -this@unaryMinus -// } -// -// override fun add(a: Buffer, b: Buffer): DoubleBuffer { -// require(a.size == size) { "The buffer size ${a.size} does not match context size $size" } -// return DoubleBufferOperations.add(a, b) -// } -// - -// -// override fun multiply(a: Buffer, b: Buffer): DoubleBuffer { -// require(a.size == size) { "The buffer size ${a.size} does not match context size $size" } -// return DoubleBufferOperations.multiply(a, b) -// } -// -// override fun divide(a: Buffer, b: Buffer): DoubleBuffer { -// require(a.size == size) { "The buffer size ${a.size} does not match context size $size" } -// return DoubleBufferOperations.divide(a, b) -// } -// -// override fun sin(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.sin(arg) -// } -// -// override fun cos(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.cos(arg) -// } -// -// override fun tan(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.tan(arg) -// } -// -// override fun asin(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.asin(arg) -// } -// -// override fun acos(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.acos(arg) -// } -// -// override fun atan(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.atan(arg) -// } -// -// override fun sinh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.sinh(arg) -// } -// -// override fun cosh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.cosh(arg) -// } -// -// override fun tanh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.tanh(arg) -// } -// -// override fun asinh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.asinh(arg) -// } -// -// override fun acosh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.acosh(arg) -// } -// -// override fun atanh(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.atanh(arg) -// } -// -// override fun power(arg: Buffer, pow: Number): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.power(arg, pow) -// } -// -// override fun exp(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.exp(arg) -// } -// -// override fun ln(arg: Buffer): DoubleBuffer { -// require(arg.size == size) { "The buffer size ${arg.size} does not match context size $size" } -// return DoubleBufferOperations.ln(arg) -// } - } \ No newline at end of file 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 669c0a390..74b41be9d 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 @@ -1,16 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.structures.Buffer -import space.kscience.kmath.structures.DoubleBuffer -import space.kscience.kmath.structures.MutableBufferFactory -import space.kscience.kmath.structures.asBuffer -import kotlin.math.* +import space.kscience.kmath.structures.* +import kotlin.math.pow +import kotlin.math.sqrt /** * [ExtendedFieldOps] over [DoubleBuffer]. @@ -19,10 +18,29 @@ public abstract class DoubleBufferOps : BufferAlgebra, Exte Norm, Double> { override val elementAlgebra: DoubleField get() = DoubleField + override val elementBufferFactory: MutableBufferFactory get() = elementAlgebra.bufferFactory - override fun Buffer.map(block: DoubleField.(Double) -> Double): DoubleBuffer = - mapInline { DoubleField.block(it) } + @Suppress("OVERRIDE_BY_INLINE") + @OptIn(UnstableKMathAPI::class) + final override inline fun Buffer.map(block: DoubleField.(Double) -> Double): DoubleBuffer = + DoubleArray(size) { DoubleField.block(getDouble(it)) }.asBuffer() + + + @OptIn(UnstableKMathAPI::class) + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun Buffer.mapIndexed(block: DoubleField.(index: Int, arg: Double) -> Double): DoubleBuffer = + DoubleBuffer(size) { DoubleField.block(it, getDouble(it)) } + + @OptIn(UnstableKMathAPI::class) + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun Buffer.zip( + other: Buffer, + block: DoubleField.(left: Double, right: Double) -> Double, + ): DoubleBuffer { + require(size == other.size) { "Incompatible buffer sizes. left: ${size}, right: ${other.size}" } + return DoubleBuffer(size) { DoubleField.block(getDouble(it), other.getDouble(it)) } + } override fun unaryOperationFunction(operation: String): (arg: Buffer) -> Buffer = super.unaryOperationFunction(operation) @@ -30,7 +48,7 @@ public abstract class DoubleBufferOps : BufferAlgebra, Exte override fun binaryOperationFunction(operation: String): (left: Buffer, right: Buffer) -> Buffer = super.binaryOperationFunction(operation) - override fun Buffer.unaryMinus(): DoubleBuffer = mapInline { -it } + override fun Buffer.unaryMinus(): DoubleBuffer = map { -it } override fun add(left: Buffer, right: Buffer): DoubleBuffer { require(right.size == left.size) { @@ -77,6 +95,7 @@ public abstract class DoubleBufferOps : BufferAlgebra, Exte // } else RealBuffer(DoubleArray(a.size) { a[it] / kValue }) // } + @UnstableKMathAPI override fun multiply(left: Buffer, right: Buffer): DoubleBuffer { require(right.size == left.size) { "The size of the first buffer ${left.size} should be the same as for second one: ${right.size} " @@ -101,49 +120,83 @@ public abstract class DoubleBufferOps : BufferAlgebra, Exte } else DoubleBuffer(DoubleArray(left.size) { left[it] / right[it] }) } - override fun sin(arg: Buffer): DoubleBuffer = arg.mapInline(::sin) + override fun sin(arg: Buffer): DoubleBuffer = arg.map { sin(it) } - override fun cos(arg: Buffer): DoubleBuffer = arg.mapInline(::cos) + override fun cos(arg: Buffer): DoubleBuffer = arg.map { cos(it) } - override fun tan(arg: Buffer): DoubleBuffer = arg.mapInline(::tan) + override fun tan(arg: Buffer): DoubleBuffer = arg.map { tan(it) } - override fun asin(arg: Buffer): DoubleBuffer = arg.mapInline(::asin) + override fun asin(arg: Buffer): DoubleBuffer = arg.map { asin(it) } - override fun acos(arg: Buffer): DoubleBuffer = arg.mapInline(::acos) + override fun acos(arg: Buffer): DoubleBuffer = arg.map { acos(it) } - override fun atan(arg: Buffer): DoubleBuffer = arg.mapInline(::atan) + override fun atan(arg: Buffer): DoubleBuffer = arg.map { atan(it) } - override fun sinh(arg: Buffer): DoubleBuffer = arg.mapInline(::sinh) + override fun sinh(arg: Buffer): DoubleBuffer = arg.map { sinh(it) } - override fun cosh(arg: Buffer): DoubleBuffer = arg.mapInline(::cosh) + override fun cosh(arg: Buffer): DoubleBuffer = arg.map { cosh(it) } - override fun tanh(arg: Buffer): DoubleBuffer = arg.mapInline(::tanh) + override fun tanh(arg: Buffer): DoubleBuffer = arg.map { tanh(it) } - override fun asinh(arg: Buffer): DoubleBuffer = arg.mapInline(::asinh) + override fun asinh(arg: Buffer): DoubleBuffer = arg.map { asinh(it) } - override fun acosh(arg: Buffer): DoubleBuffer = arg.mapInline(::acosh) + override fun acosh(arg: Buffer): DoubleBuffer = arg.map { acosh(it) } - override fun atanh(arg: Buffer): DoubleBuffer = arg.mapInline(::atanh) + override fun atanh(arg: Buffer): DoubleBuffer = arg.map { atanh(it) } - override fun exp(arg: Buffer): DoubleBuffer = arg.mapInline(::exp) + override fun exp(arg: Buffer): DoubleBuffer = arg.map { exp(it) } - override fun ln(arg: Buffer): DoubleBuffer = arg.mapInline(::ln) + override fun ln(arg: Buffer): DoubleBuffer = arg.map { ln(it) } override fun norm(arg: Buffer): Double = DoubleL2Norm.norm(arg) - override fun scale(a: Buffer, value: Double): DoubleBuffer = a.mapInline { it * value } + override fun scale(a: Buffer, value: Double): DoubleBuffer = a.map { it * value } - public companion object : DoubleBufferOps() { - public inline fun Buffer.mapInline(block: (Double) -> Double): DoubleBuffer = - if (this is DoubleBuffer) { - DoubleArray(size) { block(array[it]) }.asBuffer() - } else { - DoubleArray(size) { block(get(it)) }.asBuffer() - } + override fun power(arg: Buffer, pow: Number): Buffer = if (pow is Int) { + arg.map { it.pow(pow) } + } else { + arg.map { it.pow(pow.toDouble()) } } + + public companion object : DoubleBufferOps() } public object DoubleL2Norm : Norm, Double> { override fun norm(arg: Point): Double = sqrt(arg.fold(0.0) { acc: Double, d: Double -> acc + d.pow(2) }) } +public fun DoubleBufferOps.sum(buffer: Buffer): Double = buffer.reduce(Double::plus) + +/** + * Sum of elements using given [conversion] + */ +public inline fun DoubleBufferOps.sumOf(buffer: Buffer, conversion: (T) -> Double): Double = + buffer.fold(0.0) { acc, value -> acc + conversion(value) } + +public fun DoubleBufferOps.average(buffer: Buffer): Double = sum(buffer) / buffer.size + +/** + * Average of elements using given [conversion] + */ +public inline fun DoubleBufferOps.averageOf(buffer: Buffer, conversion: (T) -> Double): Double = + sumOf(buffer, conversion) / buffer.size + +public fun DoubleBufferOps.dispersion(buffer: Buffer): Double { + val av = average(buffer) + return buffer.fold(0.0) { acc, value -> acc + (value - av).pow(2) } / buffer.size +} + +public fun DoubleBufferOps.std(buffer: Buffer): Double = sqrt(dispersion(buffer)) + +public fun DoubleBufferOps.covariance(x: Buffer, y: Buffer): Double { + require(x.size == y.size) { "Expected buffers of the same size, but x.size == ${x.size} and y.size == ${y.size}" } + val xMean = average(x) + val yMean = average(y) + var sum = 0.0 + x.indices.forEach { + sum += (x[it] - xMean) * (y[it] - yMean) + } + return sum / (x.size - 1) +} + + diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/LogicAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/LogicAlgebra.kt index 9037525e1..7aa5aed80 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/LogicAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/LogicAlgebra.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol import space.kscience.kmath.expressions.symbol -import space.kscience.kmath.misc.UnstableKMathAPI /** * An algebra for generic boolean logic diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/NumericAlgebra.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/NumericAlgebra.kt index d0405c705..9bcfb00a2 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/NumericAlgebra.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/NumericAlgebra.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import kotlin.math.E import kotlin.math.PI diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/OptionalOperations.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/OptionalOperations.kt index 709506fc4..c24394add 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/OptionalOperations.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/OptionalOperations.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/algebraExtensions.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/algebraExtensions.kt index 539440de9..ddf599240 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/algebraExtensions.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/algebraExtensions.kt @@ -1,10 +1,25 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.structures.Buffer + +/** + * Returns the sum of all elements in the iterable in this [Group]. + * + * @receiver the algebra that provides addition. + * @param data the iterable to sum up. + * @return the sum. + */ +@PerformancePitfall("Potential boxing access to buffer elements") +public fun Group.sum(data: Buffer): T = data.fold(zero) { left, right -> + add(left, right) +} + /** * Returns the sum of all elements in the iterable in this [Group]. * @@ -29,6 +44,18 @@ public fun Group.sum(data: Sequence): T = data.fold(zero) { left, righ add(left, right) } +/** + * Returns an average value of elements in the iterable in this [Group]. + * + * @receiver the algebra that provides addition and division. + * @param data the iterable to find average. + * @return the average value. + * @author Iaroslav Postovalov + */ +@PerformancePitfall("Potential boxing access to buffer elements") +public fun S.average(data: Buffer): T where S : Group, S : ScaleOperations = + sum(data) / data.size + /** * Returns an average value of elements in the iterable in this [Group]. * @@ -65,6 +92,17 @@ public fun > Group.abs(value: T): T = if (value > zero) val */ public fun Iterable.sumWith(group: Group): T = group.sum(this) +/** + * Sum extracted elements of [Iterable] with given [group] + * + * @receiver the collection to sum up. + * @param group tha algebra that provides addition + * @param extractor the (inline) lambda function to extract value + */ +public inline fun Iterable.sumWithGroupOf(group: Group, extractor: (T) -> R): R = this.fold(group.zero) { left: R, right: T -> + group.add(left, extractor(right)) +} + /** * Returns the sum of all elements in the sequence in provided space. * @@ -95,4 +133,3 @@ public fun Iterable.averageWith(space: S): T where S : Group, S : S */ public fun Sequence.averageWith(space: S): T where S : Group, S : ScaleOperations = space.average(this) - diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/numbers.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/numbers.kt index c108aa729..224ca1daf 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/numbers.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/numbers.kt @@ -1,13 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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:Suppress("NOTHING_TO_INLINE") package space.kscience.kmath.operations import space.kscience.kmath.structures.* import kotlin.math.pow as kpow + /** * Advanced Number-like semifield that implements basic operations. */ @@ -15,7 +16,8 @@ public interface ExtendedFieldOps : FieldOps, TrigonometricOperations, ExponentialOperations, - ScaleOperations { + ScaleOperations, + PowerOperations { override fun tan(arg: T): T = sin(arg) / cos(arg) override fun tanh(arg: T): T = sinh(arg) / cosh(arg) @@ -41,7 +43,7 @@ public interface ExtendedFieldOps : /** * Advanced Number-like field that implements basic operations. */ -public interface ExtendedField : ExtendedFieldOps, Field, PowerOperations, NumericAlgebra { +public interface ExtendedField : ExtendedFieldOps, Field, NumericAlgebra { override fun sinh(arg: T): T = (exp(arg) - exp(-arg)) / 2.0 override fun cosh(arg: T): T = (exp(arg) + exp(-arg)) / 2.0 override fun tanh(arg: T): T = (exp(arg) - exp(-arg)) / (exp(-arg) + exp(arg)) @@ -64,7 +66,7 @@ public interface ExtendedField : ExtendedFieldOps, Field, PowerOperatio /** * A field for [Double] without boxing. Does not produce appropriate field element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object DoubleField : ExtendedField, Norm, ScaleOperations { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::DoubleBuffer) @@ -124,7 +126,7 @@ public val Double.Companion.algebra: DoubleField get() = DoubleField /** * A field for [Float] without boxing. Does not produce appropriate field element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object FloatField : ExtendedField, Norm { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::FloatBuffer) @@ -180,7 +182,7 @@ public val Float.Companion.algebra: FloatField get() = FloatField /** * A field for [Int] without boxing. Does not produce corresponding ring element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object IntRing : Ring, Norm, NumericAlgebra { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::IntBuffer) @@ -203,7 +205,7 @@ public val Int.Companion.algebra: IntRing get() = IntRing /** * A field for [Short] without boxing. Does not produce appropriate ring element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object ShortRing : Ring, Norm, NumericAlgebra { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::ShortBuffer) @@ -226,7 +228,7 @@ public val Short.Companion.algebra: ShortRing get() = ShortRing /** * A field for [Byte] without boxing. Does not produce appropriate ring element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object ByteRing : Ring, Norm, NumericAlgebra { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::ByteBuffer) @@ -249,7 +251,7 @@ public val Byte.Companion.algebra: ByteRing get() = ByteRing /** * A field for [Double] without boxing. Does not produce appropriate ring element. */ -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") +@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") public object LongRing : Ring, Norm, NumericAlgebra { override val bufferFactory: MutableBufferFactory = MutableBufferFactory(::LongBuffer) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ArrayBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ArrayBuffer.kt index 3528b0460..8e81dd941 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ArrayBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ArrayBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 5757848fe..cef8d1d4d 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 @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.operations.WithSize import space.kscience.kmath.operations.asSequence import kotlin.jvm.JvmInline import kotlin.reflect.KClass @@ -50,11 +51,11 @@ public fun interface MutableBufferFactory : BufferFactory { * * @param T the type of elements contained in the buffer. */ -public interface Buffer { +public interface Buffer : WithSize { /** * The size of this buffer. */ - public val size: Int + override val size: Int /** * Gets element at given index. @@ -64,7 +65,7 @@ public interface Buffer { /** * Iterates over all elements. */ - public operator fun iterator(): Iterator + public operator fun iterator(): Iterator = indices.asSequence().map(::get).iterator() override fun toString(): String @@ -114,7 +115,6 @@ public interface Buffer { * * The [size] is specified, and each element is calculated by calling the specified [initializer] function. */ - @Suppress("UNCHECKED_CAST") public inline fun auto(size: Int, initializer: (Int) -> T): Buffer = auto(T::class, size, initializer) } @@ -123,7 +123,14 @@ public interface Buffer { /** * Returns an [IntRange] of the valid indices for this [Buffer]. */ -public val Buffer<*>.indices: IntRange get() = 0 until size +public val Buffer.indices: IntRange get() = 0 until size + +public operator fun Buffer.get(index: UInt): T = get(index.toInt()) + +/** + * if index is in range of buffer, return the value. Otherwise, return null. + */ +public fun Buffer.getOrNull(index: Int): T? = if (index in indices) get(index) else null public fun Buffer.first(): T { require(size > 0) { "Can't get the first element of empty buffer" } diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferAccessor2D.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferAccessor2D.kt index 4d04a5235..48f3e919b 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferAccessor2D.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferAccessor2D.kt @@ -1,14 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures -import space.kscience.kmath.nd.DefaultStrides -import space.kscience.kmath.nd.Structure2D -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.* /** * A context that allows to operate on a [MutableBuffer] as on 2d array @@ -31,7 +28,7 @@ internal class BufferAccessor2D( //TODO optimize wrapper fun MutableBuffer.collect(): Structure2D = StructureND.buffered( - DefaultStrides(intArrayOf(rowNum, colNum)), + ColumnStrides(ShapeND(rowNum, colNum)), factory ) { (i, j) -> get(i, j) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferView.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferView.kt new file mode 100644 index 000000000..02fd2600d --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/BufferView.kt @@ -0,0 +1,192 @@ +package space.kscience.kmath.structures + +import space.kscience.kmath.UnstableKMathAPI + +/** + * A buffer that wraps an original buffer + */ +public interface BufferView : Buffer { + public val origin: Buffer + + /** + * Get the index in [origin] buffer from index in this buffer. + * Return -1 if element not present in the original buffer + * This method should be used internally to optimize non-boxing access. + */ + @UnstableKMathAPI + public fun originIndex(index: Int): Int + + @OptIn(UnstableKMathAPI::class) + override fun get(index: Int): T = origin[originIndex(index)] +} + +/** + * A zero-copy buffer that "sees" only part of original buffer. Slice can't go beyond original buffer borders. + */ +public class BufferSlice( + override val origin: Buffer, + public val offset: Int = 0, + override val size: Int, +) : BufferView { + + init { + require(size > 0) { "Size must be positive" } + require(offset + size <= origin.size) { + "End of buffer ${offset + size} is beyond the end of origin buffer size ${origin.size}" + } + } + + override fun get(index: Int): T = if (index >= size) { + throw IndexOutOfBoundsException("$index is out of ${0 until size} rage") + } else { + origin[index + offset] + } + + override fun iterator(): Iterator = + (offset until (offset + size)).asSequence().map { origin[it] }.iterator() + + @UnstableKMathAPI + override fun originIndex(index: Int): Int = if (index >= size) -1 else index - offset + + override fun toString(): String = "$origin[$offset..${offset + size}" +} + +/** + * An expanded buffer that could include the whole initial buffer or its part and fills all space beyond it borders with [defaultValue]. + * + * The [offset] parameter shows the shift of expanded buffer start relative to origin start and could be both positive and negative. + */ +public class BufferExpanded( + override val origin: Buffer, + private val defaultValue: T, + public val offset: Int = 0, + override val size: Int = origin.size, +) : BufferView { + + init { + require(size > 0) { "Size must be positive" } + } + + override fun get(index: Int): T = when (index) { + !in 0 until size -> throw IndexOutOfBoundsException("Index $index is not in $indices") + in -offset until origin.size - offset -> origin[index + offset] + else -> defaultValue + } + + @UnstableKMathAPI + override fun originIndex(index: Int): Int = if (index in -offset until origin.size - offset) index + offset else -1 + + override fun toString(): String = "$origin[$offset..${offset + size}]" +} + +/** + * Zero-copy select a slice inside the original buffer + */ +public fun Buffer.slice(range: IntRange): BufferView = if (this is BufferSlice) { + BufferSlice( + origin, + this.offset + range.first, + (range.last - range.first) + 1 + ) +} else { + BufferSlice( + this, + range.first, + (range.last - range.first) + 1 + ) +} + +/** + * Resize original buffer to a given range using given [range], filling additional segments with [defaultValue]. + * Range left border could be negative to designate adding new blank segment to the beginning of the buffer + */ +public fun Buffer.expand( + range: IntRange, + defaultValue: T, +): BufferView = if (range.first >= 0 && range.last < size) { + BufferSlice( + this, + range.first, + (range.last - range.first) + 1 + ) +} else { + BufferExpanded( + this, + defaultValue, + range.first, + (range.last - range.first) + 1 + ) +} + +/** + * A [BufferView] that overrides indexing of the original buffer + */ +public class PermutedBuffer( + override val origin: Buffer, + private val permutations: IntArray, +) : BufferView { + init { + permutations.forEach { index -> + if (index !in origin.indices) { + throw IndexOutOfBoundsException("Index $index is not in ${origin.indices}") + } + } + } + + override val size: Int get() = permutations.size + + override fun get(index: Int): T = origin[permutations[index]] + + override fun iterator(): Iterator = permutations.asSequence().map { origin[it] }.iterator() + + @UnstableKMathAPI + override fun originIndex(index: Int): Int = if (index in permutations.indices) permutations[index] else -1 + + override fun toString(): String = Buffer.toString(this) +} + +/** + * Created a permuted view of given buffer using provided [indices] + */ +public fun Buffer.permute(indices: IntArray): PermutedBuffer = + PermutedBuffer(this, indices) + +/** + * A [BufferView] that overrides indexing of the original buffer + */ +public class PermutedMutableBuffer( + override val origin: MutableBuffer, + private val permutations: IntArray, +) : BufferView, MutableBuffer { + init { + permutations.forEach { index -> + if (index !in origin.indices) { + throw IndexOutOfBoundsException("Index $index is not in ${origin.indices}") + } + } + } + + override val size: Int get() = permutations.size + + override fun get(index: Int): T = origin[permutations[index]] + + override fun set(index: Int, value: T) { + origin[permutations[index]] = value + } + + override fun copy(): MutableBuffer = PermutedMutableBuffer(origin.copy(), permutations) + //TODO Probably could be optimized + + override fun iterator(): Iterator = permutations.asSequence().map { origin[it] }.iterator() + + @UnstableKMathAPI + override fun originIndex(index: Int): Int = if (index in permutations.indices) permutations[index] else -1 + + override fun toString(): String = Buffer.toString(this) +} + +/** + * Created a permuted mutable view of given buffer using provided [indices] + */ +public fun MutableBuffer.permute(indices: IntArray): PermutedMutableBuffer = + PermutedMutableBuffer(this, indices) \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ByteBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ByteBuffer.kt index e7bf2b47c..2be17c5e4 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ByteBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ByteBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/DoubleBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/DoubleBuffer.kt index f4388a477..1696d5055 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/DoubleBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/DoubleBuffer.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.operations.BufferTransform import kotlin.jvm.JvmInline /** @@ -13,7 +14,7 @@ import kotlin.jvm.JvmInline * @property array the underlying array. */ @JvmInline -public value class DoubleBuffer(public val array: DoubleArray) : MutableBuffer { +public value class DoubleBuffer(public val array: DoubleArray) : PrimitiveBuffer { override val size: Int get() = array.size override operator fun get(index: Int): Double = array[index] @@ -28,7 +29,7 @@ public value class DoubleBuffer(public val array: DoubleArray) : MutableBuffer Double): DoubleBuffer = DoubleBuffer(DoubleArray(size) { init(it) }) +public inline fun DoubleBuffer(size: Int, init: (Int) -> Double): DoubleBuffer = + DoubleBuffer(DoubleArray(size) { init(it) }) /** * Returns a new [DoubleBuffer] of given elements. */ public fun DoubleBuffer(vararg doubles: Double): DoubleBuffer = DoubleBuffer(doubles) -/** - * Simplified [DoubleBuffer] to array comparison - */ -public fun DoubleBuffer.contentEquals(vararg doubles: Double): Boolean = array.contentEquals(doubles) - /** * Returns a new [DoubleArray] containing all the elements of this [Buffer]. */ public fun Buffer.toDoubleArray(): DoubleArray = when (this) { - is DoubleBuffer -> array.copyOf() + is DoubleBuffer -> array else -> DoubleArray(size, ::get) } +/** + * Represent this buffer as [DoubleBuffer]. Does not guarantee that changes in the original buffer are reflected on this buffer. + */ +public fun Buffer.toDoubleBuffer(): DoubleBuffer = when (this) { + is DoubleBuffer -> this + else -> DoubleArray(size, ::get).asBuffer() +} + /** * Returns [DoubleBuffer] over this array. * @@ -67,3 +72,10 @@ public fun Buffer.toDoubleArray(): DoubleArray = when (this) { * @return the new buffer. */ public fun DoubleArray.asBuffer(): DoubleBuffer = DoubleBuffer(this) + + +public fun interface DoubleBufferTransform : BufferTransform { + public fun transform(arg: DoubleBuffer): DoubleBuffer + + override fun transform(arg: Buffer): DoubleBuffer = arg.toDoubleBuffer() +} diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FlaggedBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FlaggedBuffer.kt index b3c537280..d99e02996 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FlaggedBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FlaggedBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FloatBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FloatBuffer.kt index e7e98fc71..f1533ee3a 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FloatBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/FloatBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -14,7 +14,7 @@ import kotlin.jvm.JvmInline * @author Iaroslav Postovalov */ @JvmInline -public value class FloatBuffer(public val array: FloatArray) : MutableBuffer { +public value class FloatBuffer(public val array: FloatArray) : PrimitiveBuffer { override val size: Int get() = array.size override operator fun get(index: Int): Float = array[index] diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/IntBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/IntBuffer.kt index 35b722e2b..0de7119b1 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/IntBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/IntBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,7 +13,7 @@ import kotlin.jvm.JvmInline * @property array the underlying array. */ @JvmInline -public value class IntBuffer(public val array: IntArray) : MutableBuffer { +public value class IntBuffer(public val array: IntArray) : PrimitiveBuffer { override val size: Int get() = array.size override operator fun get(index: Int): Int = array[index] @@ -24,8 +24,7 @@ public value class IntBuffer(public val array: IntArray) : MutableBuffer { override operator fun iterator(): IntIterator = array.iterator() - override fun copy(): MutableBuffer = - IntBuffer(array.copyOf()) + override fun copy(): IntBuffer = IntBuffer(array.copyOf()) } /** diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ListBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ListBuffer.kt index 65d9dc77d..fbc9a489b 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ListBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ListBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/LongBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/LongBuffer.kt index c69f4646d..9f77fc9d8 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/LongBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/LongBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,7 +13,7 @@ import kotlin.jvm.JvmInline * @property array the underlying array. */ @JvmInline -public value class LongBuffer(public val array: LongArray) : MutableBuffer { +public value class LongBuffer(public val array: LongArray) : PrimitiveBuffer { override val size: Int get() = array.size override operator fun get(index: Int): Long = array[index] diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MemoryBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MemoryBuffer.kt index 1dadaf7d4..cbfd6b9cd 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MemoryBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MemoryBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -17,9 +17,7 @@ import space.kscience.kmath.memory.* public open class MemoryBuffer(protected val memory: Memory, protected val spec: MemorySpec) : Buffer { override val size: Int get() = memory.size / spec.objectSize - private val reader: MemoryReader = memory.reader() - - override operator fun get(index: Int): T = reader.read(spec, spec.objectSize * index) + override operator fun get(index: Int): T = memory.read { read(spec, spec.objectSize * index) } override operator fun iterator(): Iterator = (0 until size).asSequence().map { get(it) }.iterator() override fun toString(): String = Buffer.toString(this) diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MutableBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MutableBuffer.kt index 429c1a64b..c0bfc6ecc 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MutableBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/MutableBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -94,4 +94,7 @@ public interface MutableBuffer : Buffer { public inline fun auto(size: Int, initializer: (Int) -> T): MutableBuffer = auto(T::class, size, initializer) } -} \ No newline at end of file +} + + +public sealed interface PrimitiveBuffer: MutableBuffer \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ShortBuffer.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ShortBuffer.kt index 20691511b..7dbb2b58e 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ShortBuffer.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/ShortBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/bufferExtensions.kt similarity index 65% rename from kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt rename to kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/bufferExtensions.kt index 46abc0266..6a7b6d836 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/operations/bufferOperation.kt +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/bufferExtensions.kt @@ -1,22 +1,26 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.structures.* /** - * Typealias for buffer transformations. + * Type alias for buffer transformations. */ -public typealias BufferTransform = (Buffer) -> Buffer +public fun interface BufferTransform { + public fun transform(arg: Buffer): Buffer +} -/** - * Typealias for buffer transformations with suspend function. - */ -public typealias SuspendBufferTransform = suspend (Buffer) -> Buffer +///** +// * Type alias for buffer transformations with suspend function. +// */ +//public fun interface SuspendBufferTransform{ +// public suspend fun transform(arg: Buffer): Buffer +//} /** @@ -57,18 +61,18 @@ public fun Buffer.toMutableList(): MutableList = when (this) { */ @UnstableKMathAPI public inline fun Buffer.toTypedArray(): Array = Array(size, ::get) - -/** - * 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 = - Buffer.auto(size) { block(get(it)) } +// +///** +// * 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 = +// 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.mapToBuffer( bufferFactory: BufferFactory, crossinline block: (T) -> R, ): Buffer = bufferFactory(size) { block(get(it)) } @@ -77,23 +81,24 @@ public inline fun Buffer.map( * 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( +public inline fun Buffer.mapIndexedToBuffer( 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 = Buffer.auto(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 = Buffer.auto(size) { block(it, get(it)) } /** * Fold given buffer according to [operation] */ public inline fun Buffer.fold(initial: R, operation: (acc: R, T) -> R): R { + if (size == 0) return initial var accumulator = initial for (index in this.indices) accumulator = operation(accumulator, get(index)) return accumulator @@ -103,18 +108,31 @@ public inline fun Buffer.fold(initial: R, operation: (acc: R, T) -> R) * Fold given buffer according to indexed [operation] */ public inline fun Buffer.foldIndexed(initial: R, operation: (index: Int, acc: R, T) -> R): R { + if (size == 0) return initial var accumulator = initial for (index in this.indices) accumulator = operation(index, accumulator, get(index)) return accumulator } +/** + * Reduce a buffer from left to right according to [operation] + */ +public inline fun Buffer.reduce(operation: (left: T, value: T) -> T): T { + require(size > 0) { "Buffer must have elements" } + var current = get(0) + for (i in 1 until size) { + current = operation(current, get(i)) + } + return current +} + /** * Zip two buffers using given [transform]. */ @UnstableKMathAPI -public inline fun Buffer.zip( +public inline fun Buffer.combineToBuffer( other: Buffer, - bufferFactory: BufferFactory = BufferFactory.auto(), + bufferFactory: BufferFactory, 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/bufferPrimitiveAccess.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/bufferPrimitiveAccess.kt new file mode 100644 index 000000000..353892105 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/bufferPrimitiveAccess.kt @@ -0,0 +1,37 @@ +package space.kscience.kmath.structures + +import space.kscience.kmath.UnstableKMathAPI + +/** + * Non-boxing access to primitive [Double] + */ +@UnstableKMathAPI +public fun Buffer.getDouble(index: Int): Double = if (this is BufferView) { + val originIndex = originIndex(index) + if (originIndex >= 0) { + origin.getDouble(originIndex) + } else { + get(index) + } +} else if (this is DoubleBuffer) { + array[index] +} else { + get(index) +} + +/** + * Non-boxing access to primitive [Int] + */ +@UnstableKMathAPI +public fun Buffer.getInt(index: Int): Int = if (this is BufferView) { + val originIndex = originIndex(index) + if (originIndex >= 0) { + origin.getInt(originIndex) + } else { + get(index) + } +} else if (this is IntBuffer) { + array[index] +} else { + get(index) +} \ No newline at end of file diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/types.kt b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/types.kt new file mode 100644 index 000000000..4ace17538 --- /dev/null +++ b/kmath-core/src/commonMain/kotlin/space/kscience/kmath/structures/types.kt @@ -0,0 +1,20 @@ +/* + * Copyright 2018-2022 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.structures + + +public typealias Float32 = Float +public typealias Float64 = Double + +public typealias Int8 = Byte +public typealias Int16 = Short +public typealias Int32 = Int +public typealias Int64 = Long + +public typealias UInt8 = UByte +public typealias UInt16 = UShort +public typealias UInt32 = UInt +public typealias UInt64 = ULong \ No newline at end of file diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DSTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DSTest.kt index b6581e503..871119f48 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DSTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/DSTest.kt @@ -1,15 +1,14 @@ /* - * 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. + * Copyright 2018-2022 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.expressions -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.structures.DoubleBuffer import kotlin.contracts.InvocationKind import kotlin.contracts.contract import kotlin.test.Test @@ -22,7 +21,7 @@ internal inline fun diff( block: DSField.() -> Unit, ) { contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - DSField(DoubleField, order, mapOf(*parameters), ::DoubleBuffer).block() + DSField(DoubleField, order, mapOf(*parameters)).block() } internal class DSTest { @@ -45,7 +44,7 @@ internal class DSTest { @Test fun dsExpressionTest() { - val f = DSFieldExpression(DoubleField, ::DoubleBuffer) { + val f = DSFieldExpression(DoubleField) { val x by binding val y by binding x.pow(2) + 2 * x * y + y.pow(2) + 1 diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/ExpressionFieldTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/ExpressionFieldTest.kt index 80c5943cf..def9f91a6 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/ExpressionFieldTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/ExpressionFieldTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/InterpretTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/InterpretTest.kt index 156334b2e..83f00ce6c 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/InterpretTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/InterpretTest.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.expressions +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.expressions.Symbol.Companion.x -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.BooleanAlgebra import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.invoke diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/SimpleAutoDiffTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/SimpleAutoDiffTest.kt index 201890933..1618296be 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/SimpleAutoDiffTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/expressions/SimpleAutoDiffTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/DoubleLUSolverTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/DoubleLUSolverTest.kt index 70e010f2e..4d05f9043 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/DoubleLUSolverTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/DoubleLUSolverTest.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.algebra import kotlin.test.Test diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/MatrixTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/MatrixTest.kt index 25d187bf0..531aee259 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/MatrixTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/linear/MatrixTest.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.linear -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.as2D import space.kscience.kmath.operations.algebra diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/CumulativeKtTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/CumulativeKtTest.kt index e5f3f337f..811f2e87f 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/CumulativeKtTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/misc/CumulativeKtTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 4a724ac5f..dd97df1e8 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 @@ -1,10 +1,11 @@ /* - * 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. + * Copyright 2018-2022 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.misc +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.misc.PermSortTest.Platform.* import space.kscience.kmath.structures.IntBuffer import space.kscience.kmath.structures.asBuffer @@ -14,6 +15,7 @@ import kotlin.test.assertContentEquals import kotlin.test.assertEquals import kotlin.test.assertTrue +@OptIn(UnstableKMathAPI::class) class PermSortTest { private enum class Platform { 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 index 25b062b44..e909a2aea 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/NdOperationsTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/StridesTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/StridesTest.kt new file mode 100644 index 000000000..e6335f652 --- /dev/null +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/nd/StridesTest.kt @@ -0,0 +1,38 @@ +/* + * Copyright 2018-2022 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 kotlin.test.Test + +class StridesTest { + @Test + fun checkRowBasedStrides() { + val strides = RowStrides(ShapeND(3, 3)) + var counter = 0 + for(i in 0..2){ + for(j in 0..2){ +// print(strides.offset(intArrayOf(i,j)).toString() + "\t") + require(strides.offset(intArrayOf(i,j)) == counter) + counter++ + } + println() + } + } + + @Test + fun checkColumnBasedStrides() { + val strides = ColumnStrides(ShapeND(3, 3)) + var counter = 0 + for(i in 0..2){ + for(j in 0..2){ +// print(strides.offset(intArrayOf(i,j)).toString() + "\t") + require(strides.offset(intArrayOf(j,i)) == counter) + counter++ + } + println() + } + } +} \ No newline at end of file diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntAlgebraTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntAlgebraTest.kt index 0527f5252..06a9ab439 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntAlgebraTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntAlgebraTest.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.testutils.RingVerifier import kotlin.math.pow import kotlin.test.Test diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConstructorTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConstructorTest.kt index eec3dc3bf..786c68c70 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConstructorTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConstructorTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConversionsTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConversionsTest.kt index 85f368f3e..36f00dc75 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConversionsTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntConversionsTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntOperationsTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntOperationsTest.kt index 26d6af224..8a6116605 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntOperationsTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/BigIntOperationsTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/DoubleFieldTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/DoubleFieldTest.kt index 76171fedd..688daa7fe 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/DoubleFieldTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/operations/DoubleFieldTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/BufferExpandedTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/BufferExpandedTest.kt new file mode 100644 index 000000000..04671e040 --- /dev/null +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/BufferExpandedTest.kt @@ -0,0 +1,27 @@ +package space.kscience.kmath.structures + +import kotlin.test.Test +import kotlin.test.assertEquals +import kotlin.test.assertFails + +internal class BufferExpandedTest { + private val buffer = (0..100).toList().asBuffer() + + @Test + fun shrink(){ + val view = buffer.slice(20..30) + assertEquals(20, view[0]) + assertEquals(30, view[10]) + assertFails { view[11] } + } + + @Test + fun expandNegative(){ + val view: BufferView = buffer.expand(-20..113,0) + assertEquals(0,view[4]) + assertEquals(0,view[123]) + assertEquals(100, view[120]) + assertFails { view[-2] } + assertFails { view[134] } + } +} \ No newline at end of file diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NDFieldTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NDFieldTest.kt index b7b89d107..566145621 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NDFieldTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NDFieldTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NumberNDFieldTest.kt b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NumberNDFieldTest.kt index d33eb5112..993fb089f 100644 --- a/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NumberNDFieldTest.kt +++ b/kmath-core/src/commonTest/kotlin/space/kscience/kmath/structures/NumberNDFieldTest.kt @@ -1,22 +1,28 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.linear.linearSpace -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.* +import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.nd.get +import space.kscience.kmath.nd.ndAlgebra +import space.kscience.kmath.nd.structureND import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.Norm import space.kscience.kmath.operations.algebra import space.kscience.kmath.operations.invoke +import kotlin.collections.component1 +import kotlin.collections.component2 import kotlin.math.abs import kotlin.math.pow import kotlin.test.Test import kotlin.test.assertEquals +@OptIn(PerformancePitfall::class) @Suppress("UNUSED_VARIABLE") class NumberNDFieldTest { val algebra = DoubleField.ndAlgebra @@ -74,7 +80,9 @@ class NumberNDFieldTest { @Test fun combineTest() { - val division = array1.zip(array2, Double::div) + algebra { + val division = zip(array1, array2) { l, r -> l / r } + } } object L2Norm : Norm, Double> { @@ -86,7 +94,7 @@ class NumberNDFieldTest { @Test fun testInternalContext() { algebra { - (DoubleField.ndAlgebra(*array1.shape)) { with(L2Norm) { 1 + norm(array1) + exp(array2) } } + (DoubleField.ndAlgebra(array1.shape)) { with(L2Norm) { 1 + norm(array1) + exp(array2) } } } } } diff --git a/kmath-core/src/jsMain/kotlin/space/kscience/kmath/misc/numbers.kt b/kmath-core/src/jsMain/kotlin/space/kscience/kmath/misc/numbers.kt index 68a3c995b..e52ea9298 100644 --- a/kmath-core/src/jsMain/kotlin/space/kscience/kmath/misc/numbers.kt +++ b/kmath-core/src/jsMain/kotlin/space/kscience/kmath/misc/numbers.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/jsMain/kotlin/space/kscience/kmath/operations/isInteger.kt b/kmath-core/src/jsMain/kotlin/space/kscience/kmath/operations/isInteger.kt index 24b81322e..3103f5168 100644 --- a/kmath-core/src/jsMain/kotlin/space/kscience/kmath/operations/isInteger.kt +++ b/kmath-core/src/jsMain/kotlin/space/kscience/kmath/operations/isInteger.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/misc/numbersJVM.kt b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/misc/numbersJVM.kt index 5ba0dbc9b..3780ea1ae 100644 --- a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/misc/numbersJVM.kt +++ b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/misc/numbersJVM.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/BigNumbers.kt b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/BigNumbers.kt index 6e22c2381..584748bd7 100644 --- a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/BigNumbers.kt +++ b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/BigNumbers.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/isInteger.kt b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/isInteger.kt index b2f9b957b..9868daddf 100644 --- a/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/isInteger.kt +++ b/kmath-core/src/jvmMain/kotlin/space/kscience/kmath/operations/isInteger.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/jvmTest/kotlin/space/kscience/kmath/misc/JBigTest.kt b/kmath-core/src/jvmTest/kotlin/space/kscience/kmath/misc/JBigTest.kt new file mode 100644 index 000000000..f7f8027e6 --- /dev/null +++ b/kmath-core/src/jvmTest/kotlin/space/kscience/kmath/misc/JBigTest.kt @@ -0,0 +1,20 @@ +/* + * Copyright 2018-2022 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.misc + +import org.junit.jupiter.api.Test +import space.kscience.kmath.operations.JBigDecimalField +import kotlin.test.assertEquals +import kotlin.test.assertNotEquals + +class JBigTest { + + @Test + fun testExact() = with(JBigDecimalField) { + assertNotEquals(0.3, 0.1 + 0.2) + assertEquals(one * 0.3, one * 0.1 + one * 0.2) + } +} \ No newline at end of file diff --git a/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/misc/numbers.kt b/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/misc/numbers.kt index 68a3c995b..e52ea9298 100644 --- a/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/misc/numbers.kt +++ b/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/misc/numbers.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/operations/isInteger.kt b/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/operations/isInteger.kt index b2f9b957b..9868daddf 100644 --- a/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/operations/isInteger.kt +++ b/kmath-core/src/nativeMain/kotlin/space/kscience/kmath/operations/isInteger.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/misc/numbers.kt b/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/misc/numbers.kt new file mode 100644 index 000000000..e320f350e --- /dev/null +++ b/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/misc/numbers.kt @@ -0,0 +1,12 @@ +/* + * Copyright 2018-2023 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.misc + +public actual fun Long.toIntExact(): Int { + val i = toInt() + if (i.toLong() == this) throw ArithmeticException("integer overflow") + return i +} diff --git a/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/operations/isInteger.kt b/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/operations/isInteger.kt new file mode 100644 index 000000000..11c82bf9e --- /dev/null +++ b/kmath-core/src/wasmMain/kotlin/space/kscience/kmath/operations/isInteger.kt @@ -0,0 +1,12 @@ +/* + * Copyright 2018-2023 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.operations + +/** + * Check if number is an integer from platform point of view + */ +public actual fun Number.isInteger(): Boolean = + (this is Int) || (this is Long) || (this is Short) || (this.toDouble() % 1 == 0.0) \ No newline at end of file diff --git a/kmath-coroutines/README.md b/kmath-coroutines/README.md index 337d8e037..21831e514 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-coroutines:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-coroutines:0.3.1-dev-1' + implementation 'space.kscience:kmath-coroutines:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-coroutines:0.3.1-dev-1") + implementation("space.kscience:kmath-coroutines:0.4.0-dev-1") } ``` diff --git a/kmath-coroutines/build.gradle.kts b/kmath-coroutines/build.gradle.kts index aa30c412b..1e901ca98 100644 --- a/kmath-coroutines/build.gradle.kts +++ b/kmath-coroutines/build.gradle.kts @@ -1,27 +1,19 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets { - all { - with(languageSettings) { - optIn("kotlinx.coroutines.InternalCoroutinesApi") - optIn("kotlinx.coroutines.ExperimentalCoroutinesApi") - optIn("kotlinx.coroutines.FlowPreview") - } - } +kscience { + jvm() + js() + native() - commonMain { - dependencies { - api(project(":kmath-core")) - api(project(":kmath-complex")) - api("org.jetbrains.kotlinx:kotlinx-coroutines-core:${ru.mipt.npm.gradle.KScienceVersions.coroutinesVersion}") - } + dependencies { + api(project(":kmath-core")) + api(project(":kmath-complex")) + api(spclibs.kotlinx.coroutines.core) } } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } \ No newline at end of file diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingChain.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingChain.kt index 87aebff61..2e9a15eed 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingChain.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingChain.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingDoubleChain.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingDoubleChain.kt index 25e20291e..797d2db4a 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingDoubleChain.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingDoubleChain.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingIntChain.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingIntChain.kt index ac0327d0b..a481156f2 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingIntChain.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/BlockingIntChain.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/Chain.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/Chain.kt index 994255e38..977346e68 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/Chain.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/Chain.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,7 +10,7 @@ import kotlinx.coroutines.flow.FlowCollector import kotlinx.coroutines.flow.flow import kotlinx.coroutines.sync.Mutex import kotlinx.coroutines.sync.withLock -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI /** * A not-necessary-Markov chain of some type diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/flowExtra.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/flowExtra.kt index 7bf54d50f..77d4203c5 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/flowExtra.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/chains/flowExtra.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/coroutines/coroutinesExtra.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/coroutines/coroutinesExtra.kt index 1f17efe49..48be93b87 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/coroutines/coroutinesExtra.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/coroutines/coroutinesExtra.kt @@ -1,11 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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(ExperimentalCoroutinesApi::class, FlowPreview::class) + package space.kscience.kmath.coroutines import kotlinx.coroutines.* +import kotlinx.coroutines.channels.ReceiveChannel import kotlinx.coroutines.channels.produce import kotlinx.coroutines.flow.* @@ -55,7 +58,7 @@ public suspend fun AsyncFlow.collect(concurrency: Int, collector: FlowCol coroutineScope { //Starting up to N deferred coroutines ahead of time - val channel = produce(capacity = concurrency - 1) { + val channel: ReceiveChannel> = produce(capacity = concurrency - 1) { deferredFlow.collect { value -> value.start(this@coroutineScope) send(value) @@ -81,9 +84,7 @@ public suspend fun AsyncFlow.collect(concurrency: Int, collector: FlowCol public suspend inline fun AsyncFlow.collect( concurrency: Int, crossinline action: suspend (value: T) -> Unit, -): Unit = collect(concurrency, object : FlowCollector { - override suspend fun emit(value: T): Unit = action(value) -}) +): Unit = collect(concurrency, FlowCollector { value -> action(value) }) public inline fun Flow.mapParallel( dispatcher: CoroutineDispatcher = Dispatchers.Default, diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/BufferFlow.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/BufferFlow.kt index 4d4493aa4..2cc8b8393 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/BufferFlow.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/BufferFlow.kt @@ -1,12 +1,18 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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(FlowPreview::class) + package space.kscience.kmath.streaming +import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.FlowPreview -import kotlinx.coroutines.flow.* +import kotlinx.coroutines.flow.Flow +import kotlinx.coroutines.flow.asFlow +import kotlinx.coroutines.flow.flatMapConcat +import kotlinx.coroutines.flow.flow import space.kscience.kmath.chains.BlockingDoubleChain import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory @@ -20,7 +26,7 @@ public fun Buffer.asFlow(): Flow = iterator().asFlow() /** * Flat map a [Flow] of [Buffer] into continuous [Flow] of elements */ -@FlowPreview +@OptIn(ExperimentalCoroutinesApi::class) public fun Flow>.spread(): Flow = flatMapConcat { it.asFlow() } /** diff --git a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/RingBuffer.kt b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/RingBuffer.kt index abe1c9df9..2ac8c1eb4 100644 --- a/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/RingBuffer.kt +++ b/kmath-coroutines/src/commonMain/kotlin/space/kscience/kmath/streaming/RingBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/chains/ChainExt.kt b/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/chains/ChainExt.kt index dd6e39071..a62bcc6b8 100644 --- a/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/chains/ChainExt.kt +++ b/kmath-coroutines/src/jvmMain/kotlin/space/kscience/kmath/chains/ChainExt.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 2b9265843..22c2ac3ff 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 @@ -1,19 +1,20 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.structures import kotlinx.coroutines.* +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.coroutines.Math -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.nd.ColumnStrides +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND public class LazyStructureND( public val scope: CoroutineScope, - override val shape: IntArray, + override val shape: ShapeND, public val function: suspend (IntArray) -> T, ) : StructureND { private val cache: MutableMap> = HashMap() @@ -23,30 +24,35 @@ public class LazyStructureND( } public suspend fun await(index: IntArray): T = async(index).await() + @PerformancePitfall override operator fun get(index: IntArray): T = runBlocking { async(index).await() } @OptIn(PerformancePitfall::class) override fun elements(): Sequence> { - val strides = DefaultStrides(shape) + val strides = ColumnStrides(shape) val res = runBlocking { strides.asSequence().toList().map { index -> index to await(index) } } return res.asSequence() } } +@OptIn(PerformancePitfall::class) public fun StructureND.async(index: IntArray): Deferred = if (this is LazyStructureND) this@async.async(index) else CompletableDeferred(get(index)) +@OptIn(PerformancePitfall::class) public suspend fun StructureND.await(index: IntArray): T = if (this is LazyStructureND) await(index) else get(index) /** * PENDING would benefit from KEEP-176 */ +@OptIn(PerformancePitfall::class) public inline fun StructureND.mapAsyncIndexed( scope: CoroutineScope, crossinline function: suspend (T, index: IntArray) -> R, ): LazyStructureND = LazyStructureND(scope, shape) { index -> function(get(index), index) } +@OptIn(PerformancePitfall::class) public inline fun StructureND.mapAsync( scope: CoroutineScope, crossinline function: suspend (T) -> R, diff --git a/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/BufferFlowTest.kt b/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/BufferFlowTest.kt index 9b67f7253..c448168e3 100644 --- a/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/BufferFlowTest.kt +++ b/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/BufferFlowTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/RingBufferTest.kt b/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/RingBufferTest.kt index 305b97e5d..a6d7f006c 100644 --- a/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/RingBufferTest.kt +++ b/kmath-coroutines/src/jvmTest/kotlin/space/kscience/kmath/streaming/RingBufferTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-dimensions/README.md b/kmath-dimensions/README.md index 12aa2a7fa..2e7250b51 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-dimensions:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-dimensions:0.3.1-dev-1' + implementation 'space.kscience:kmath-dimensions:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-dimensions:0.3.1-dev-1") + implementation("space.kscience:kmath-dimensions:0.4.0-dev-1") } ``` diff --git a/kmath-dimensions/build.gradle.kts b/kmath-dimensions/build.gradle.kts index 885f3c227..be1fc65a0 100644 --- a/kmath-dimensions/build.gradle.kts +++ b/kmath-dimensions/build.gradle.kts @@ -1,25 +1,23 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -description = "A proof of concept module for adding type-safe dimensions to structures" +kscience{ + jvm() + js() + native() -kotlin.sourceSets { - commonMain { - dependencies { - api(project(":kmath-core")) - } + dependencies{ + api(projects.kmathCore) } - jvmMain { - dependencies { - api(kotlin("reflect")) - } + dependencies(jvmMain) { + api(kotlin("reflect")) } } +description = "A proof of concept module for adding type-safe dimensions to structures" + readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } diff --git a/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt b/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt index e57c22834..14677319c 100644 --- a/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt +++ b/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Wrappers.kt b/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Wrappers.kt index f04536f04..dde2d4fcf 100644 --- a/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Wrappers.kt +++ b/kmath-dimensions/src/commonMain/kotlin/space/kscience/kmath/dimensions/Wrappers.kt @@ -1,11 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.dimensions import space.kscience.kmath.linear.* +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.Ring @@ -47,7 +48,7 @@ public interface DMatrix : Structure2D { public value class DMatrixWrapper( private val structure: Structure2D, ) : DMatrix { - override val shape: IntArray get() = structure.shape + override val shape: ShapeND get() = structure.shape override val rowNum: Int get() = shape[0] override val colNum: Int get() = shape[1] override operator fun get(i: Int, j: Int): T = structure[i, j] diff --git a/kmath-dimensions/src/commonTest/kotlin/space/kscience/dimensions/DMatrixContextTest.kt b/kmath-dimensions/src/commonTest/kotlin/space/kscience/dimensions/DMatrixContextTest.kt index 59260fe73..e2793855b 100644 --- a/kmath-dimensions/src/commonTest/kotlin/space/kscience/dimensions/DMatrixContextTest.kt +++ b/kmath-dimensions/src/commonTest/kotlin/space/kscience/dimensions/DMatrixContextTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-dimensions/src/jsMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt b/kmath-dimensions/src/jsMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt index 610e8b4c0..1ae484228 100644 --- a/kmath-dimensions/src/jsMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt +++ b/kmath-dimensions/src/jsMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-dimensions/src/jvmMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt b/kmath-dimensions/src/jvmMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt index e6d8b3b35..24cfb14e8 100644 --- a/kmath-dimensions/src/jvmMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt +++ b/kmath-dimensions/src/jvmMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-dimensions/src/nativeMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt b/kmath-dimensions/src/nativeMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt index 64edbe935..f5f749c8a 100644 --- a/kmath-dimensions/src/nativeMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt +++ b/kmath-dimensions/src/nativeMain/kotlin/space/kscience/kmath/dimensions/Dimension.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ejml/README.md b/kmath-ejml/README.md index 2d6c661e4..ad80ba183 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-ejml:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-ejml:0.3.1-dev-1' + implementation 'space.kscience:kmath-ejml:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-ejml:0.3.1-dev-1") + implementation("space.kscience:kmath-ejml:0.4.0-dev-1") } ``` diff --git a/kmath-ejml/build.gradle.kts b/kmath-ejml/build.gradle.kts index 727d21e3a..d7f780d79 100644 --- a/kmath-ejml/build.gradle.kts +++ b/kmath-ejml/build.gradle.kts @@ -1,8 +1,7 @@ import space.kscience.kmath.ejml.codegen.ejmlCodegen plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } dependencies { @@ -14,7 +13,7 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlLinearSpace.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlLinearSpace.kt index 32030dfe3..8925fb045 100644 --- a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlLinearSpace.kt +++ b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlLinearSpace.kt @@ -1,15 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.ejml +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.InverseMatrixFeature import space.kscience.kmath.linear.LinearSpace import space.kscience.kmath.linear.Matrix import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.operations.Ring diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlMatrix.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlMatrix.kt index 27fd3fc53..1d70c0e7d 100644 --- a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlMatrix.kt +++ b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlMatrix.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlVector.kt b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlVector.kt index 37995c27e..c4fae9951 100644 --- a/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlVector.kt +++ b/kmath-ejml/src/main/kotlin/space/kscience/kmath/ejml/EjmlVector.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 aac327a84..8ad7f7293 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 @@ -21,7 +21,7 @@ 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.UnstableKMathAPI import space.kscience.kmath.nd.StructureFeature import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.FloatField 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 af6284e5e..e89810e0d 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -11,10 +11,11 @@ import org.ejml.data.DMatrixRMaj import org.ejml.dense.row.CommonOps_DDRM import org.ejml.dense.row.RandomMatrices_DDRM import org.ejml.dense.row.factory.DecompositionFactory_DDRM +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.* -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.nd.toArray import space.kscience.kmath.operations.algebra import kotlin.random.Random import kotlin.random.asJavaRandom @@ -52,7 +53,7 @@ internal class EjmlMatrixTest { fun shape() { val m = randomMatrix val w = EjmlDoubleMatrix(m) - assertContentEquals(intArrayOf(m.numRows, m.numCols), w.shape) + assertContentEquals(intArrayOf(m.numRows, m.numCols), w.shape.toArray()) } @OptIn(UnstableKMathAPI::class) diff --git a/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlVectorTest.kt b/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlVectorTest.kt index 9592bfa6c..7d3ea314b 100644 --- a/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlVectorTest.kt +++ b/kmath-ejml/src/test/kotlin/space/kscience/kmath/ejml/EjmlVectorTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-for-real/README.md b/kmath-for-real/README.md index 5a8376976..638b15bfa 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-for-real:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-for-real:0.3.1-dev-1' + implementation 'space.kscience:kmath-for-real:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-for-real:0.3.1-dev-1") + implementation("space.kscience:kmath-for-real:0.4.0-dev-1") } ``` diff --git a/kmath-for-real/build.gradle.kts b/kmath-for-real/build.gradle.kts index 18c2c50ad..99ce5903f 100644 --- a/kmath-for-real/build.gradle.kts +++ b/kmath-for-real/build.gradle.kts @@ -1,12 +1,18 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets.commonMain { +kscience { + jvm() + js() + native() + dependencies { - api(project(":kmath-core")) + api(projects.kmathCore) + } + + testDependencies { + implementation(projects.testUtils) } } @@ -16,27 +22,27 @@ readme { All operations are specialized to work with `Double` numbers without declaring algebraic contexts. One can still use generic algebras though. """.trimIndent() - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( id = "DoubleVector", ref = "src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt" - ){ + ) { "Numpy-like operations for Buffers/Points" } feature( id = "DoubleMatrix", ref = "src/commonMain/kotlin/space/kscience/kmath/real/DoubleMatrix.kt" - ){ + ) { "Numpy-like operations for 2d real structures" } feature( id = "grids", ref = "src/commonMain/kotlin/space/kscience/kmath/structures/grids.kt" - ){ + ) { "Uniform grid generators" } } diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt index 7b9740c35..411a35188 100644 --- a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt +++ b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/DoubleVector.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.real +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.Point -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleL2Norm import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.MutableBuffer.Companion.double diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealMatrix.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealMatrix.kt index 671e272ab..40e4a91f1 100644 --- a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealMatrix.kt +++ b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/RealMatrix.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,9 +8,9 @@ package space.kscience.kmath.real +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.* -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.algebra import space.kscience.kmath.operations.asIterable @@ -131,7 +131,7 @@ public fun RealMatrix.extractColumn(columnIndex: Int): RealMatrix = extractColumns(columnIndex..columnIndex) public fun RealMatrix.sumByColumn(): DoubleBuffer = DoubleBuffer(colNum) { j -> - columns[j].asIterable().sum() + columns[j].sum() } public fun RealMatrix.minByColumn(): DoubleBuffer = DoubleBuffer(colNum) { j -> diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/dot.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/dot.kt index dc5c58be0..0c18602f1 100644 --- a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/dot.kt +++ b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/dot.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/grids.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/grids.kt index 1926ef02c..adb62b173 100644 --- a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/grids.kt +++ b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/grids.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.real -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer import kotlin.math.floor diff --git a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/realND.kt b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/realND.kt index 52362f4b4..2c06b76b7 100644 --- a/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/realND.kt +++ b/kmath-for-real/src/commonMain/kotlin/space/kscience/kmath/real/realND.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleMatrixTest.kt b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleMatrixTest.kt index 4a0e8de1d..c00cd84d1 100644 --- a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleMatrixTest.kt +++ b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleMatrixTest.kt @@ -1,17 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.real +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.linear.linearSpace import space.kscience.kmath.linear.matrix -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.algebra -import space.kscience.kmath.structures.contentEquals +import space.kscience.kmath.testutils.contentEquals import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue diff --git a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleVectorTest.kt b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleVectorTest.kt index e77b96c12..a25091ac2 100644 --- a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleVectorTest.kt +++ b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/DoubleVectorTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/GridTest.kt b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/GridTest.kt index 8fed8d10e..35c53f9d6 100644 --- a/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/GridTest.kt +++ b/kmath-for-real/src/commonTest/kotlin/space/kscience/kmath/real/GridTest.kt @@ -1,15 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.real -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.real.DoubleVector -import space.kscience.kmath.real.minus -import space.kscience.kmath.real.norm -import space.kscience.kmath.real.step +import space.kscience.kmath.UnstableKMathAPI import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue diff --git a/kmath-functions/README.md b/kmath-functions/README.md index 1292424b5..929fd9172 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-functions:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -21,7 +21,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-functions:0.3.1-dev-1' + implementation 'space.kscience:kmath-functions:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -32,6 +32,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-functions:0.3.1-dev-1") + implementation("space.kscience:kmath-functions:0.4.0-dev-1") } ``` diff --git a/kmath-functions/build.gradle.kts b/kmath-functions/build.gradle.kts index 337875ba4..4ec52f5ee 100644 --- a/kmath-functions/build.gradle.kts +++ b/kmath-functions/build.gradle.kts @@ -1,25 +1,29 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -description = "Functions, integration and interpolation" +kscience{ + jvm() + js() + native() + + wasm() + -kotlin.sourceSets { - commonMain { - dependencies { - api(project(":kmath-core")) - } + + dependencies { + api(projects.kmathCore) } } +description = "Functions, integration and interpolation" + dependencies { - dokkaPlugin("org.jetbrains.dokka:mathjax-plugin:${npmlibs.versions.dokka.get()}") + dokkaPlugin("org.jetbrains.dokka:mathjax-plugin:${spclibs.versions.dokka.get()}") } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature("piecewise", "src/commonMain/kotlin/space/kscience/kmath/functions/Piecewise.kt") { diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Piecewise.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Piecewise.kt index 16af7f555..a9e75e456 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Piecewise.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Piecewise.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.functions -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.operations.Ring /** diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt index 1f9bab52c..af84f47f2 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 0e814993c..c2f95f040 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialConstructors.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialConstructors.kt index 2da9ea6f5..4e9791a87 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialConstructors.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialConstructors.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialUtil.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialUtil.kt index c9377a6c1..0d4b93f03 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialUtil.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/functions/polynomialUtil.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.functions -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.* import kotlin.contracts.InvocationKind import kotlin.contracts.contract diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegrator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegrator.kt index 9785d7744..f2ac0a296 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegrator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegrator.kt @@ -1,10 +1,10 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.Field import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.asBuffer diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegratorRuleFactory.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegratorRuleFactory.kt index 778d85e66..4ed4965c9 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegratorRuleFactory.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/GaussIntegratorRuleFactory.kt @@ -1,15 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration -import space.kscience.kmath.operations.map +import space.kscience.kmath.operations.mapToBuffer import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.asBuffer -import kotlin.jvm.Synchronized import kotlin.math.ulp import kotlin.native.concurrent.ThreadLocal @@ -30,14 +29,14 @@ public fun GaussIntegratorRuleFactory.build( numPoints: Int, range: ClosedRange, ): Pair, Buffer> { - val normalized = build(numPoints) + val normalized: Pair, Buffer> = build(numPoints) val length = range.endInclusive - range.start - val points = normalized.first.map(::DoubleBuffer) { + val points = normalized.first.mapToBuffer(::DoubleBuffer) { range.start + length / 2 + length / 2 * it } - val weights = normalized.second.map(::DoubleBuffer) { + val weights = normalized.second.mapToBuffer(::DoubleBuffer) { it * length / 2 } @@ -57,7 +56,6 @@ public object GaussLegendreRuleFactory : GaussIntegratorRuleFactory { private val cache = HashMap, Buffer>>() - @Synchronized private fun getOrBuildRule(numPoints: Int): Pair, Buffer> = cache.getOrPut(numPoints) { buildRule(numPoints) } diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrand.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrand.kt index 05e2e5c55..40fe78898 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrand.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrand.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrator.kt index 1cf15b42f..18c46b83b 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/Integrator.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/MultivariateIntegrand.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/MultivariateIntegrand.kt index 96b81aaa6..53a563086 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/MultivariateIntegrand.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/MultivariateIntegrand.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SimpsonIntegrator.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SimpsonIntegrator.kt index 7815757aa..73a3cc25b 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SimpsonIntegrator.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/SimpsonIntegrator.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.Field import space.kscience.kmath.operations.invoke 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 eb88d9ae0..993812b29 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 @@ -1,17 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.functions.PiecewisePolynomial import space.kscience.kmath.functions.integrate import space.kscience.kmath.interpolation.PolynomialInterpolator import space.kscience.kmath.interpolation.SplineInterpolator import space.kscience.kmath.interpolation.interpolatePolynomials -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.* import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer @@ -65,9 +65,9 @@ public class SplineIntegrator>( DoubleBuffer(numPoints) { i -> range.start + i * step } } - val values = nodes.map(bufferFactory) { integrand.function(it) } + val values = nodes.mapToBuffer(bufferFactory) { integrand.function(it) } val polynomials = interpolator.interpolatePolynomials( - nodes.map(bufferFactory) { number(it) }, + nodes.mapToBuffer(bufferFactory) { number(it) }, values ) val res = polynomials.integrate(algebra, number(range.start)..number(range.endInclusive)) @@ -93,7 +93,7 @@ public object DoubleSplineIntegrator : UnivariateIntegrator { DoubleBuffer(numPoints) { i -> range.start + i * step } } - val values = nodes.map { integrand.function(it) } + val values = nodes.mapToBuffer(::DoubleBuffer) { integrand.function(it) } val polynomials = interpolator.interpolatePolynomials(nodes, values) val res = polynomials.integrate(DoubleField, range) return integrand + IntegrandValue(res) + IntegrandCallsPerformed(integrand.calls + nodes.size) diff --git a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/UnivariateIntegrand.kt b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/UnivariateIntegrand.kt index 6fd75e6e6..f18e86b80 100644 --- a/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/UnivariateIntegrand.kt +++ b/kmath-functions/src/commonMain/kotlin/space/kscience/kmath/integration/UnivariateIntegrand.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.misc.FeatureSet -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.DoubleBuffer 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 2266092a3..191e7dfd9 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,11 +7,11 @@ package space.kscience.kmath.interpolation +import space.kscience.kmath.UnstableKMathAPI 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 import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.asBuffer 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 34d7bcf41..5c56e406a 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 @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.interpolation +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.functions.PiecewisePolynomial import space.kscience.kmath.functions.Polynomial -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.Field import space.kscience.kmath.operations.invoke 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 afcb33bd4..a3cc17954 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 @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.interpolation +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.functions.PiecewisePolynomial import space.kscience.kmath.functions.Polynomial -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.Field import space.kscience.kmath.operations.invoke diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialTest.kt index 7e0c6cdf2..3051cdd8d 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialUtilTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialUtilTest.kt index 9d0fe4cc3..48e641335 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialUtilTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/PolynomialUtilTest.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.functions +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.functions.testUtils.Rational import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.misc.UnstableKMathAPI import kotlin.test.Test import kotlin.test.assertEquals diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt index ef601c941..3b7409e82 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt index 730a455bf..ffab2157c 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt index 19cb77df5..ff05805da 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,7 +7,7 @@ package space.kscience.kmath.functions.testUtils -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.Field import space.kscience.kmath.operations.NumbersAddOps diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt index ff67f19d8..61b50f128 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/GaussIntegralTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/GaussIntegralTest.kt index 9f48a15ea..7424f3566 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/GaussIntegralTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/GaussIntegralTest.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import kotlin.math.PI import kotlin.math.sin diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SimpsonIntegralTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SimpsonIntegralTest.kt index 9f2d71554..7b699ebbc 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SimpsonIntegralTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SimpsonIntegralTest.kt @@ -1,11 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import kotlin.math.PI import kotlin.math.sin diff --git a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SplineIntegralTest.kt b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SplineIntegralTest.kt index afeba0be4..b17d21abf 100644 --- a/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SplineIntegralTest.kt +++ b/kmath-functions/src/commonTest/kotlin/space/kscience/kmath/integration/SplineIntegralTest.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.integration +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.functions.Polynomial import space.kscience.kmath.functions.integrate -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import kotlin.math.PI import kotlin.math.sin 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 1143036d4..c0ca6c484 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 4c7d816d4..851a8ab7d 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-geometry/README.md b/kmath-geometry/README.md index 72d275697..480945c4f 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-geometry:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-geometry:0.3.1-dev-1' + implementation 'space.kscience:kmath-geometry:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-geometry:0.3.1-dev-1") + implementation("space.kscience:kmath-geometry:0.4.0-dev-1") } ``` diff --git a/kmath-geometry/build.gradle.kts b/kmath-geometry/build.gradle.kts index bfe2e32a2..32926db7e 100644 --- a/kmath-geometry/build.gradle.kts +++ b/kmath-geometry/build.gradle.kts @@ -1,15 +1,24 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets.commonMain { - dependencies { +kscience{ + jvm() + js() + native() + + useContextReceivers() + useSerialization() + dependencies{ api(projects.kmath.kmathComplex) } + + testDependencies { + implementation(projects.testUtils) + } + } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Circle2D.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Circle2D.kt index 8623335b9..d37ed45c0 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Circle2D.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Circle2D.kt @@ -1,18 +1,22 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlin.math.PI +import kotlinx.serialization.Serializable +import space.kscience.kmath.geometry.Euclidean2DSpace.distanceTo +import kotlin.math.* /** * A circle in 2D space */ -public class Circle2D( - public val center: Vector2D, +@Serializable +public data class Circle2D( + @Serializable(Euclidean2DSpace.VectorSerializer::class) public val center: DoubleVector2D, public val radius: Double ) + public val Circle2D.circumference: Double get() = radius * 2 * PI 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 a83cb3ac7..3df8dba7b 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 @@ -1,50 +1,90 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.serialization.KSerializer +import kotlinx.serialization.SerialName +import kotlinx.serialization.Serializable +import kotlinx.serialization.descriptors.SerialDescriptor +import kotlinx.serialization.encoding.Decoder +import kotlinx.serialization.encoding.Encoder import space.kscience.kmath.linear.Point +import space.kscience.kmath.operations.Norm import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.operations.invoke +import kotlin.math.pow import kotlin.math.sqrt -public interface Vector2D : Point, Vector { - public val x: Double - public val y: Double +public interface Vector2D : Point, Vector { + public val x: T + public val y: T override val size: Int get() = 2 - override operator fun get(index: Int): Double = when (index) { + override operator fun get(index: Int): T = when (index) { 0 -> x 1 -> y else -> error("Accessing outside of point bounds") } - override operator fun iterator(): Iterator = listOf(x, y).iterator() + override operator fun iterator(): Iterator = iterator { + yield(x) + yield(y) + } } -public val Vector2D.r: Double - get() = Euclidean2DSpace { norm() } -public fun Vector2D(x: Double, y: Double): Vector2D = Vector2DImpl(x, y) +public operator fun Vector2D.component1(): T = x +public operator fun Vector2D.component2(): T = y + +public typealias DoubleVector2D = Vector2D +public typealias Float64Vector2D = Vector2D + +public val Vector2D.r: Double get() = Euclidean2DSpace.norm(this) -private data class Vector2DImpl( - override val x: Double, - override val y: Double, -) : Vector2D /** * 2D Euclidean space */ -public object Euclidean2DSpace : GeometrySpace, ScaleOperations { - override val zero: Vector2D by lazy { Vector2D(0.0, 0.0) } +public object Euclidean2DSpace : GeometrySpace, + ScaleOperations, + Norm { + + @Serializable + @SerialName("Float64Vector2D") + private data class Vector2DImpl( + override val x: Double, + override val y: Double, + ) : DoubleVector2D + + public object VectorSerializer : KSerializer { + private val proxySerializer = Vector2DImpl.serializer() + override val descriptor: SerialDescriptor get() = proxySerializer.descriptor + + override fun deserialize(decoder: Decoder): DoubleVector2D = decoder.decodeSerializableValue(proxySerializer) + + override fun serialize(encoder: Encoder, value: DoubleVector2D) { + val vector = value as? Vector2DImpl ?: Vector2DImpl(value.x, value.y) + encoder.encodeSerializableValue(proxySerializer, vector) + } + } + + public fun vector(x: Number, y: Number): DoubleVector2D = Vector2DImpl(x.toDouble(), y.toDouble()) + + override val zero: DoubleVector2D by lazy { vector(0.0, 0.0) } + + override fun norm(arg: DoubleVector2D): Double = sqrt(arg.x.pow(2) + arg.y.pow(2)) + + override fun DoubleVector2D.unaryMinus(): DoubleVector2D = vector(-x, -y) + + override fun DoubleVector2D.distanceTo(other: DoubleVector2D): Double = norm(this - other) + override fun add(left: DoubleVector2D, right: DoubleVector2D): DoubleVector2D = + vector(left.x + right.x, left.y + right.y) - public fun Vector2D.norm(): Double = sqrt(x * x + y * y) - override fun Vector2D.unaryMinus(): Vector2D = Vector2D(-x, -y) + override fun scale(a: DoubleVector2D, value: Double): DoubleVector2D = vector(a.x * value, a.y * value) + override fun DoubleVector2D.dot(other: DoubleVector2D): Double = x * other.x + y * other.y - override fun Vector2D.distanceTo(other: Vector2D): Double = (this - other).norm() - override fun add(left: Vector2D, right: Vector2D): Vector2D = Vector2D(left.x + right.x, left.y + right.y) - override fun scale(a: Vector2D, value: Double): Vector2D = Vector2D(a.x * value, a.y * value) - override fun Vector2D.dot(other: Vector2D): Double = x * other.x + y * other.y + public val xAxis: DoubleVector2D = vector(1.0, 0.0) + public val yAxis: DoubleVector2D = vector(0.0, 1.0) } 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 c1fc74bf1..3059cefe6 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 @@ -1,70 +1,149 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.serialization.KSerializer +import kotlinx.serialization.SerialName +import kotlinx.serialization.Serializable +import kotlinx.serialization.descriptors.SerialDescriptor +import kotlinx.serialization.encoding.Decoder +import kotlinx.serialization.encoding.Encoder import space.kscience.kmath.linear.Point +import space.kscience.kmath.operations.Norm import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.Buffer +import kotlin.math.pow import kotlin.math.sqrt -public interface Vector3D : Point, Vector { - public val x: Double - public val y: Double - public val z: Double +public interface Vector3D : Point, Vector { + public val x: T + public val y: T + public val z: T override val size: Int get() = 3 - override operator fun get(index: Int): Double = when (index) { + override operator fun get(index: Int): T = when (index) { 0 -> x 1 -> y 2 -> z else -> error("Accessing outside of point bounds") } - override operator fun iterator(): Iterator = listOf(x, y, z).iterator() + override operator fun iterator(): Iterator = listOf(x, y, z).iterator() } -@Suppress("FunctionName") -public fun Vector3D(x: Double, y: Double, z: Double): Vector3D = Vector3DImpl(x, y, z) +public operator fun Vector3D.component1(): T = x +public operator fun Vector3D.component2(): T = y +public operator fun Vector3D.component3(): T = z -public fun Buffer.asVector3D(): Vector3D = object : Vector3D { +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 val x: T get() = this@asVector3D[0] + override val y: T get() = this@asVector3D[1] + override val z: T get() = this@asVector3D[2] override fun toString(): String = this@asVector3D.toString() - } -public val Vector3D.r: Double get() = Euclidean3DSpace { norm() } +public typealias DoubleVector3D = Vector3D +public typealias Float64Vector3D = Vector3D + +public val DoubleVector3D.r: Double get() = Euclidean3DSpace.norm(this) + +public object Euclidean3DSpace : GeometrySpace, ScaleOperations, + Norm { + + @Serializable + @SerialName("Float64Vector3D") + private data class Vector3DImpl( + override val x: Double, + override val y: Double, + override val z: Double, + ) : DoubleVector3D + + public object VectorSerializer : KSerializer { + private val proxySerializer = Vector3DImpl.serializer() + override val descriptor: SerialDescriptor get() = proxySerializer.descriptor + + override fun deserialize(decoder: Decoder): DoubleVector3D = decoder.decodeSerializableValue(proxySerializer) + + override fun serialize(encoder: Encoder, value: DoubleVector3D) { + val vector = value as? Vector3DImpl ?: Vector3DImpl(value.x, value.y, value.z) + encoder.encodeSerializableValue(proxySerializer, vector) + } + } + + public fun vector(x: Double, y: Double, z: Double): DoubleVector3D = + Vector3DImpl(x, y, z) -private data class Vector3DImpl( - override val x: Double, - override val y: Double, - override val z: Double, -) : Vector3D + public fun vector(x: Number, y: Number, z: Number): DoubleVector3D = + vector(x.toDouble(), y.toDouble(), z.toDouble()) -public object Euclidean3DSpace : GeometrySpace, ScaleOperations { - override val zero: Vector3D by lazy { Vector3D(0.0, 0.0, 0.0) } + override val zero: DoubleVector3D by lazy { vector(0.0, 0.0, 0.0) } - public fun Vector3D.norm(): Double = sqrt(x * x + y * y + z * z) - override fun Vector3D.unaryMinus(): Vector3D = Vector3D(-x, -y, -z) + override fun norm(arg: DoubleVector3D): Double = sqrt(arg.x.pow(2) + arg.y.pow(2) + arg.z.pow(2)) - override fun Vector3D.distanceTo(other: Vector3D): Double = (this - other).norm() + public fun DoubleVector3D.norm(): Double = norm(this) - override fun add(left: Vector3D, right: Vector3D): Vector3D = - Vector3D(left.x + right.x, left.y + right.y, left.z + right.z) + override fun DoubleVector3D.unaryMinus(): DoubleVector3D = vector(-x, -y, -z) - override fun scale(a: Vector3D, value: Double): Vector3D = - Vector3D(a.x * value, a.y * value, a.z * value) + override fun DoubleVector3D.distanceTo(other: DoubleVector3D): Double = (this - other).norm() - override fun Vector3D.dot(other: Vector3D): Double = + override fun add(left: DoubleVector3D, right: DoubleVector3D): DoubleVector3D = + vector(left.x + right.x, left.y + right.y, left.z + right.z) + + override fun scale(a: DoubleVector3D, value: Double): DoubleVector3D = + vector(a.x * value, a.y * value, a.z * value) + + override fun DoubleVector3D.dot(other: DoubleVector3D): Double = x * other.x + y * other.y + z * other.z + + private fun leviCivita(i: Int, j: Int, k: Int): Int = when { + // even permutation + i == 0 && j == 1 && k == 2 -> 1 + i == 1 && j == 2 && k == 0 -> 1 + i == 2 && j == 0 && k == 1 -> 1 + // odd permutations + i == 2 && j == 1 && k == 0 -> -1 + i == 0 && j == 2 && k == 1 -> -1 + i == 1 && j == 0 && k == 2 -> -1 + + else -> 0 + } + + /** + * Compute vector product of [first] and [second]. The basis assumed to be right-handed. + */ + public fun vectorProduct( + first: DoubleVector3D, + second: DoubleVector3D, + ): DoubleVector3D { + var x = 0.0 + var y = 0.0 + var z = 0.0 + + for (j in (0..2)) { + for (k in (0..2)) { + x += leviCivita(0, j, k) * first[j] * second[k] + y += leviCivita(1, j, k) * first[j] * second[k] + z += leviCivita(2, j, k) * first[j] * second[k] + } + } + + return vector(x, y, z) + } + + /** + * Vector product with right basis + */ + public infix fun DoubleVector3D.cross(other: DoubleVector3D): Vector3D = vectorProduct(this, other) + + public val xAxis: DoubleVector3D = vector(1.0, 0.0, 0.0) + public val yAxis: DoubleVector3D = vector(0.0, 1.0, 0.0) + public val zAxis: DoubleVector3D = vector(0.0, 0.0, 1.0) } diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/GeometrySpace.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/GeometrySpace.kt index d4245c744..d6d7e5725 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/GeometrySpace.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/GeometrySpace.kt @@ -1,16 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations.Group +import space.kscience.kmath.operations.Norm import space.kscience.kmath.operations.ScaleOperations public interface Vector -public interface GeometrySpace : Group, ScaleOperations { +public interface GeometrySpace : Group, ScaleOperations, Norm { /** * L2 distance */ @@ -20,4 +21,11 @@ public interface GeometrySpace : Group, ScaleOperations { * Scalar product */ public infix fun V.dot(other: V): Double + + public companion object{ + /** + * Default precision for geometry objects comparison + */ + internal const val DEFAULT_PRECISION = 1e-6 + } } \ No newline at end of file diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Line.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Line.kt index 85bfcdd8f..a7f6ae35d 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Line.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Line.kt @@ -1,15 +1,51 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.serialization.SerialName +import kotlinx.serialization.Serializable + /** - * A line formed by [base] vector of start and a [direction] vector. Direction vector is not necessarily normalized, + * A line formed by [start] vector of start and a [direction] vector. Direction vector is not necessarily normalized, * but its length does not affect line properties */ -public data class Line(val base: V, val direction: V) +public interface Line { + public val start: V + public val direction: V +} + +@Serializable +@SerialName("Line") +private data class LineImpl(override val start: V, override val direction: V): Line + +public fun Line(base: V, direction: V): Line = LineImpl(base, direction) + +public typealias Line2D = Line +public typealias Line3D = Line + +/** + * A directed line segment between [begin] and [end] + */ +public interface LineSegment { + public val begin: V + public val end: V +} + +/** + * Basic implementation for [LineSegment] + */ +@Serializable +@SerialName("LineSegment") +private data class LineSegmentImpl(override val begin: V, override val end: V) : LineSegment + +public fun LineSegment(begin: V, end: V): LineSegment = LineSegmentImpl(begin, end) + +public fun LineSegment.line(algebra: GeometrySpace): Line = with(algebra) { + Line(begin, end - begin) +} -public typealias Line2D = Line -public typealias Line3D = Line +public typealias LineSegment2D = LineSegment +public typealias LineSegment3D = LineSegment diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Polygon.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Polygon.kt new file mode 100644 index 000000000..20f4a031e --- /dev/null +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/Polygon.kt @@ -0,0 +1,14 @@ +/* + * Copyright 2018-2023 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 + + +/** + * A closed polygon in 2D space + */ +public interface Polygon { + public val points: List> +} \ No newline at end of file diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/ReferenceFrame.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/ReferenceFrame.kt index a7a28b596..21045e94e 100644 --- a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/ReferenceFrame.kt +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/ReferenceFrame.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/angles.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/angles.kt new file mode 100644 index 000000000..3855514fb --- /dev/null +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/angles.kt @@ -0,0 +1,109 @@ +/* + * 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 kotlinx.serialization.KSerializer +import kotlinx.serialization.Serializable +import kotlinx.serialization.builtins.serializer +import kotlinx.serialization.descriptors.SerialDescriptor +import kotlinx.serialization.encoding.Decoder +import kotlinx.serialization.encoding.Encoder +import kotlin.jvm.JvmInline +import kotlin.math.PI +import kotlin.math.floor + +@Serializable(AngleSerializer::class) +public sealed interface Angle : Comparable { + public fun toRadians(): Radians + public fun toDegrees(): Degrees + + public operator fun plus(other: Angle): Angle + public operator fun minus(other: Angle): Angle + + public operator fun times(other: Number): Angle + public operator fun div(other: Number): Angle + public operator fun div(other: Angle): Double + public operator fun unaryMinus(): Angle + + public companion object { + public val zero: Radians = Radians(0.0) + public val pi: Radians = Radians(PI) + public val piTimes2: Radians = Radians(PI * 2) + public val piDiv2: Radians = Radians(PI / 2) + } +} + + +public object AngleSerializer : KSerializer { + override val descriptor: SerialDescriptor get() = Double.serializer().descriptor + + override fun deserialize(decoder: Decoder): Angle = decoder.decodeDouble().degrees + + override fun serialize(encoder: Encoder, value: Angle) { + encoder.encodeDouble(value.degrees) + } +} + +/** + * Type safe radians + */ +@Serializable +@JvmInline +public value class Radians(public val value: Double) : Angle { + override fun toRadians(): Radians = this + override fun toDegrees(): Degrees = Degrees(value * 180 / PI) + + public override fun plus(other: Angle): Radians = Radians(value + other.radians) + public override fun minus(other: Angle): Radians = Radians(value - other.radians) + + public override fun times(other: Number): Radians = Radians(value * other.toDouble()) + public override fun div(other: Number): Radians = Radians(value / other.toDouble()) + override fun div(other: Angle): Double = value / other.radians + + public override fun unaryMinus(): Radians = Radians(-value) + + override fun compareTo(other: Angle): Int = value.compareTo(other.radians) +} + +public fun sin(angle: Angle): Double = kotlin.math.sin(angle.toRadians().value) +public fun cos(angle: Angle): Double = kotlin.math.cos(angle.toRadians().value) +public fun tan(angle: Angle): Double = kotlin.math.tan(angle.toRadians().value) + +public val Number.radians: Radians get() = Radians(toDouble()) + +public val Angle.radians: Double get() = toRadians().value + +/** + * Type safe degrees + */ +@JvmInline +public value class Degrees(public val value: Double) : Angle { + override fun toRadians(): Radians = Radians(value * PI / 180) + override fun toDegrees(): Degrees = this + + public override fun plus(other: Angle): Degrees = Degrees(value + other.degrees) + public override fun minus(other: Angle): Degrees = Degrees(value - other.degrees) + + public override fun times(other: Number): Degrees = Degrees(value * other.toDouble()) + public override fun div(other: Number): Degrees = Degrees(value / other.toDouble()) + override fun div(other: Angle): Double = value / other.degrees + + public override fun unaryMinus(): Degrees = Degrees(-value) + + override fun compareTo(other: Angle): Int = value.compareTo(other.degrees) +} + +public val Number.degrees: Degrees get() = Degrees(toDouble()) + +public val Angle.degrees: Double get() = toDegrees().value + +/** + * Normalized angle 2 PI range symmetric around [center]. By default, uses (0, 2PI) range. + */ +public fun Angle.normalized(center: Angle = Angle.pi): Angle = + this - Angle.piTimes2 * floor((radians + PI - center.radians) / PI / 2) + +public fun abs(angle: Angle): Angle = if (angle < Angle.zero) -angle else angle \ No newline at end of file diff --git a/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/floatPrecision.kt b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/floatPrecision.kt new file mode 100644 index 000000000..ea46ab90f --- /dev/null +++ b/kmath-geometry/src/commonMain/kotlin/space/kscience/kmath/geometry/floatPrecision.kt @@ -0,0 +1,56 @@ +/* + * Copyright 2018-2023 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.geometry.GeometrySpace.Companion.DEFAULT_PRECISION + +/** + * Float equality within given [precision] + */ +public fun Double.equalsFloat(other: Double, precision: Double = DEFAULT_PRECISION): Boolean = + kotlin.math.abs(this - other) < precision + +/** + * Float equality within given [precision] + */ +public fun Double.equalsFloat(other: Float, precision: Double = DEFAULT_PRECISION): Boolean = + kotlin.math.abs(this - other) < precision + +/** + * Vector equality within given [precision] (using [GeometrySpace.norm] provided by the space + */ +public fun V.equalsVector( + space: GeometrySpace, + other: V, + precision: Double = DEFAULT_PRECISION, +): Boolean = with(space) { + norm(this@equalsVector - other) < precision +} + +/** + * Vector equality using Euclidian L2 norm and given [precision] + */ +public fun Float64Vector2D.equalsVector( + other: Float64Vector2D, + precision: Double = DEFAULT_PRECISION, +): Boolean = equalsVector(Euclidean2DSpace, other, precision) + +/** + * Vector equality using Euclidian L2 norm and given [precision] + */ +public fun Float64Vector3D.equalsVector( + other: Float64Vector3D, + precision: Double = DEFAULT_PRECISION, +): Boolean = equalsVector(Euclidean3DSpace, other, precision) + +/** + * Line equality using [GeometrySpace.norm] provided by the [space] and given [precision] + */ +public fun LineSegment.equalsLine( + space: GeometrySpace, + other: LineSegment, + precision: Double = DEFAULT_PRECISION, +): Boolean = begin.equalsVector(space, other.begin, precision) && end.equalsVector(space, other.end, precision) \ No newline at end of file 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 index 6ffc43739..c5c3487a1 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,7 +13,7 @@ package space.kscience.kmath.geometry * @param line line to which vector should be projected */ public fun GeometrySpace.projectToLine(vector: V, line: Line): V = with(line) { - base + (direction dot (vector - base)) / (direction dot direction) * direction + start + (direction dot (vector - start)) / (direction dot direction) * direction } /** 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 67c3666ed..1f3850c7c 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 @@ -1,37 +1,47 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.UnstableKMathAPI import space.kscience.kmath.complex.Quaternion import space.kscience.kmath.complex.QuaternionField +import space.kscience.kmath.complex.normalized 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 kotlin.math.pow import kotlin.math.sqrt -internal fun Vector3D.toQuaternion(): Quaternion = Quaternion(0.0, x, y, z) +internal fun DoubleVector3D.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 +public val Quaternion.theta: Radians get() = (kotlin.math.acos(normalized().w) * 2).radians + +/** + * Create a normalized Quaternion from rotation angle and rotation vector + */ +public fun Quaternion.Companion.fromRotation(theta: Angle, vector: DoubleVector3D): Quaternion { + val s = sin(theta / 2) + val c = cos(theta / 2) + val norm = with(Euclidean3DSpace) { vector.norm() } + return Quaternion(c, vector.x * s / norm, vector.y * s / norm, vector.z * s / norm) +} /** * An axis of quaternion rotation */ -public val Quaternion.vector: Vector3D +public val Quaternion.vector: DoubleVector3D get() { - val sint2 = sqrt(1 - w * w) - - return object : Vector3D { + return object : DoubleVector3D { + private val sint2 = sqrt(1 - w * w) 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 @@ -42,7 +52,7 @@ public val Quaternion.vector: Vector3D /** * Rotate a vector in a [Euclidean3DSpace] */ -public fun Euclidean3DSpace.rotate(vector: Vector3D, q: Quaternion): Vector3D = with(QuaternionField) { +public fun Euclidean3DSpace.rotate(vector: DoubleVector3D, q: Quaternion): DoubleVector3D = with(QuaternionField) { val p = vector.toQuaternion() (q * p * q.reciprocal).vector } @@ -50,10 +60,11 @@ public fun Euclidean3DSpace.rotate(vector: Vector3D, q: Quaternion): Vector3D = /** * Use a composition of quaternions to create a rotation */ -public fun Euclidean3DSpace.rotate(vector: Vector3D, composition: QuaternionField.() -> Quaternion): Vector3D = +@UnstableKMathAPI +public fun Euclidean3DSpace.rotate(vector: DoubleVector3D, composition: QuaternionField.() -> Quaternion): DoubleVector3D = rotate(vector, QuaternionField.composition()) -public fun Euclidean3DSpace.rotate(vector: Vector3D, matrix: Matrix): Vector3D { +public fun Euclidean3DSpace.rotate(vector: DoubleVector3D, matrix: Matrix): DoubleVector3D { require(matrix.colNum == 3 && matrix.rowNum == 3) { "Square 3x3 rotation matrix is required" } return with(DoubleField.linearSpace) { matrix.dot(vector).asVector3D() } } @@ -113,4 +124,87 @@ public fun Quaternion.Companion.fromRotationMatrix(matrix: Matrix): Quat z = 0.25 * s, ) } +} + +public enum class RotationOrder { + // proper Euler + XZX, + XYX, + YXY, + YZY, + ZYZ, + ZXZ, + + //Tait–Bryan + XZY, + XYZ, + YXZ, + YZX, + ZYX, + ZXY +} + +/** + * Based on https://github.com/mrdoob/three.js/blob/master/src/math/Quaternion.js + */ +public fun Quaternion.Companion.fromEuler( + a: Angle, + b: Angle, + c: Angle, + rotationOrder: RotationOrder, +): Quaternion { + val c1 = cos (a / 2) + val c2 = cos (b / 2) + val c3 = cos (c / 2) + + val s1 = sin (a / 2) + val s2 = sin (b / 2) + val s3 = sin (c / 2) + + return when (rotationOrder) { + + RotationOrder.XYZ -> Quaternion( + c1 * c2 * c3 - s1 * s2 * s3, + s1 * c2 * c3 + c1 * s2 * s3, + c1 * s2 * c3 - s1 * c2 * s3, + c1 * c2 * s3 + s1 * s2 * c3 + ) + + RotationOrder.YXZ -> Quaternion( + c1 * c2 * c3 + s1 * s2 * s3, + s1 * c2 * c3 + c1 * s2 * s3, + c1 * s2 * c3 - s1 * c2 * s3, + c1 * c2 * s3 - s1 * s2 * c3 + ) + + RotationOrder.ZXY -> Quaternion( + c1 * c2 * c3 - s1 * s2 * s3, + s1 * c2 * c3 - c1 * s2 * s3, + c1 * s2 * c3 + s1 * c2 * s3, + c1 * c2 * s3 + s1 * s2 * c3 + ) + + + RotationOrder.ZYX -> Quaternion( + c1 * c2 * c3 + s1 * s2 * s3, + s1 * c2 * c3 - c1 * s2 * s3, + c1 * s2 * c3 + s1 * c2 * s3, + c1 * c2 * s3 - s1 * s2 * c3 + ) + + RotationOrder.YZX -> Quaternion( + c1 * c2 * c3 - s1 * s2 * s3, + s1 * c2 * c3 + c1 * s2 * s3, + c1 * s2 * c3 + s1 * c2 * s3, + c1 * c2 * s3 - s1 * s2 * c3 + ) + + RotationOrder.XZY -> Quaternion( + c1 * c2 * c3 + s1 * s2 * s3, + s1 * c2 * c3 - c1 * s2 * s3, + c1 * s2 * c3 - s1 * c2 * s3, + c1 * c2 * s3 + s1 * s2 * c3 + ) + else -> TODO("Proper Euler rotation orders are not supported yet") + } } \ No newline at end of file diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/AngleTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/AngleTest.kt new file mode 100644 index 000000000..b8086eb75 --- /dev/null +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/AngleTest.kt @@ -0,0 +1,16 @@ +package space.kscience.kmath.geometry + +import kotlin.test.Test +import kotlin.test.assertEquals + +class AngleTest { + @Test + fun normalization() { + assertEquals(30.degrees, 390.degrees.normalized()) + assertEquals(30.degrees, (-330).degrees.normalized()) + assertEquals(200.degrees, 200.degrees.normalized()) + assertEquals(30.degrees, 390.degrees.normalized(Angle.zero)) + assertEquals(30.degrees, (-330).degrees.normalized(Angle.zero)) + assertEquals((-160).degrees, 200.degrees.normalized(Angle.zero)) + } +} \ No newline at end of file diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean2DSpaceTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean2DSpaceTest.kt index 6b5f474bc..22cbee6f0 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean2DSpaceTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean2DSpaceTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,16 +12,16 @@ import kotlin.test.assertEquals internal class Euclidean2DSpaceTest { @Test fun zero() { - assertVectorEquals(Vector2D(0.0, 0.0), Euclidean2DSpace.zero) + assertVectorEquals(Euclidean2DSpace.vector(0.0, 0.0), Euclidean2DSpace.zero) } @Test fun norm() { with(Euclidean2DSpace) { - assertEquals(0.0, zero.norm()) - assertEquals(1.0, Vector2D(1.0, 0.0).norm()) - assertEquals(sqrt(2.0), Vector2D(1.0, 1.0).norm()) - assertEquals(sqrt(5.002001), Vector2D(-2.0, 1.001).norm()) + assertEquals(0.0, norm(zero)) + assertEquals(1.0, norm(vector(1.0, 0.0))) + assertEquals(sqrt(2.0), norm(vector(1.0, 1.0))) + assertEquals(sqrt(5.002001), norm(vector(-2.0, 1.001))) } } @@ -29,16 +29,16 @@ internal class Euclidean2DSpaceTest { fun dotProduct() { with(Euclidean2DSpace) { assertEquals(0.0, zero dot zero) - assertEquals(0.0, zero dot Vector2D(1.0, 0.0)) - assertEquals(0.0, Vector2D(-2.0, 0.001) dot zero) - assertEquals(0.0, Vector2D(1.0, 0.0) dot Vector2D(0.0, 1.0)) + assertEquals(0.0, zero dot vector(1.0, 0.0)) + assertEquals(0.0, vector(-2.0, 0.001) dot zero) + assertEquals(0.0, vector(1.0, 0.0) dot vector(0.0, 1.0)) - assertEquals(1.0, Vector2D(1.0, 0.0) dot Vector2D(1.0, 0.0)) - assertEquals(-2.0, Vector2D(0.0, 1.0) dot Vector2D(1.0, -2.0)) - assertEquals(2.0, Vector2D(1.0, 1.0) dot Vector2D(1.0, 1.0)) - assertEquals(4.001001, Vector2D(-2.0, 1.001) dot Vector2D(-2.0, 0.001)) + assertEquals(1.0, vector(1.0, 0.0) dot vector(1.0, 0.0)) + assertEquals(-2.0, vector(0.0, 1.0) dot vector(1.0, -2.0)) + assertEquals(2.0, vector(1.0, 1.0) dot vector(1.0, 1.0)) + assertEquals(4.001001, vector(-2.0, 1.001) dot vector(-2.0, 0.001)) - assertEquals(-4.998, Vector2D(1.0, 2.0) dot Vector2D(-5.0, 0.001)) + assertEquals(-4.998, vector(1.0, 2.0) dot vector(-5.0, 0.001)) } } @@ -46,12 +46,12 @@ internal class Euclidean2DSpaceTest { fun add() { with(Euclidean2DSpace) { assertVectorEquals( - Vector2D(-2.0, 0.001), - Vector2D(-2.0, 0.001) + zero + vector(-2.0, 0.001), + vector(-2.0, 0.001) + zero ) assertVectorEquals( - Vector2D(-3.0, 3.001), - Vector2D(2.0, 3.0) + Vector2D(-5.0, 0.001) + vector(-3.0, 3.001), + vector(2.0, 3.0) + vector(-5.0, 0.001) ) } } @@ -59,9 +59,9 @@ internal class Euclidean2DSpaceTest { @Test fun multiply() { with(Euclidean2DSpace) { - assertVectorEquals(Vector2D(-4.0, 0.0), Vector2D(-2.0, 0.0) * 2) - assertVectorEquals(Vector2D(4.0, 0.0), Vector2D(-2.0, 0.0) * -2) - assertVectorEquals(Vector2D(300.0, 0.0003), Vector2D(100.0, 0.0001) * 3) + assertVectorEquals(vector(-4.0, 0.0), vector(-2.0, 0.0) * 2) + assertVectorEquals(vector(4.0, 0.0), vector(-2.0, 0.0) * -2) + assertVectorEquals(vector(300.0, 0.0003), vector(100.0, 0.0001) * 3) } } } diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean3DSpaceTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean3DSpaceTest.kt index 0bc91e77e..20e112ad1 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean3DSpaceTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Euclidean3DSpaceTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -11,21 +11,21 @@ import kotlin.test.assertEquals internal class Euclidean3DSpaceTest { @Test fun zero() { - assertVectorEquals(Vector3D(0.0, 0.0, 0.0), Euclidean3DSpace.zero) + assertVectorEquals(Euclidean3DSpace.vector(0.0, 0.0, 0.0), Euclidean3DSpace.zero) } @Test fun distance() { with(Euclidean3DSpace) { assertEquals(0.0, zero.distanceTo(zero)) - assertEquals(1.0, zero.distanceTo(Vector3D(1.0, 0.0, 0.0))) - assertEquals(kotlin.math.sqrt(5.000001), Vector3D(1.0, -2.0, 0.001).distanceTo(zero)) - assertEquals(0.0, Vector3D(1.0, -2.0, 0.001).distanceTo(Vector3D(1.0, -2.0, 0.001))) - assertEquals(0.0, Vector3D(1.0, 0.0, 0.0).distanceTo(Vector3D(1.0, 0.0, 0.0))) - assertEquals(kotlin.math.sqrt(2.0), Vector3D(1.0, 0.0, 0.0).distanceTo(Vector3D(1.0, 1.0, 1.0))) - assertEquals(3.1622778182822584, Vector3D(0.0, 1.0, 0.0).distanceTo(Vector3D(1.0, -2.0, 0.001))) - assertEquals(0.0, Vector3D(1.0, -2.0, 0.001).distanceTo(Vector3D(1.0, -2.0, 0.001))) - assertEquals(9.695050335093676, Vector3D(1.0, 2.0, 3.0).distanceTo(Vector3D(7.0, -5.0, 0.001))) + assertEquals(1.0, zero.distanceTo(vector(1.0, 0.0, 0.0))) + assertEquals(kotlin.math.sqrt(5.000001), vector(1.0, -2.0, 0.001).distanceTo(zero)) + assertEquals(0.0, vector(1.0, -2.0, 0.001).distanceTo(vector(1.0, -2.0, 0.001))) + assertEquals(0.0, vector(1.0, 0.0, 0.0).distanceTo(vector(1.0, 0.0, 0.0))) + assertEquals(kotlin.math.sqrt(2.0), vector(1.0, 0.0, 0.0).distanceTo(vector(1.0, 1.0, 1.0))) + assertEquals(3.1622778182822584, vector(0.0, 1.0, 0.0).distanceTo(vector(1.0, -2.0, 0.001))) + assertEquals(0.0, vector(1.0, -2.0, 0.001).distanceTo(vector(1.0, -2.0, 0.001))) + assertEquals(9.695050335093676, vector(1.0, 2.0, 3.0).distanceTo(vector(7.0, -5.0, 0.001))) } } @@ -33,9 +33,9 @@ internal class Euclidean3DSpaceTest { fun norm() { with(Euclidean3DSpace) { assertEquals(0.0, zero.norm()) - assertEquals(1.0, Vector3D(1.0, 0.0, 0.0).norm()) - assertEquals(kotlin.math.sqrt(3.0), Vector3D(1.0, 1.0, 1.0).norm()) - assertEquals(kotlin.math.sqrt(5.000001), Vector3D(1.0, -2.0, 0.001).norm()) + assertEquals(1.0, vector(1.0, 0.0, 0.0).norm()) + assertEquals(kotlin.math.sqrt(3.0), vector(1.0, 1.0, 1.0).norm()) + assertEquals(kotlin.math.sqrt(5.000001), vector(1.0, -2.0, 0.001).norm()) } } @@ -43,37 +43,52 @@ internal class Euclidean3DSpaceTest { fun dotProduct() { with(Euclidean3DSpace) { assertEquals(0.0, zero dot zero) - assertEquals(0.0, zero dot Vector3D(1.0, 0.0, 0.0)) - assertEquals(0.0, Vector3D(1.0, -2.0, 0.001) dot zero) + assertEquals(0.0, zero dot vector(1.0, 0.0, 0.0)) + assertEquals(0.0, vector(1.0, -2.0, 0.001) dot zero) - assertEquals(1.0, Vector3D(1.0, 0.0, 0.0) dot Vector3D(1.0, 0.0, 0.0)) - assertEquals(1.0, Vector3D(1.0, 0.0, 0.0) dot Vector3D(1.0, 1.0, 1.0)) - assertEquals(-2.0, Vector3D(0.0, 1.0, 0.0) dot Vector3D(1.0, -2.0, 0.001)) - assertEquals(3.0, Vector3D(1.0, 1.0, 1.0) dot Vector3D(1.0, 1.0, 1.0)) - assertEquals(5.000001, Vector3D(1.0, -2.0, 0.001) dot Vector3D(1.0, -2.0, 0.001)) + assertEquals(1.0, vector(1.0, 0.0, 0.0) dot vector(1.0, 0.0, 0.0)) + assertEquals(1.0, vector(1.0, 0.0, 0.0) dot vector(1.0, 1.0, 1.0)) + assertEquals(-2.0, vector(0.0, 1.0, 0.0) dot vector(1.0, -2.0, 0.001)) + assertEquals(3.0, vector(1.0, 1.0, 1.0) dot vector(1.0, 1.0, 1.0)) + assertEquals(5.000001, vector(1.0, -2.0, 0.001) dot vector(1.0, -2.0, 0.001)) - assertEquals(-2.997, Vector3D(1.0, 2.0, 3.0) dot Vector3D(7.0, -5.0, 0.001)) + assertEquals(-2.997, vector(1.0, 2.0, 3.0) dot vector(7.0, -5.0, 0.001)) } } @Test - fun add() { - with(Euclidean3DSpace) { - assertVectorEquals( - Vector3D(1.0, -2.0, 0.001), - Vector3D(1.0, -2.0, 0.001) + zero - ) - assertVectorEquals( - Vector3D(8.0, -3.0, 3.001), - Vector3D(1.0, 2.0, 3.0) + Vector3D(7.0, -5.0, 0.001) - ) - } + fun add() = with(Euclidean3DSpace) { + assertVectorEquals( + vector(1.0, -2.0, 0.001), + vector(1.0, -2.0, 0.001) + zero + ) + assertVectorEquals( + vector(8.0, -3.0, 3.001), + vector(1.0, 2.0, 3.0) + vector(7.0, -5.0, 0.001) + ) } @Test - fun multiply() { - with(Euclidean3DSpace) { - assertVectorEquals(Vector3D(2.0, -4.0, 0.0), Vector3D(1.0, -2.0, 0.0) * 2) - } + fun multiply() = with(Euclidean3DSpace) { + assertVectorEquals(vector(2.0, -4.0, 0.0), vector(1.0, -2.0, 0.0) * 2) + } + + @Test + fun vectorProduct() = with(Euclidean3DSpace) { + assertVectorEquals(zAxis, vectorProduct(xAxis, yAxis)) + assertVectorEquals(zAxis, xAxis cross yAxis) + assertVectorEquals(-zAxis, vectorProduct(yAxis, xAxis)) + } + + @Test + fun doubleVectorProduct() = with(Euclidean3DSpace) { + val a = vector(1, 2, -3) + val b = vector(-1, 0, 1) + val c = vector(4, 5, 6) + + val res = a cross (b cross c) + val expected = b * (a dot c) - c * (a dot b) + assertVectorEquals(expected, res) } + } diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionAlongTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionAlongTest.kt index dfb65a57c..cc74b06e3 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionAlongTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionAlongTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,14 +12,14 @@ internal class ProjectionAlongTest { @Test fun projectionIntoYEqualsX() { with(Euclidean2DSpace) { - val normal = Vector2D(-2.0, 2.0) - val base = Vector2D(2.3, 2.3) + val normal = vector(-2.0, 2.0) + val base = vector(2.3, 2.3) assertVectorEquals(zero, projectAlong(zero, normal, base)) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> val d = (y - x) / 2.0 - assertVectorEquals(Vector2D(x + d, y - d), projectAlong(Vector2D(x, y), normal, base)) + assertVectorEquals(vector(x + d, y - d), projectAlong(vector(x, y), normal, base)) } } } @@ -30,28 +30,28 @@ internal class ProjectionAlongTest { val a = 5.0 val b = -3.0 val c = -15.0 - val normal = Vector2D(-5.0, 3.0) - val base = Vector2D(3.0, 0.0) + val normal = vector(-5.0, 3.0) + val base = vector(3.0, 0.0) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> val xProj = (b * (b * x - a * y) - a * c) / (a * a + b * b) val yProj = (a * (-b * x + a * y) - b * c) / (a * a + b * b) - assertVectorEquals(Vector2D(xProj, yProj), projectAlong(Vector2D(x, y), normal, base)) + assertVectorEquals(vector(xProj, yProj), projectAlong(vector(x, y), normal, base)) } } } @Test - fun projectOntoPlane() { - val normal = Vector3D(1.0, 3.5, 0.07) - val base = Vector3D(2.0, -0.0037, 11.1111) + fun projectOntoPlane() = with(Euclidean3DSpace){ + val normal = vector(1.0, 3.5, 0.07) + val base = vector(2.0, -0.0037, 11.1111) with(Euclidean3DSpace) { val testDomain = (-10.0..10.0).generateList(0.43) for (x in testDomain) { for (y in testDomain) { for (z in testDomain) { - val v = Vector3D(x, y, z) + val v = vector(x, y, z) val result = projectAlong(v, normal, base) // assert that result is on plane diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionOntoLineTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionOntoLineTest.kt index 076025110..7c6c105cf 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionOntoLineTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/ProjectionOntoLineTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,10 +12,10 @@ internal class ProjectionOntoLineTest { @Test fun projectionIntoOx() { with(Euclidean2DSpace) { - val ox = Line(zero, Vector2D(1.0, 0.0)) + val ox = Line(zero, vector(1.0, 0.0)) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> - assertVectorEquals(Vector2D(x, 0.0), projectToLine(Vector2D(x, y), ox)) + assertVectorEquals(vector(x, 0.0), projectToLine(vector(x, y), ox)) } } } @@ -23,10 +23,10 @@ internal class ProjectionOntoLineTest { @Test fun projectionIntoOy() { with(Euclidean2DSpace) { - val line = Line(zero, Vector2D(0.0, 1.0)) + val line = Line(zero, vector(0.0, 1.0)) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> - assertVectorEquals(Vector2D(0.0, y), projectToLine(Vector2D(x, y), line)) + assertVectorEquals(vector(0.0, y), projectToLine(vector(x, y), line)) } } } @@ -34,13 +34,13 @@ internal class ProjectionOntoLineTest { @Test fun projectionIntoYEqualsX() { with(Euclidean2DSpace) { - val line = Line(zero, Vector2D(1.0, 1.0)) + val line = Line(zero, vector(1.0, 1.0)) assertVectorEquals(zero, projectToLine(zero, line)) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> val d = (y - x) / 2.0 - assertVectorEquals(Vector2D(x + d, y - d), projectToLine(Vector2D(x, y), line)) + assertVectorEquals(vector(x + d, y - d), projectToLine(vector(x, y), line)) } } } @@ -51,38 +51,38 @@ internal class ProjectionOntoLineTest { val a = 5.0 val b = -3.0 val c = -15.0 - val line = Line(Vector2D(3.0, 0.0), Vector2D(3.0, 5.0)) + val line = Line(vector(3.0, 0.0), vector(3.0, 5.0)) grid(-10.0..10.0, -10.0..10.0, 0.15).forEach { (x, y) -> val xProj = (b * (b * x - a * y) - a * c) / (a * a + b * b) val yProj = (a * (-b * x + a * y) - b * c) / (a * a + b * b) - assertVectorEquals(Vector2D(xProj, yProj), projectToLine(Vector2D(x, y), line)) + assertVectorEquals(vector(xProj, yProj), projectToLine(vector(x, y), line)) } } } @Test - fun projectionOntoLine3d() { - val line = Line3D( - base = Vector3D(1.0, 3.5, 0.07), - direction = Vector3D(2.0, -0.0037, 11.1111) + fun projectionOntoLine3d() = with(Euclidean3DSpace) { + val line = Line( + base = vector(1.0, 3.5, 0.07), + direction = vector(2.0, -0.0037, 11.1111) ) - with(Euclidean3DSpace) { - val testDomain = (-10.0..10.0).generateList(0.43) - for (x in testDomain) { - for (y in testDomain) { - for (z in testDomain) { - val v = Vector3D(x, y, z) - val result = projectToLine(v, line) - - // assert that result is on line - assertTrue(isCollinear(result - line.base, line.direction)) - // assert that PV vector is orthogonal to direction vector - assertTrue(isOrthogonal(v - result, line.direction)) - } + + val testDomain = (-10.0..10.0).generateList(0.43) + for (x in testDomain) { + for (y in testDomain) { + for (z in testDomain) { + val v = vector(x, y, z) + val result = projectToLine(v, line) + + // assert that result is on the line + assertTrue(isCollinear(result - line.start, line.direction)) + // assert that PV vector is orthogonal to direction vector + assertTrue(isOrthogonal(v - result, line.direction)) } } } + } } 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 89b69d0f2..6177382a2 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,24 +7,25 @@ package space.kscience.kmath.geometry import space.kscience.kmath.complex.Quaternion import space.kscience.kmath.complex.normalized +import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.testutils.assertBufferEquals import kotlin.test.Test class RotationTest { @Test - fun rotations() = with(Euclidean3DSpace) { - val vector = Vector3D(1.0, 1.0, 1.0) + fun differentRotations() = with(Euclidean3DSpace) { + val vector = vector(1.0, 1.0, 1.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) + val rotatedByM = rotate(vector, matrix) assertBufferEquals(rotatedByQ, rotatedByM, 1e-4) } @Test - fun rotationConversion() { + fun matrixConversion() { val q = Quaternion(1.0, 2.0, -3.0, 4.0).normalized() @@ -32,4 +33,18 @@ class RotationTest { assertBufferEquals(q, Quaternion.fromRotationMatrix(matrix)) } + + @Test + fun fromRotation() { + val q = Quaternion.fromRotation(0.3.radians, Euclidean3DSpace.vector(1.0, 1.0, 1.0)) + + assertBufferEquals(DoubleBuffer(0.9887711, 0.0862781, 0.0862781, 0.0862781), q) + } + + @Test + fun fromEuler() { + val q = Quaternion.fromEuler(0.1.radians, 0.2.radians, 0.3.radians, RotationOrder.ZXY) + + assertBufferEquals(DoubleBuffer(0.9818562, 0.0342708, 0.1060205, 0.1534393), q) + } } \ No newline at end of file diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector2DTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector2DTest.kt index 5e45b4870..0db06f4c8 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector2DTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector2DTest.kt @@ -1,16 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.operations.toList import kotlin.test.Test import kotlin.test.assertEquals internal class Vector2DTest { - private val vector = Vector2D(1.0, -7.999) + private val vector = Euclidean2DSpace.vector(1.0, -7.999) @Test fun size() { diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector3DTest.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector3DTest.kt index 55bab4775..1c8607838 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector3DTest.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/Vector3DTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,7 +10,7 @@ import kotlin.test.Test import kotlin.test.assertEquals internal class Vector3DTest { - private val vector = Vector3D(1.0, -7.999, 0.001) + private val vector = Euclidean3DSpace.vector(1.0, -7.999, 0.001) @Test fun size() { diff --git a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/testUtils.kt b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/testUtils.kt index 0f957529d..c62af3cd3 100644 --- a/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/testUtils.kt +++ b/kmath-geometry/src/commonTest/kotlin/space/kscience/kmath/geometry/testUtils.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -25,12 +25,12 @@ fun grid( return xs.flatMap { x -> ys.map { y -> x to y } } } -fun assertVectorEquals(expected: Vector2D, actual: Vector2D, absoluteTolerance: Double = 1e-6) { +fun assertVectorEquals(expected: DoubleVector2D, actual: DoubleVector2D, absoluteTolerance: Double = 1e-6) { assertEquals(expected.x, actual.x, absoluteTolerance) assertEquals(expected.y, actual.y, absoluteTolerance) } -fun assertVectorEquals(expected: Vector3D, actual: Vector3D, absoluteTolerance: Double = 1e-6) { +fun assertVectorEquals(expected: DoubleVector3D, actual: DoubleVector3D, absoluteTolerance: Double = 1e-6) { assertEquals(expected.x, actual.x, absoluteTolerance) assertEquals(expected.y, actual.y, absoluteTolerance) assertEquals(expected.z, actual.z, absoluteTolerance) @@ -44,3 +44,6 @@ fun GeometrySpace.isCollinear(a: V, b: V, absoluteTolerance: Dou fun GeometrySpace.isOrthogonal(a: V, b: V, absoluteTolerance: Double = 1e-6): Boolean = abs(a dot b) < absoluteTolerance + +fun Double.equalFloat(other: Double, maxFloatDelta: Double = 0.000001): + Boolean = kotlin.math.abs(this - other) < maxFloatDelta \ No newline at end of file diff --git a/kmath-geometry/src/jvmMain/kotlin/space/kscience/kmath/geometry/lineExtensions.kt b/kmath-geometry/src/jvmMain/kotlin/space/kscience/kmath/geometry/lineExtensions.kt new file mode 100644 index 000000000..5fcd2b23e --- /dev/null +++ b/kmath-geometry/src/jvmMain/kotlin/space/kscience/kmath/geometry/lineExtensions.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. + */ + +import space.kscience.kmath.geometry.GeometrySpace +import space.kscience.kmath.geometry.Line +import space.kscience.kmath.geometry.LineSegment +import space.kscience.kmath.geometry.Vector +import space.kscience.kmath.operations.Group + +/** + * Get a line, containing this [LineSegment] + */ +context(Group) public val LineSegment.line: Line get() = Line(begin, end - begin) + +/** + * Get a length of a line segment + */ +context(GeometrySpace) public val LineSegment.length: Double get() = norm(end - begin) \ No newline at end of file diff --git a/kmath-histograms/README.md b/kmath-histograms/README.md index 5fd91ee0c..bc7f0fa5b 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-histograms:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-histograms:0.3.1-dev-1' + implementation 'space.kscience:kmath-histograms:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-histograms:0.3.1-dev-1") + implementation("space.kscience:kmath-histograms:0.4.0-dev-1") } ``` diff --git a/kmath-histograms/build.gradle.kts b/kmath-histograms/build.gradle.kts index 786086c9f..33704c29e 100644 --- a/kmath-histograms/build.gradle.kts +++ b/kmath-histograms/build.gradle.kts @@ -1,6 +1,11 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") +} + +kscience{ + jvm() + js() + native() } //apply(plugin = "kotlinx-atomicfu") @@ -9,7 +14,7 @@ kotlin.sourceSets { commonMain { dependencies { api(project(":kmath-core")) - api(npmlibs.atomicfu) + api(spclibs.atomicfu) } } commonTest { @@ -22,5 +27,5 @@ kotlin.sourceSets { } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } 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 fe3278026..43ed24c70 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 12edafd81..a4ae6d935 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 710e4478b..f50610a17 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 @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.UnstableKMathAPI 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 import space.kscience.kmath.structures.Buffer 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 68b24db5d..5fdc2ffb0 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 @@ -1,15 +1,16 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.PerformancePitfall import space.kscience.kmath.domains.Domain import space.kscience.kmath.linear.Point -import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.nd.ColumnStrides import space.kscience.kmath.nd.FieldOpsND -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.Group import space.kscience.kmath.operations.ScaleOperations @@ -24,6 +25,7 @@ public class HistogramND, D : Domain, V : Any>( internal val values: StructureND, ) : Histogram> { + @OptIn(PerformancePitfall::class) override fun get(point: Point): DomainBin? { val index = group.getIndexOrNull(point) ?: return null return group.produceBin(index, values[index]) @@ -31,8 +33,9 @@ public class HistogramND, D : Domain, V : Any>( override val dimension: Int get() = group.shape.size + @OptIn(PerformancePitfall::class) override val bins: Iterable> - get() = DefaultStrides(group.shape).asSequence().map { + get() = ColumnStrides(group.shape).asSequence().map { group.produceBin(it, values[it]) }.asIterable() } @@ -42,7 +45,7 @@ public class HistogramND, D : Domain, V : Any>( */ public interface HistogramGroupND, D : Domain, V : Any> : Group>, ScaleOperations> { - public val shape: Shape + public val shape: ShapeND public val valueAlgebraND: FieldOpsND //= 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 e13928394..154d35350 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.UnstableKMathAPI 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 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 1ead049e6..61ce450a7 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,13 +7,12 @@ package space.kscience.kmath.histogram +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI 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.operations.* import space.kscience.kmath.structures.* import kotlin.math.floor @@ -40,7 +39,7 @@ public class UniformHistogramGroupND>( public val dimension: Int get() = lower.size - override val shape: IntArray = IntArray(binNums.size) { binNums[it] + 2 } + override val shape: ShapeND = ShapeND(IntArray(binNums.size) { binNums[it] + 2 }) private val binSize = DoubleBuffer(dimension) { (upper[it] - lower[it]) / binNums[it] } @@ -83,8 +82,12 @@ public class UniformHistogramGroupND>( } - override fun produce(builder: HistogramBuilder.() -> Unit): HistogramND { - val ndCounter = StructureND.buffered(shape) { Counter.of(valueAlgebraND.elementAlgebra) } + @OptIn(PerformancePitfall::class) + override fun produce( + builder: HistogramBuilder.() -> Unit, + ): HistogramND { + val ndCounter: BufferND> = + StructureND.buffered(shape) { Counter.of(valueAlgebraND.elementAlgebra) } val hBuilder = object : HistogramBuilder { override val defaultValue: V get() = valueAlgebraND.elementAlgebra.one @@ -94,7 +97,8 @@ public class UniformHistogramGroupND>( } } hBuilder.apply(builder) - val values: BufferND = ndCounter.mapToBuffer(valueBufferFactory) { it.value } + val values: BufferND = BufferND(ndCounter.indices, ndCounter.buffer.mapToBuffer(valueBufferFactory) { it.value }) + return HistogramND(this, values) } 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 ca7c2f324..54806c9fa 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,8 +7,9 @@ package space.kscience.kmath.histogram -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.nd.ColumnStrides import space.kscience.kmath.operations.invoke import space.kscience.kmath.real.DoubleVector import kotlin.random.Random @@ -50,6 +51,7 @@ internal class MultivariateHistogramTest { assertEquals(n, histogram.bins.sumOf { it.binValue.toInt() }) } + @OptIn(PerformancePitfall::class) @Test fun testHistogramAlgebra() { Histogram.uniformDoubleNDFromRanges( @@ -73,7 +75,7 @@ internal class MultivariateHistogramTest { } val res = histogram1 - histogram2 assertTrue { - DefaultStrides(shape).asSequence().all { index -> + ColumnStrides(shape).asSequence().all { index -> res.values[index] <= histogram1.values[index] } } 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 09bf3939d..fa129fad6 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,10 +7,10 @@ package space.kscience.kmath.histogram import kotlinx.coroutines.ExperimentalCoroutinesApi import kotlinx.coroutines.test.runTest +import space.kscience.kmath.UnstableKMathAPI 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.random.RandomGenerator import space.kscience.kmath.stat.nextBuffer import kotlin.native.concurrent.ThreadLocal import kotlin.test.Test @@ -36,7 +36,7 @@ internal class UniformHistogram1DTest { @Test fun rebinDown() = runTest { val h1 = Histogram.uniform1D(DoubleField, 0.01).produce(generator.nextDoubleBuffer(10000)) - val h2 = Histogram.uniform1D(DoubleField,0.03).produceFrom(h1) + val h2 = Histogram.uniform1D(DoubleField, 0.03).produceFrom(h1) assertEquals(10000, h2.bins.sumOf { it.binValue }.toInt()) } @@ -44,13 +44,13 @@ internal class UniformHistogram1DTest { @Test fun rebinUp() = runTest { val h1 = Histogram.uniform1D(DoubleField, 0.03).produce(generator.nextDoubleBuffer(10000)) - val h2 = Histogram.uniform1D(DoubleField,0.01).produceFrom(h1) + val h2 = Histogram.uniform1D(DoubleField, 0.01).produceFrom(h1) assertEquals(10000, h2.bins.sumOf { it.binValue }.toInt()) } @ThreadLocal - companion object{ + companion object { private val generator = RandomGenerator.default(123) } } \ No newline at end of file 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 index 6bec01f9b..772db7df3 100644 --- a/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt +++ b/kmath-histograms/src/jvmMain/kotlin/space/kscience/kmath/histogram/TreeHistogramGroup.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,9 +7,9 @@ package space.kscience.kmath.histogram +import space.kscience.kmath.UnstableKMathAPI 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 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 2c56a88a7..b7c1f34ba 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 org.junit.jupiter.api.Test -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.real.step import kotlin.random.Random diff --git a/kmath-jafama/README.md b/kmath-jafama/README.md index c008c76ca..47142f174 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-jafama:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -17,7 +17,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-jafama:0.3.1-dev-1' + implementation 'space.kscience:kmath-jafama:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -28,7 +28,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-jafama:0.3.1-dev-1") + implementation("space.kscience:kmath-jafama:0.4.0-dev-1") } ``` diff --git a/kmath-jafama/build.gradle.kts b/kmath-jafama/build.gradle.kts index 925a2bc60..5a77a97ed 100644 --- a/kmath-jafama/build.gradle.kts +++ b/kmath-jafama/build.gradle.kts @@ -1,5 +1,5 @@ plugins { - id("ru.mipt.npm.gradle.jvm") + id("space.kscience.gradle.jvm") } description = "Jafama integration module" @@ -14,14 +14,10 @@ repositories { } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature("jafama-double", "src/main/kotlin/space/kscience/kmath/jafama/") { "Double ExtendedField implementations based on Jafama" } -} - -kotlin.sourceSets.all { - languageSettings.optIn("space.kscience.kmath.misc.UnstableKMathAPI") -} +} \ No newline at end of file diff --git a/kmath-jafama/src/main/kotlin/space/kscience/kmath/jafama/KMathJafama.kt b/kmath-jafama/src/main/kotlin/space/kscience/kmath/jafama/KMathJafama.kt index 91d952a76..f9b8287b4 100644 --- a/kmath-jafama/src/main/kotlin/space/kscience/kmath/jafama/KMathJafama.kt +++ b/kmath-jafama/src/main/kotlin/space/kscience/kmath/jafama/KMathJafama.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-jupyter/README.md b/kmath-jupyter/README.md index 3c9832625..2b26878dc 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-jupyter:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-jupyter:0.3.1-dev-1' + implementation 'space.kscience:kmath-jupyter:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-jupyter:0.3.1-dev-1") + implementation("space.kscience:kmath-jupyter:0.4.0-dev-1") } ``` diff --git a/kmath-jupyter/build.gradle.kts b/kmath-jupyter/build.gradle.kts index ca1a5485f..a0e217177 100644 --- a/kmath-jupyter/build.gradle.kts +++ b/kmath-jupyter/build.gradle.kts @@ -1,24 +1,17 @@ plugins { - id("ru.mipt.npm.gradle.jvm") + id("space.kscience.gradle.jvm") kotlin("jupyter.api") } dependencies { + api(spclibs.kotlinx.html) api(project(":kmath-ast")) api(project(":kmath-complex")) api(project(":kmath-for-real")) } -kscience { - useHtml() -} - readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE -} - -kotlin.sourceSets.all { - languageSettings.optIn("space.kscience.kmath.misc.UnstableKMathAPI") + maturity = space.kscience.gradle.Maturity.PROTOTYPE } tasks.processJupyterApiResources { diff --git a/kmath-jupyter/src/main/kotlin/space/kscience/kmath/jupyter/KMathJupyter.kt b/kmath-jupyter/src/main/kotlin/space/kscience/kmath/jupyter/KMathJupyter.kt index 504ad693e..944666c9e 100644 --- a/kmath-jupyter/src/main/kotlin/space/kscience/kmath/jupyter/KMathJupyter.kt +++ b/kmath-jupyter/src/main/kotlin/space/kscience/kmath/jupyter/KMathJupyter.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,6 +12,8 @@ import kotlinx.html.unsafe import org.jetbrains.kotlinx.jupyter.api.DisplayResult import org.jetbrains.kotlinx.jupyter.api.HTML import org.jetbrains.kotlinx.jupyter.api.libraries.JupyterIntegration +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.ast.rendering.FeaturedMathRendererWithPostProcess import space.kscience.kmath.ast.rendering.MathMLSyntaxRenderer import space.kscience.kmath.ast.rendering.renderWithStringBuilder @@ -19,7 +21,6 @@ import space.kscience.kmath.complex.Complex import space.kscience.kmath.complex.Quaternion import space.kscience.kmath.expressions.MST import space.kscience.kmath.expressions.MstRing -import space.kscience.kmath.misc.PerformancePitfall import space.kscience.kmath.nd.Structure2D import space.kscience.kmath.operations.asSequence import space.kscience.kmath.operations.invoke @@ -30,6 +31,7 @@ import space.kscience.kmath.structures.Buffer */ public fun Number.toMst(): MST.Numeric = MST.Numeric(this) +@OptIn(UnstableKMathAPI::class) internal class KMathJupyter : JupyterIntegration() { private val mathRender = FeaturedMathRendererWithPostProcess.Default private val syntaxRender = MathMLSyntaxRenderer @@ -47,11 +49,13 @@ internal class KMathJupyter : JupyterIntegration() { syntaxRender.renderPart(mathRender.render(MST.Numeric(it)), s) +s.toString() } + is MST -> { val s = StringBuilder() syntaxRender.renderPart(mathRender.render(it), s) +s.toString() } + else -> { +"" +it.toString() diff --git a/kmath-kotlingrad/README.md b/kmath-kotlingrad/README.md index 457652aaf..f1a918b4b 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-kotlingrad:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -18,7 +18,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-kotlingrad:0.3.1-dev-1' + implementation 'space.kscience:kmath-kotlingrad:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -29,6 +29,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-kotlingrad:0.3.1-dev-1") + implementation("space.kscience:kmath-kotlingrad:0.4.0-dev-1") } ``` diff --git a/kmath-kotlingrad/build.gradle.kts b/kmath-kotlingrad/build.gradle.kts index 2f6d41bbb..56e191360 100644 --- a/kmath-kotlingrad/build.gradle.kts +++ b/kmath-kotlingrad/build.gradle.kts @@ -1,12 +1,11 @@ plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } kotlin.sourceSets .filter { it.name.contains("test", true) } .map(org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet::languageSettings) - .forEach { it.optIn("space.kscience.kmath.misc.UnstableKMathAPI") } + .forEach { it.optIn("space.kscience.kmath.UnstableKMathAPI") } description = "Kotlin∇ integration module" @@ -18,7 +17,7 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( diff --git a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KMathNumber.kt b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KMathNumber.kt index f7858e172..cd35e0c42 100644 --- a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KMathNumber.kt +++ b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KMathNumber.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KotlingradExpression.kt b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KotlingradExpression.kt index 31b8a9286..110572140 100644 --- a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KotlingradExpression.kt +++ b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/KotlingradExpression.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/scalarsAdapters.kt b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/scalarsAdapters.kt index 37ce40cab..dd75a704c 100644 --- a/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/scalarsAdapters.kt +++ b/kmath-kotlingrad/src/main/kotlin/space/kscience/kmath/kotlingrad/scalarsAdapters.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-kotlingrad/src/test/kotlin/space/kscience/kmath/kotlingrad/AdaptingTests.kt b/kmath-kotlingrad/src/test/kotlin/space/kscience/kmath/kotlingrad/AdaptingTests.kt index 570d7dd7f..ccd89f063 100644 --- a/kmath-kotlingrad/src/test/kotlin/space/kscience/kmath/kotlingrad/AdaptingTests.kt +++ b/kmath-kotlingrad/src/test/kotlin/space/kscience/kmath/kotlingrad/AdaptingTests.kt @@ -1,11 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.kotlingrad import ai.hypergraph.kotlingrad.api.* +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.asm.compileToExpression import space.kscience.kmath.ast.parseMath import space.kscience.kmath.expressions.MstNumericAlgebra @@ -17,6 +18,7 @@ import kotlin.test.assertEquals import kotlin.test.assertTrue import kotlin.test.fail +@OptIn(UnstableKMathAPI::class) internal class AdaptingTests { @Test fun symbol() { diff --git a/kmath-memory/README.md b/kmath-memory/README.md index 536d7f145..594588ecf 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-memory:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-memory:0.3.1-dev-1' + implementation 'space.kscience:kmath-memory:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-memory:0.3.1-dev-1") + implementation("space.kscience:kmath-memory:0.4.0-dev-1") } ``` diff --git a/kmath-memory/api/kmath-memory.api b/kmath-memory/api/kmath-memory.api index 9c9641461..cebb04af2 100644 --- a/kmath-memory/api/kmath-memory.api +++ b/kmath-memory/api/kmath-memory.api @@ -1,3 +1,14 @@ +public abstract interface annotation class space/kscience/kmath/PerformancePitfall : java/lang/annotation/Annotation { + public abstract fun message ()Ljava/lang/String; +} + +public abstract interface annotation class space/kscience/kmath/UnsafeKMathAPI : java/lang/annotation/Annotation { + public abstract fun message ()Ljava/lang/String; +} + +public abstract interface annotation class space/kscience/kmath/UnstableKMathAPI : java/lang/annotation/Annotation { +} + public final class space/kscience/kmath/memory/ByteBufferMemory : space/kscience/kmath/memory/Memory { public fun (Ljava/nio/ByteBuffer;II)V public synthetic fun (Ljava/nio/ByteBuffer;IIILkotlin/jvm/internal/DefaultConstructorMarker;)V @@ -36,7 +47,8 @@ public final class space/kscience/kmath/memory/MemoryKt { public static final fun write (Lspace/kscience/kmath/memory/Memory;Lkotlin/jvm/functions/Function1;)V } -public abstract interface class space/kscience/kmath/memory/MemoryReader { +public abstract interface class space/kscience/kmath/memory/MemoryReader : java/lang/AutoCloseable { + public abstract fun close ()V public abstract fun getMemory ()Lspace/kscience/kmath/memory/Memory; public abstract fun readByte (I)B public abstract fun readDouble (I)D @@ -44,7 +56,6 @@ public abstract interface class space/kscience/kmath/memory/MemoryReader { public abstract fun readInt (I)I public abstract fun readLong (I)J public abstract fun readShort (I)S - public abstract fun release ()V } public abstract interface class space/kscience/kmath/memory/MemorySpec { @@ -59,9 +70,9 @@ public final class space/kscience/kmath/memory/MemorySpecKt { public static final fun writeArray (Lspace/kscience/kmath/memory/MemoryWriter;Lspace/kscience/kmath/memory/MemorySpec;I[Ljava/lang/Object;)V } -public abstract interface class space/kscience/kmath/memory/MemoryWriter { +public abstract interface class space/kscience/kmath/memory/MemoryWriter : java/lang/AutoCloseable { + public abstract fun close ()V public abstract fun getMemory ()Lspace/kscience/kmath/memory/Memory; - public abstract fun release ()V public abstract fun writeByte (IB)V public abstract fun writeDouble (ID)V public abstract fun writeFloat (IF)V diff --git a/kmath-memory/build.gradle.kts b/kmath-memory/build.gradle.kts index 2bd6dd723..fe422f751 100644 --- a/kmath-memory/build.gradle.kts +++ b/kmath-memory/build.gradle.kts @@ -1,10 +1,16 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") +} + +kscience { + jvm() + js() + native() + wasm() } readme { - maturity = ru.mipt.npm.gradle.Maturity.DEVELOPMENT + maturity = space.kscience.gradle.Maturity.DEVELOPMENT description = """ An API and basic implementation for arranging objects in a continuous memory block. """.trimIndent() diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/annotations.kt similarity index 74% rename from kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt rename to kmath-memory/src/commonMain/kotlin/space/kscience/kmath/annotations.kt index 60fa81cd8..a95b166cf 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/misc/annotations.kt +++ b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/annotations.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2023 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.misc +package space.kscience.kmath /** * Marks declarations that are still experimental in the KMath APIs, which means that the design of the corresponding @@ -29,3 +29,16 @@ public annotation class UnstableKMathAPI public annotation class PerformancePitfall( val message: String = "Potential performance problem", ) + +/** + * Marks API that is public, but should not be used without clear understanding what it does. + */ +@MustBeDocumented +@Retention(value = AnnotationRetention.BINARY) +@RequiresOptIn( + "This API is unsafe and should be used carefully", + RequiresOptIn.Level.ERROR, +) +public annotation class UnsafeKMathAPI( + val message: String = "Unsafe API", +) diff --git a/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/Memory.kt b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/Memory.kt index e8e51e9e2..a63753015 100644 --- a/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/Memory.kt +++ b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/Memory.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -43,7 +43,7 @@ public interface Memory { /** * The interface to read primitive types in this memory. */ -public interface MemoryReader { +public interface MemoryReader: AutoCloseable { /** * The underlying memory. */ @@ -82,7 +82,7 @@ public interface MemoryReader { /** * Disposes this reader if needed. */ - public fun release() + override fun close() } /** @@ -90,16 +90,13 @@ public interface MemoryReader { */ public inline fun Memory.read(block: MemoryReader.() -> R): R { contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - val reader = reader() - val result = reader.block() - reader.release() - return result + return reader().use(block) } /** * The interface to write primitive types into this memory. */ -public interface MemoryWriter { +public interface MemoryWriter: AutoCloseable { /** * The underlying memory. */ @@ -138,7 +135,7 @@ public interface MemoryWriter { /** * Disposes this writer if needed. */ - public fun release() + override fun close() } /** @@ -146,7 +143,7 @@ public interface MemoryWriter { */ public inline fun Memory.write(block: MemoryWriter.() -> Unit) { contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - writer().apply(block).release() + writer().use(block) } /** diff --git a/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/MemorySpec.kt b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/MemorySpec.kt index 1ee1cf4e2..19bc3bae4 100644 --- a/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/MemorySpec.kt +++ b/kmath-memory/src/commonMain/kotlin/space/kscience/kmath/memory/MemorySpec.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-memory/src/commonTest/kotlin/space/kscience/kmath/memory/MemoryTest.kt b/kmath-memory/src/commonTest/kotlin/space/kscience/kmath/memory/MemoryTest.kt new file mode 100644 index 000000000..3726ddbb7 --- /dev/null +++ b/kmath-memory/src/commonTest/kotlin/space/kscience/kmath/memory/MemoryTest.kt @@ -0,0 +1,37 @@ +/* + * Copyright 2018-2023 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.memory + +import kotlin.test.Test +import kotlin.test.assertEquals + +class MemoryTest { + @Test + fun memoryWriteRead() { + val memorySize = 60 + val data = buildList { + for (i in 0 until (memorySize / 4)) { + add(i) + } + } + val memory = Memory.allocate(memorySize) + memory.write { + for (i in 0 until (memory.size / 4)) { + writeInt(i*4, data[i]) + } + } + + val result = memory.read { + buildList { + for (i in 0 until (memory.size / 4)) { + add(readInt(i*4)) + } + } + } + + assertEquals(data,result) + } +} \ No newline at end of file diff --git a/kmath-memory/src/jsMain/kotlin/space/kscience/kmath/memory/DataViewMemory.kt b/kmath-memory/src/jsMain/kotlin/space/kscience/kmath/memory/DataViewMemory.kt index 6153743fc..f8bcef010 100644 --- a/kmath-memory/src/jsMain/kotlin/space/kscience/kmath/memory/DataViewMemory.kt +++ b/kmath-memory/src/jsMain/kotlin/space/kscience/kmath/memory/DataViewMemory.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -41,7 +41,7 @@ private class DataViewMemory(val view: DataView) : Memory { override fun readLong(offset: Int): Long = view.getInt32(offset, false).toLong() shl 32 or view.getInt32(offset + 4, false).toLong() - override fun release() { + override fun close() { // does nothing on JS } } @@ -76,7 +76,7 @@ private class DataViewMemory(val view: DataView) : Memory { view.setInt32(offset + 4, (value and 0xffffffffL).toInt(), littleEndian = false) } - override fun release() { + override fun close() { // does nothing on JS } } diff --git a/kmath-memory/src/jvmMain/kotlin/space/kscience/kmath/memory/ByteBufferMemory.kt b/kmath-memory/src/jvmMain/kotlin/space/kscience/kmath/memory/ByteBufferMemory.kt index aef68fd80..d022cab23 100644 --- a/kmath-memory/src/jvmMain/kotlin/space/kscience/kmath/memory/ByteBufferMemory.kt +++ b/kmath-memory/src/jvmMain/kotlin/space/kscience/kmath/memory/ByteBufferMemory.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -20,8 +20,7 @@ internal class ByteBufferMemory( val startOffset: Int = 0, override val size: Int = buffer.limit(), ) : Memory { - @Suppress("NOTHING_TO_INLINE") - private inline fun position(o: Int): Int = startOffset + o + private fun position(offset: Int): Int = startOffset + offset override fun view(offset: Int, length: Int): Memory { require(offset >= 0) { "offset shouldn't be negative: $offset" } @@ -53,7 +52,7 @@ internal class ByteBufferMemory( override fun readLong(offset: Int) = buffer.getLong(position(offset)) - override fun release() { + override fun close() { // does nothing on JVM } } @@ -87,7 +86,7 @@ internal class ByteBufferMemory( buffer.putLong(position(offset), value) } - override fun release() { + override fun close() { // does nothing on JVM } } @@ -120,7 +119,7 @@ public fun ByteBuffer.asMemory(startOffset: Int = 0, size: Int = limit()): Memor ByteBufferMemory(this, startOffset, size) /** - * Uses direct memory-mapped buffer from file to read something and close it afterwards. + * Uses direct memory-mapped buffer from file to read something and close it afterward. */ @Throws(IOException::class) public inline fun Path.readAsMemory(position: Long = 0, size: Long = Files.size(this), block: Memory.() -> R): R { diff --git a/kmath-memory/src/nativeMain/kotlin/space/kscience/kmath/memory/NativeMemory.kt b/kmath-memory/src/nativeMain/kotlin/space/kscience/kmath/memory/NativeMemory.kt index 5146d9689..32bc8d6a5 100644 --- a/kmath-memory/src/nativeMain/kotlin/space/kscience/kmath/memory/NativeMemory.kt +++ b/kmath-memory/src/nativeMain/kotlin/space/kscience/kmath/memory/NativeMemory.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -41,7 +41,7 @@ internal class NativeMemory( override fun readLong(offset: Int) = array.getLongAt(position(offset)) - override fun release() { + override fun close() { // does nothing on JVM } } @@ -75,7 +75,7 @@ internal class NativeMemory( array.setLongAt(position(offset), value) } - override fun release() { + override fun close() { // does nothing on JVM } } diff --git a/kmath-memory/src/wasmMain/kotlin/space/kscience/kmath/memory/WasmDataViewMemory.kt b/kmath-memory/src/wasmMain/kotlin/space/kscience/kmath/memory/WasmDataViewMemory.kt new file mode 100644 index 000000000..0cff551fa --- /dev/null +++ b/kmath-memory/src/wasmMain/kotlin/space/kscience/kmath/memory/WasmDataViewMemory.kt @@ -0,0 +1,103 @@ +/* + * Copyright 2018-2022 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.memory + +import org.khronos.webgl.ArrayBuffer +import org.khronos.webgl.DataView +import org.khronos.webgl.Int8Array + +private class WasmDataViewMemory(val view: DataView) : Memory { + override val size: Int get() = view.byteLength + + override fun view(offset: Int, length: Int): Memory { + require(offset >= 0) { "offset shouldn't be negative: $offset" } + require(length >= 0) { "length shouldn't be negative: $length" } + require(offset + length <= size) { "Can't view memory outside the parent region." } + + if (offset + length > size) + throw IndexOutOfBoundsException("offset + length > size: $offset + $length > $size") + + return WasmDataViewMemory(DataView(view.buffer, view.byteOffset + offset, length)) + } + + override fun copy(): Memory = WasmDataViewMemory(DataView(view.buffer.slice(0))) + + private val reader: MemoryReader = object : MemoryReader { + override val memory: Memory get() = this@WasmDataViewMemory + + override fun readDouble(offset: Int): Double = view.getFloat64(offset, false) + + override fun readFloat(offset: Int): Float = view.getFloat32(offset, false) + + override fun readByte(offset: Int): Byte = view.getInt8(offset) + + override fun readShort(offset: Int): Short = view.getInt16(offset, false) + + override fun readInt(offset: Int): Int = view.getInt32(offset, false) + + override fun readLong(offset: Int): Long = + view.getInt32(offset, false).toLong() shl 32 or view.getInt32(offset + 4, false).toLong() + + override fun close() { + // does nothing on JS + } + } + + override fun reader(): MemoryReader = reader + + private val writer: MemoryWriter = object : MemoryWriter { + override val memory: Memory get() = this@WasmDataViewMemory + + override fun writeDouble(offset: Int, value: Double) { + view.setFloat64(offset, value, false) + } + + override fun writeFloat(offset: Int, value: Float) { + view.setFloat32(offset, value, false) + } + + override fun writeByte(offset: Int, value: Byte) { + view.setInt8(offset, value) + } + + override fun writeShort(offset: Int, value: Short) { + view.setUint16(offset, value, false) + } + + override fun writeInt(offset: Int, value: Int) { + view.setInt32(offset, value, false) + } + + override fun writeLong(offset: Int, value: Long) { + view.setInt32(offset, (value shr 32).toInt(), littleEndian = false) + view.setInt32(offset + 4, (value and 0xffffffffL).toInt(), littleEndian = false) + } + + override fun close() { + // does nothing on JS + } + } + + override fun writer(): MemoryWriter = writer + +} + +/** + * Allocates memory based on a [DataView]. + */ +public actual fun Memory.Companion.allocate(length: Int): Memory { + val buffer = ArrayBuffer(length) + return WasmDataViewMemory(DataView(buffer, 0, length)) +} + +/** + * Wraps a [Memory] around existing [ByteArray]. This operation is unsafe since the array is not copied + * and could be mutated independently of the resulting [Memory]. + */ +public actual fun Memory.Companion.wrap(array: ByteArray): Memory { + @Suppress("CAST_NEVER_SUCCEEDS") val int8Array = array as Int8Array + return WasmDataViewMemory(DataView(int8Array.buffer, int8Array.byteOffset, int8Array.length)) +} diff --git a/kmath-multik/README.md b/kmath-multik/README.md index 0f5b65b4c..127b12a49 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-multik:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-multik:0.3.1-dev-1' + implementation 'space.kscience:kmath-multik:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-multik:0.3.1-dev-1") + implementation("space.kscience:kmath-multik:0.4.0-dev-1") } ``` diff --git a/kmath-multik/build.gradle.kts b/kmath-multik/build.gradle.kts index df2292f2e..fc51d2c21 100644 --- a/kmath-multik/build.gradle.kts +++ b/kmath-multik/build.gradle.kts @@ -1,14 +1,32 @@ plugins { - id("ru.mipt.npm.gradle.jvm") + id("space.kscience.gradle.mpp") } description = "JetBrains Multik connector" -dependencies { - api(project(":kmath-tensors")) - api("org.jetbrains.kotlinx:multik-default:0.1.0") +val multikVersion: String by rootProject.extra + +kscience { + jvm() + js() +} + +kotlin{ + sourceSets{ + commonMain{ + dependencies{ + api(project(":kmath-tensors")) + api("org.jetbrains.kotlinx:multik-core:$multikVersion") + } + } + commonTest{ + dependencies{ + api("org.jetbrains.kotlinx:multik-default:$multikVersion") + } + } + } } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } \ No newline at end of file diff --git a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt similarity index 77% rename from kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt rename to kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt index 0de2d8349..beab5c18b 100644 --- a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikDoubleAlgebra.kt @@ -1,18 +1,23 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.multik +import org.jetbrains.kotlinx.multik.api.Engine +import org.jetbrains.kotlinx.multik.api.Multik +import org.jetbrains.kotlinx.multik.api.ndarrayOf import org.jetbrains.kotlinx.multik.ndarray.data.DataType -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.ExponentialOperations import space.kscience.kmath.operations.TrigonometricOperations -public object MultikDoubleAlgebra : MultikDivisionTensorAlgebra(), +public class MultikDoubleAlgebra( + multikEngine: Engine +) : MultikDivisionTensorAlgebra(multikEngine), TrigonometricOperations>, ExponentialOperations> { override val elementAlgebra: DoubleField get() = DoubleField override val type: DataType get() = DataType.DoubleDataType @@ -54,8 +59,10 @@ public object MultikDoubleAlgebra : MultikDivisionTensorAlgebra): MultikTensor = arg.map { atanh(it) } + + override fun scalar(value: Double): MultikTensor = Multik.ndarrayOf(value).wrap() } -public val Double.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikDoubleAlgebra -public val DoubleField.multikAlgebra: MultikTensorAlgebra get() = MultikDoubleAlgebra +//public val Double.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikDoubleAlgebra +//public val DoubleField.multikAlgebra: MultikTensorAlgebra get() = MultikDoubleAlgebra diff --git a/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikFloatAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikFloatAlgebra.kt new file mode 100644 index 000000000..ee194ae24 --- /dev/null +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikFloatAlgebra.kt @@ -0,0 +1,25 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.api.Engine +import org.jetbrains.kotlinx.multik.api.Multik +import org.jetbrains.kotlinx.multik.api.ndarrayOf +import org.jetbrains.kotlinx.multik.ndarray.data.DataType +import space.kscience.kmath.operations.FloatField + +public class MultikFloatAlgebra( + multikEngine: Engine +) : MultikDivisionTensorAlgebra(multikEngine) { + override val elementAlgebra: FloatField get() = FloatField + override val type: DataType get() = DataType.FloatDataType + + override fun scalar(value: Float): MultikTensor = Multik.ndarrayOf(value).wrap() +} + + +//public val Float.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikFloatAlgebra +//public val FloatField.multikAlgebra: MultikTensorAlgebra get() = MultikFloatAlgebra \ No newline at end of file diff --git a/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikIntAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikIntAlgebra.kt new file mode 100644 index 000000000..05b240787 --- /dev/null +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikIntAlgebra.kt @@ -0,0 +1,23 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.api.Engine +import org.jetbrains.kotlinx.multik.api.Multik +import org.jetbrains.kotlinx.multik.api.ndarrayOf +import org.jetbrains.kotlinx.multik.ndarray.data.DataType +import space.kscience.kmath.operations.IntRing + +public class MultikIntAlgebra( + multikEngine: Engine +) : MultikTensorAlgebra(multikEngine) { + override val elementAlgebra: IntRing get() = IntRing + override val type: DataType get() = DataType.IntDataType + override fun scalar(value: Int): MultikTensor = Multik.ndarrayOf(value).wrap() +} + +//public val Int.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikIntAlgebra +//public val IntRing.multikAlgebra: MultikTensorAlgebra get() = MultikIntAlgebra \ No newline at end of file diff --git a/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikLongAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikLongAlgebra.kt new file mode 100644 index 000000000..e713e556e --- /dev/null +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikLongAlgebra.kt @@ -0,0 +1,25 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.api.Engine +import org.jetbrains.kotlinx.multik.api.Multik +import org.jetbrains.kotlinx.multik.api.ndarrayOf +import org.jetbrains.kotlinx.multik.ndarray.data.DataType +import space.kscience.kmath.operations.LongRing + +public class MultikLongAlgebra( + multikEngine: Engine +) : MultikTensorAlgebra(multikEngine) { + override val elementAlgebra: LongRing get() = LongRing + override val type: DataType get() = DataType.LongDataType + + override fun scalar(value: Long): MultikTensor = Multik.ndarrayOf(value).wrap() +} + + +//public val Long.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikLongAlgebra +//public val LongRing.multikAlgebra: MultikTensorAlgebra get() = MultikLongAlgebra \ No newline at end of file diff --git a/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikShortAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikShortAlgebra.kt new file mode 100644 index 000000000..6e5ca5882 --- /dev/null +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikShortAlgebra.kt @@ -0,0 +1,23 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.api.Engine +import org.jetbrains.kotlinx.multik.api.Multik +import org.jetbrains.kotlinx.multik.api.ndarrayOf +import org.jetbrains.kotlinx.multik.ndarray.data.DataType +import space.kscience.kmath.operations.ShortRing + +public class MultikShortAlgebra( + multikEngine: Engine +) : MultikTensorAlgebra(multikEngine) { + override val elementAlgebra: ShortRing get() = ShortRing + override val type: DataType get() = DataType.ShortDataType + override fun scalar(value: Short): MultikTensor = Multik.ndarrayOf(value).wrap() +} + +//public val Short.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikShortAlgebra +//public val ShortRing.multikAlgebra: MultikTensorAlgebra get() = MultikShortAlgebra \ No newline at end of file diff --git a/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensor.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensor.kt new file mode 100644 index 000000000..59a9a1bf3 --- /dev/null +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensor.kt @@ -0,0 +1,43 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.ndarray.data.* +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.tensors.api.Tensor +import kotlin.jvm.JvmInline + +@JvmInline +public value class MultikTensor(public val array: MutableMultiArray) : Tensor { + override val shape: ShapeND get() = ShapeND(array.shape) + + @PerformancePitfall + override fun get(index: IntArray): T = array[index] + + @PerformancePitfall + override fun elements(): Sequence> = + array.multiIndices.iterator().asSequence().map { it to get(it) } + + @PerformancePitfall + override fun set(index: IntArray, value: T) { + array[index] = value + } +} + + +internal fun MultiArray.asD1Array(): D1Array { + if (this is NDArray) + return this.asD1Array() + else throw ClassCastException("Cannot cast MultiArray to NDArray.") +} + + +internal fun MultiArray.asD2Array(): D2Array { + if (this is NDArray) + return this.asD2Array() + else throw ClassCastException("Cannot cast MultiArray to NDArray.") +} \ No newline at end of file diff --git a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt similarity index 59% rename from kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt rename to kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt index 250ef7e7f..c3a82b167 100644 --- a/kmath-multik/src/main/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt +++ b/kmath-multik/src/commonMain/kotlin/space/kscience/kmath/multik/MultikTensorAlgebra.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,71 +10,44 @@ package space.kscience.kmath.multik import org.jetbrains.kotlinx.multik.api.* import org.jetbrains.kotlinx.multik.api.linalg.LinAlg import org.jetbrains.kotlinx.multik.api.math.Math +import org.jetbrains.kotlinx.multik.api.stat.Statistics import org.jetbrains.kotlinx.multik.ndarray.data.* import org.jetbrains.kotlinx.multik.ndarray.operations.* -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DefaultStrides -import space.kscience.kmath.nd.Shape -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.nd.mapInPlace -import space.kscience.kmath.operations.* +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.nd.* +import space.kscience.kmath.operations.Field +import space.kscience.kmath.operations.Ring import space.kscience.kmath.tensors.api.Tensor import space.kscience.kmath.tensors.api.TensorAlgebra import space.kscience.kmath.tensors.api.TensorPartialDivisionAlgebra -@JvmInline -public value class MultikTensor(public val array: MutableMultiArray) : Tensor { - override val shape: Shape get() = array.shape - - override fun get(index: IntArray): T = array[index] - - @PerformancePitfall - override fun elements(): Sequence> = - array.multiIndices.iterator().asSequence().map { it to get(it) } - - override fun set(index: IntArray, value: T) { - array[index] = value - } -} - -private fun MultiArray.asD1Array(): D1Array { - if (this is NDArray) - return this.asD1Array() - else throw ClassCastException("Cannot cast MultiArray to NDArray.") -} - - -private fun MultiArray.asD2Array(): D2Array { - if (this is NDArray) - return this.asD2Array() - else throw ClassCastException("Cannot cast MultiArray to NDArray.") -} - -public abstract class MultikTensorAlgebra> : TensorAlgebra - where T : Number, T : Comparable { +public abstract class MultikTensorAlgebra>( + private val multikEngine: Engine, +) : TensorAlgebra where T : Number, T : Comparable { public abstract val type: DataType - protected val multikMath: Math = mk.math - protected val multikLinAl: LinAlg = mk.linalg - protected val multikStat: Statistics = mk.stat - + protected val multikMath: Math = multikEngine.getMath() + protected val multikLinAl: LinAlg = multikEngine.getLinAlg() + protected val multikStat: Statistics = multikEngine.getStatistics() - override fun structureND(shape: Shape, initializer: A.(IntArray) -> T): MultikTensor { - val strides = DefaultStrides(shape) + @OptIn(UnsafeKMathAPI::class) + override fun structureND(shape: ShapeND, initializer: A.(IntArray) -> T): MultikTensor { + val strides = ColumnStrides(shape) val memoryView = initMemoryView(strides.linearSize, type) strides.asSequence().forEachIndexed { linearIndex, tensorIndex -> memoryView[linearIndex] = elementAlgebra.initializer(tensorIndex) } - return MultikTensor(NDArray(memoryView, shape = shape, dim = DN(shape.size))) + return MultikTensor(NDArray(memoryView, shape = shape.asArray(), dim = DN(shape.size))) } - @OptIn(PerformancePitfall::class) + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override fun StructureND.map(transform: A.(T) -> T): MultikTensor = if (this is MultikTensor) { val data = initMemoryView(array.size, type) var count = 0 for (el in array) data[count++] = elementAlgebra.transform(el) - NDArray(data, shape = shape, dim = array.dim).wrap() + NDArray(data, shape = shape.asArray(), dim = array.dim).wrap() } else { structureND(shape) { index -> transform(get(index)) @@ -102,6 +75,21 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra } } + /** + * Transform a structure element-by element in place. + */ + @OptIn(PerformancePitfall::class) + public inline fun MutableStructureND.mapIndexedInPlace(operation: (index: IntArray, t: T) -> T): Unit { + if (this is MultikTensor) { + array.multiIndices.iterator().forEach { + set(it, operation(it, get(it))) + } + } else { + indices.forEach { set(it, operation(it, get(it))) } + } + } + + @OptIn(PerformancePitfall::class) override fun zip(left: StructureND, right: StructureND, transform: A.(T, T) -> T): MultikTensor { require(left.shape.contentEquals(right.shape)) { "ND array shape mismatch" } //TODO replace by ShapeMismatchException @@ -122,10 +110,11 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra * Convert a tensor to [MultikTensor] if necessary. If tensor is converted, changes on the resulting tensor * are not reflected back onto the source */ + @OptIn(UnsafeKMathAPI::class, PerformancePitfall::class) public fun StructureND.asMultik(): MultikTensor = if (this is MultikTensor) { this } else { - val res = mk.zeros(shape, type).asDNArray() + val res = mk.zeros(shape.asArray(), type).asDNArray() for (index in res.multiIndices) { res[index] = this[index] } @@ -134,7 +123,8 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra public fun MutableMultiArray.wrap(): MultikTensor = MultikTensor(this.asDNArray()) - override fun StructureND.valueOrNull(): T? = if (shape contentEquals intArrayOf(1)) { + @OptIn(PerformancePitfall::class) + override fun StructureND.valueOrNull(): T? = if (shape contentEquals ShapeND(1)) { get(intArrayOf(0)) } else null @@ -151,15 +141,16 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra if (this is MultikTensor) { array.plusAssign(value) } else { - mapInPlace { _, t -> elementAlgebra.add(t, value) } + mapIndexedInPlace { _, t -> elementAlgebra.add(t, value) } } } + @OptIn(PerformancePitfall::class) override fun Tensor.plusAssign(arg: StructureND) { if (this is MultikTensor) { array.plusAssign(arg.asMultik().array) } else { - mapInPlace { index, t -> elementAlgebra.add(t, arg[index]) } + mapIndexedInPlace { index, t -> elementAlgebra.add(t, arg[index]) } } } @@ -175,15 +166,16 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra if (this is MultikTensor) { array.minusAssign(value) } else { - mapInPlace { _, t -> elementAlgebra.run { t - value } } + mapIndexedInPlace { _, t -> elementAlgebra.run { t - value } } } } + @OptIn(PerformancePitfall::class) override fun Tensor.minusAssign(arg: StructureND) { if (this is MultikTensor) { array.minusAssign(arg.asMultik().array) } else { - mapInPlace { index, t -> elementAlgebra.run { t - arg[index] } } + mapIndexedInPlace { index, t -> elementAlgebra.run { t - arg[index] } } } } @@ -200,30 +192,31 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra if (this is MultikTensor) { array.timesAssign(value) } else { - mapInPlace { _, t -> elementAlgebra.multiply(t, value) } + mapIndexedInPlace { _, t -> elementAlgebra.multiply(t, value) } } } + @OptIn(PerformancePitfall::class) override fun Tensor.timesAssign(arg: StructureND) { if (this is MultikTensor) { array.timesAssign(arg.asMultik().array) } else { - mapInPlace { index, t -> elementAlgebra.multiply(t, arg[index]) } + mapIndexedInPlace { index, t -> elementAlgebra.multiply(t, arg[index]) } } } override fun StructureND.unaryMinus(): MultikTensor = asMultik().array.unaryMinus().wrap() - override fun Tensor.get(i: Int): MultikTensor = asMultik().array.mutableView(i).wrap() + override fun Tensor.getTensor(i: Int): MultikTensor = asMultik().array.mutableView(i).wrap() - override fun Tensor.transpose(i: Int, j: Int): MultikTensor = asMultik().array.transpose(i, j).wrap() + override fun StructureND.transposed(i: Int, j: Int): MultikTensor = asMultik().array.transpose(i, j).wrap() - override fun Tensor.view(shape: IntArray): MultikTensor { - require(shape.all { it > 0 }) - require(shape.fold(1, Int::times) == this.shape.size) { + override fun Tensor.view(shape: ShapeND): MultikTensor { + require(shape.asList().all { it > 0 }) + require(shape.linearSize == this.shape.size) { "Cannot reshape array of size ${this.shape.size} into a new shape ${ - shape.joinToString( + shape.asList().joinToString( prefix = "(", postfix = ")" ) @@ -231,20 +224,25 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra } val mt = asMultik().array - return if (mt.shape.contentEquals(shape)) { + return if (ShapeND(mt.shape).contentEquals(shape)) { mt } else { - NDArray(mt.data, mt.offset, shape, dim = DN(shape.size), base = mt.base ?: mt) + @OptIn(UnsafeKMathAPI::class) + NDArray(mt.data, mt.offset, shape.asArray(), dim = DN(shape.size), base = mt.base ?: mt) }.wrap() } override fun Tensor.viewAs(other: StructureND): MultikTensor = view(other.shape) + public abstract fun scalar(value: T): MultikTensor + override fun StructureND.dot(other: StructureND): MultikTensor = if (this.shape.size == 1 && other.shape.size == 1) { - Multik.ndarrayOf( - multikLinAl.linAlgEx.dotVV(asMultik().array.asD1Array(), other.asMultik().array.asD1Array()) - ).wrap() + scalar( + multikLinAl.linAlgEx.dotVV( + asMultik().array.asD1Array(), other.asMultik().array.asD1Array() + ) + ) } else if (this.shape.size == 2 && other.shape.size == 2) { multikLinAl.linAlgEx.dotMM(asMultik().array.asD2Array(), other.asMultik().array.asD2Array()).wrap() } else if (this.shape.size == 2 && other.shape.size == 1) { @@ -253,42 +251,55 @@ public abstract class MultikTensorAlgebra> : TensorAlgebra TODO("Not implemented for broadcasting") } - override fun diagonalEmbedding(diagonalEntries: Tensor, offset: Int, dim1: Int, dim2: Int): MultikTensor { + override fun diagonalEmbedding(diagonalEntries: StructureND, offset: Int, dim1: Int, dim2: Int): MultikTensor { + TODO("Diagonal embedding not implemented") } - override fun StructureND.sum(): T = asMultik().array.reduceMultiIndexed { _: IntArray, acc: T, t: T -> - elementAlgebra.add(acc, t) - } + override fun StructureND.sum(): T = multikMath.sum(asMultik().array) override fun StructureND.sum(dim: Int, keepDim: Boolean): MultikTensor { - TODO("Not yet implemented") + if (keepDim) TODO("keepDim not implemented") + return multikMath.sumDN(asMultik().array, dim).wrap() } override fun StructureND.min(): T? = asMultik().array.min() override fun StructureND.min(dim: Int, keepDim: Boolean): Tensor { - TODO("Not yet implemented") + if (keepDim) TODO("keepDim not implemented") + return multikMath.minDN(asMultik().array, dim).wrap() + } + + override fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor { + if (keepDim) TODO("keepDim not implemented") + val res = multikMath.argMinDN(asMultik().array, dim) + return with(MultikIntAlgebra(multikEngine)) { res.wrap() } } override fun StructureND.max(): T? = asMultik().array.max() override fun StructureND.max(dim: Int, keepDim: Boolean): Tensor { - TODO("Not yet implemented") + if (keepDim) TODO("keepDim not implemented") + return multikMath.maxDN(asMultik().array, dim).wrap() } override fun StructureND.argMax(dim: Int, keepDim: Boolean): Tensor { - TODO("Not yet implemented") + if (keepDim) TODO("keepDim not implemented") + val res = multikMath.argMaxDN(asMultik().array, dim) + return with(MultikIntAlgebra(multikEngine)) { res.wrap() } } } -public abstract class MultikDivisionTensorAlgebra> - : MultikTensorAlgebra(), TensorPartialDivisionAlgebra where T : Number, T : Comparable { +public abstract class MultikDivisionTensorAlgebra>( + multikEngine: Engine, +) : MultikTensorAlgebra(multikEngine), TensorPartialDivisionAlgebra where T : Number, T : Comparable { - override fun T.div(arg: StructureND): MultikTensor = arg.map { elementAlgebra.divide(this@div, it) } + @OptIn(UnsafeKMathAPI::class) + override fun T.div(arg: StructureND): MultikTensor = + Multik.ones(arg.shape.asArray(), type).apply { divAssign(arg.asMultik().array) }.wrap() override fun StructureND.div(arg: T): MultikTensor = - asMultik().array.deepCopy().apply { divAssign(arg) }.wrap() + asMultik().array.div(arg).wrap() override fun StructureND.div(arg: StructureND): MultikTensor = asMultik().array.div(arg.asMultik().array).wrap() @@ -297,47 +308,16 @@ public abstract class MultikDivisionTensorAlgebra> if (this is MultikTensor) { array.divAssign(value) } else { - mapInPlace { _, t -> elementAlgebra.divide(t, value) } + mapIndexedInPlace { _, t -> elementAlgebra.divide(t, value) } } } + @OptIn(PerformancePitfall::class) override fun Tensor.divAssign(arg: StructureND) { if (this is MultikTensor) { array.divAssign(arg.asMultik().array) } else { - mapInPlace { index, t -> elementAlgebra.divide(t, arg[index]) } + mapIndexedInPlace { index, t -> elementAlgebra.divide(t, arg[index]) } } } -} - -public object MultikFloatAlgebra : MultikDivisionTensorAlgebra() { - override val elementAlgebra: FloatField get() = FloatField - override val type: DataType get() = DataType.FloatDataType -} - -public val Float.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikFloatAlgebra -public val FloatField.multikAlgebra: MultikTensorAlgebra get() = MultikFloatAlgebra - -public object MultikShortAlgebra : MultikTensorAlgebra() { - override val elementAlgebra: ShortRing get() = ShortRing - override val type: DataType get() = DataType.ShortDataType -} - -public val Short.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikShortAlgebra -public val ShortRing.multikAlgebra: MultikTensorAlgebra get() = MultikShortAlgebra - -public object MultikIntAlgebra : MultikTensorAlgebra() { - override val elementAlgebra: IntRing get() = IntRing - override val type: DataType get() = DataType.IntDataType -} - -public val Int.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikIntAlgebra -public val IntRing.multikAlgebra: MultikTensorAlgebra get() = MultikIntAlgebra - -public object MultikLongAlgebra : MultikTensorAlgebra() { - override val elementAlgebra: LongRing get() = LongRing - override val type: DataType get() = DataType.LongDataType -} - -public val Long.Companion.multikAlgebra: MultikTensorAlgebra get() = MultikLongAlgebra -public val LongRing.multikAlgebra: MultikTensorAlgebra get() = MultikLongAlgebra \ No newline at end of file +} \ No newline at end of file diff --git a/kmath-multik/src/commonTest/kotlin/space/kscience/kmath/multik/MultikNDTest.kt b/kmath-multik/src/commonTest/kotlin/space/kscience/kmath/multik/MultikNDTest.kt new file mode 100644 index 000000000..1a130aa92 --- /dev/null +++ b/kmath-multik/src/commonTest/kotlin/space/kscience/kmath/multik/MultikNDTest.kt @@ -0,0 +1,49 @@ +/* + * Copyright 2018-2022 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.multik + +import org.jetbrains.kotlinx.multik.default.DefaultEngine +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.nd.one +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra +import space.kscience.kmath.tensors.core.randomNormal +import space.kscience.kmath.tensors.core.tensorAlgebra +import kotlin.test.Test +import kotlin.test.assertTrue + +@OptIn(PerformancePitfall::class) +internal class MultikNDTest { + val multikAlgebra = MultikDoubleAlgebra(DefaultEngine()) + + @Test + fun basicAlgebra(): Unit = with(multikAlgebra) { + one(2, 2) + 1.0 + } + + @Test + fun dotResult() { + val dim = 100 + + val tensor1 = DoubleTensorAlgebra.randomNormal(shape = ShapeND(dim, dim), 12224) + val tensor2 = DoubleTensorAlgebra.randomNormal(shape = ShapeND(dim, dim), 12225) + + val multikResult = with(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-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt b/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt deleted file mode 100644 index 72c43d8e6..000000000 --- a/kmath-multik/src/test/kotlin/space/kscience/kmath/multik/MultikNDTest.kt +++ /dev/null @@ -1,43 +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.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-nd4j/README.md b/kmath-nd4j/README.md index bb065a300..b299c1b37 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-nd4j:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-nd4j:0.3.1-dev-1' + implementation 'space.kscience:kmath-nd4j:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -30,7 +30,7 @@ repositories { } dependencies { - implementation("space.kscience:kmath-nd4j:0.3.1-dev-1") + implementation("space.kscience:kmath-nd4j:0.4.0-dev-1") } ``` diff --git a/kmath-nd4j/build.gradle.kts b/kmath-nd4j/build.gradle.kts index 09264501f..e5c4af891 100644 --- a/kmath-nd4j/build.gradle.kts +++ b/kmath-nd4j/build.gradle.kts @@ -1,6 +1,5 @@ plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } description = "ND4J NDStructure implementation and according NDAlgebra classes" @@ -13,7 +12,7 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature(id = "nd4jarraystructure") { "NDStructure wrapper for INDArray" } feature(id = "nd4jarrayrings") { "Rings over Nd4jArrayStructure of Int and Long" } diff --git a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebra.kt b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebra.kt index e29a3f467..0eb147b6f 100644 --- a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebra.kt +++ b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebra.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -10,8 +10,9 @@ import org.nd4j.linalg.api.ops.impl.transforms.strict.ACosh import org.nd4j.linalg.api.ops.impl.transforms.strict.ASinh import org.nd4j.linalg.factory.Nd4j import org.nd4j.linalg.ops.transforms.Transforms -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.* import space.kscience.kmath.operations.* @@ -32,8 +33,10 @@ public sealed interface Nd4jArrayAlgebra> : AlgebraND.ndArray: INDArray - override fun structureND(shape: Shape, initializer: C.(IntArray) -> T): Nd4jArrayStructure { - val struct = Nd4j.create(*shape)!!.wrap() + @OptIn(PerformancePitfall::class) + override fun structureND(shape: ShapeND, initializer: C.(IntArray) -> T): Nd4jArrayStructure { + @OptIn(UnsafeKMathAPI::class) + val struct: Nd4jArrayStructure = Nd4j.create(*shape.asArray())!!.wrap() struct.indicesIterator().forEach { struct[it] = elementAlgebra.initializer(it) } return struct } @@ -45,21 +48,23 @@ public sealed interface Nd4jArrayAlgebra> : AlgebraND.mapIndexed( transform: C.(index: IntArray, T) -> T, ): Nd4jArrayStructure { - val new = Nd4j.create(*shape).wrap() + val new = Nd4j.create(*shape.asArray()).wrap() new.indicesIterator().forEach { idx -> new[idx] = elementAlgebra.transform(idx, this[idx]) } return new } + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override fun zip( left: StructureND, right: StructureND, transform: C.(T, T) -> T, ): Nd4jArrayStructure { require(left.shape.contentEquals(right.shape)) { "Can't zip tow structures of shape ${left.shape} and ${right.shape}" } - val new = Nd4j.create(*left.shape).wrap() + val new = Nd4j.create(*left.shape.asArray()).wrap() new.indicesIterator().forEach { idx -> new[idx] = elementAlgebra.transform(left[idx], right[idx]) } return new } @@ -190,11 +195,11 @@ public open class DoubleNd4jArrayFieldOps : Nd4jArrayExtendedFieldOps = asDoubleStructure() - @OptIn(PerformancePitfall::class) + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override val StructureND.ndArray: INDArray get() = when (this) { is Nd4jArrayStructure -> ndArray - else -> Nd4j.zeros(*shape).also { + else -> Nd4j.zeros(*shape.asArray()).also { elements().forEach { (idx, value) -> it.putScalar(idx, value) } } } @@ -220,10 +225,10 @@ public open class DoubleNd4jArrayFieldOps : Nd4jArrayExtendedFieldOps +public class DoubleNd4jArrayField(override val shape: ShapeND) : DoubleNd4jArrayFieldOps(), FieldND public fun DoubleField.nd4j(shapeFirst: Int, vararg shapeRest: Int): DoubleNd4jArrayField = - DoubleNd4jArrayField(intArrayOf(shapeFirst, * shapeRest)) + DoubleNd4jArrayField(ShapeND(shapeFirst, * shapeRest)) /** @@ -234,11 +239,11 @@ public open class FloatNd4jArrayFieldOps : Nd4jArrayExtendedFieldOps = asFloatStructure() - @OptIn(PerformancePitfall::class) + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override val StructureND.ndArray: INDArray get() = when (this) { is Nd4jArrayStructure -> ndArray - else -> Nd4j.zeros(*shape).also { + else -> Nd4j.zeros(*shape.asArray()).also { elements().forEach { (idx, value) -> it.putScalar(idx, value) } } } @@ -267,12 +272,12 @@ public open class FloatNd4jArrayFieldOps : Nd4jArrayExtendedFieldOps +public class FloatNd4jArrayField(override val shape: ShapeND) : FloatNd4jArrayFieldOps(), RingND public val FloatField.nd4j: FloatNd4jArrayFieldOps get() = FloatNd4jArrayFieldOps public fun FloatField.nd4j(shapeFirst: Int, vararg shapeRest: Int): FloatNd4jArrayField = - FloatNd4jArrayField(intArrayOf(shapeFirst, * shapeRest)) + FloatNd4jArrayField(ShapeND(shapeFirst, * shapeRest)) /** * Represents [RingND] over [Nd4jArrayIntStructure]. @@ -282,11 +287,11 @@ public open class IntNd4jArrayRingOps : Nd4jArrayRingOps { override fun INDArray.wrap(): Nd4jArrayStructure = asIntStructure() - @OptIn(PerformancePitfall::class) + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override val StructureND.ndArray: INDArray get() = when (this) { is Nd4jArrayStructure -> ndArray - else -> Nd4j.zeros(*shape).also { + else -> Nd4j.zeros(*shape.asArray()).also { elements().forEach { (idx, value) -> it.putScalar(idx, value) } } } @@ -308,7 +313,7 @@ public open class IntNd4jArrayRingOps : Nd4jArrayRingOps { public val IntRing.nd4j: IntNd4jArrayRingOps get() = IntNd4jArrayRingOps -public class IntNd4jArrayRing(override val shape: Shape) : IntNd4jArrayRingOps(), RingND +public class IntNd4jArrayRing(override val shape: ShapeND) : IntNd4jArrayRingOps(), RingND public fun IntRing.nd4j(shapeFirst: Int, vararg shapeRest: Int): IntNd4jArrayRing = - IntNd4jArrayRing(intArrayOf(shapeFirst, * shapeRest)) \ No newline at end of file + IntNd4jArrayRing(ShapeND(shapeFirst, * shapeRest)) \ No newline at end of file diff --git a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayIterator.kt b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayIterator.kt index d4cad8996..fedad26e0 100644 --- a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayIterator.kt +++ b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayIterator.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructure.kt b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructure.kt index 2a0fdc86c..93fbc8f85 100644 --- a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructure.kt +++ b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructure.kt @@ -1,14 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.nd4j import org.nd4j.linalg.api.ndarray.INDArray -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.MutableStructureND -import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.* /** * Represents a [StructureND] wrapping an [INDArray] object. @@ -22,7 +21,7 @@ public sealed class Nd4jArrayStructure : MutableStructureND { */ public abstract val ndArray: INDArray - override val shape: IntArray get() = ndArray.shape().toIntArray() + override val shape: ShapeND get() = ShapeND(ndArray.shape().toIntArray()) internal abstract fun elementsIterator(): Iterator> internal fun indicesIterator(): Iterator = ndArray.indicesIterator() @@ -31,20 +30,31 @@ public sealed class Nd4jArrayStructure : MutableStructureND { override fun elements(): Sequence> = Sequence(::elementsIterator) } -private data class Nd4jArrayIntStructure(override val ndArray: INDArray) : Nd4jArrayStructure() { +public data class Nd4jArrayIntStructure(override val ndArray: INDArray) : Nd4jArrayStructure(), StructureNDOfInt { override fun elementsIterator(): Iterator> = ndArray.intIterator() + + @OptIn(PerformancePitfall::class) override fun get(index: IntArray): Int = ndArray.getInt(*index) + + override fun getInt(index: IntArray): Int = ndArray.getInt(*index) + + @OptIn(PerformancePitfall::class) override fun set(index: IntArray, value: Int): Unit = run { ndArray.putScalar(index, value) } } /** * Wraps this [INDArray] to [Nd4jArrayStructure]. */ -public fun INDArray.asIntStructure(): Nd4jArrayStructure = Nd4jArrayIntStructure(this) +public fun INDArray.asIntStructure(): Nd4jArrayIntStructure = Nd4jArrayIntStructure(this) -private data class Nd4jArrayDoubleStructure(override val ndArray: INDArray) : Nd4jArrayStructure() { +public data class Nd4jArrayDoubleStructure(override val ndArray: INDArray) : Nd4jArrayStructure(), StructureNDOfDouble { override fun elementsIterator(): Iterator> = ndArray.realIterator() + @OptIn(PerformancePitfall::class) override fun get(index: IntArray): Double = ndArray.getDouble(*index) + + override fun getDouble(index: IntArray): Double = ndArray.getDouble(*index) + + @OptIn(PerformancePitfall::class) override fun set(index: IntArray, value: Double): Unit = run { ndArray.putScalar(index, value) } } @@ -53,9 +63,12 @@ private data class Nd4jArrayDoubleStructure(override val ndArray: INDArray) : Nd */ public fun INDArray.asDoubleStructure(): Nd4jArrayStructure = Nd4jArrayDoubleStructure(this) -private data class Nd4jArrayFloatStructure(override val ndArray: INDArray) : Nd4jArrayStructure() { +public data class Nd4jArrayFloatStructure(override val ndArray: INDArray) : Nd4jArrayStructure() { override fun elementsIterator(): Iterator> = ndArray.floatIterator() + @PerformancePitfall override fun get(index: IntArray): Float = ndArray.getFloat(*index) + + @PerformancePitfall override fun set(index: IntArray, value: Float): Unit = run { ndArray.putScalar(index, value) } } diff --git a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jTensorAlgebra.kt b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jTensorAlgebra.kt index ceb384f0d..5905739f8 100644 --- a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jTensorAlgebra.kt +++ b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/Nd4jTensorAlgebra.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -12,10 +12,9 @@ import org.nd4j.linalg.api.ops.impl.transforms.strict.ASinh import org.nd4j.linalg.factory.Nd4j import org.nd4j.linalg.factory.ops.NDBase import org.nd4j.linalg.ops.transforms.Transforms -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DefaultStrides -import space.kscience.kmath.nd.Shape -import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.Field import space.kscience.kmath.tensors.api.AnalyticTensorAlgebra @@ -38,14 +37,17 @@ public sealed interface Nd4jTensorAlgebra> : AnalyticTe */ public val StructureND.ndArray: INDArray - override fun structureND(shape: Shape, initializer: A.(IntArray) -> T): Nd4jArrayStructure + override fun structureND(shape: ShapeND, initializer: A.(IntArray) -> T): Nd4jArrayStructure + @OptIn(PerformancePitfall::class) override fun StructureND.map(transform: A.(T) -> T): Nd4jArrayStructure = structureND(shape) { index -> elementAlgebra.transform(get(index)) } + @OptIn(PerformancePitfall::class) override fun StructureND.mapIndexed(transform: A.(index: IntArray, T) -> T): Nd4jArrayStructure = structureND(shape) { index -> elementAlgebra.transform(index, get(index)) } + @OptIn(PerformancePitfall::class) override fun zip(left: StructureND, right: StructureND, transform: A.(T, T) -> T): Nd4jArrayStructure { require(left.shape.contentEquals(right.shape)) return structureND(left.shape) { index -> elementAlgebra.transform(left[index], right[index]) } @@ -92,8 +94,8 @@ public sealed interface Nd4jTensorAlgebra> : AnalyticTe } override fun StructureND.unaryMinus(): Nd4jArrayStructure = ndArray.neg().wrap() - override fun Tensor.get(i: Int): Nd4jArrayStructure = ndArray.slice(i.toLong()).wrap() - override fun Tensor.transpose(i: Int, j: Int): Nd4jArrayStructure = ndArray.swapAxes(i, j).wrap() + override fun Tensor.getTensor(i: Int): Nd4jArrayStructure = ndArray.slice(i.toLong()).wrap() + override fun StructureND.transposed(i: Int, j: Int): Nd4jArrayStructure = ndArray.swapAxes(i, j).wrap() override fun StructureND.dot(other: StructureND): Nd4jArrayStructure = ndArray.mmul(other.ndArray).wrap() override fun StructureND.min(dim: Int, keepDim: Boolean): Nd4jArrayStructure = @@ -105,40 +107,46 @@ public sealed interface Nd4jTensorAlgebra> : AnalyticTe override fun StructureND.max(dim: Int, keepDim: Boolean): Nd4jArrayStructure = ndArray.max(keepDim, dim).wrap() - override fun Tensor.view(shape: IntArray): Nd4jArrayStructure = ndArray.reshape(shape).wrap() + @OptIn(UnsafeKMathAPI::class) + override fun Tensor.view(shape: ShapeND): Nd4jArrayStructure = ndArray.reshape(shape.asArray()).wrap() + override fun Tensor.viewAs(other: StructureND): Nd4jArrayStructure = view(other.shape) + override fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor = + ndBase.get().argmin(ndArray, keepDim, dim).asIntStructure() + override fun StructureND.argMax(dim: Int, keepDim: Boolean): Tensor = ndBase.get().argmax(ndArray, keepDim, dim).asIntStructure() - override fun StructureND.mean(dim: Int, keepDim: Boolean): Nd4jArrayStructure = - ndArray.mean(keepDim, dim).wrap() + override fun mean(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + structureND.ndArray.mean(keepDim, dim).wrap() - override fun StructureND.exp(): Nd4jArrayStructure = Transforms.exp(ndArray).wrap() - override fun StructureND.ln(): Nd4jArrayStructure = Transforms.log(ndArray).wrap() - override fun StructureND.sqrt(): Nd4jArrayStructure = Transforms.sqrt(ndArray).wrap() - override fun StructureND.cos(): Nd4jArrayStructure = Transforms.cos(ndArray).wrap() - override fun StructureND.acos(): Nd4jArrayStructure = Transforms.acos(ndArray).wrap() - override fun StructureND.cosh(): Nd4jArrayStructure = Transforms.cosh(ndArray).wrap() + override fun exp(arg: StructureND): Nd4jArrayStructure = Transforms.exp(arg.ndArray).wrap() + override fun ln(arg: StructureND): Nd4jArrayStructure = Transforms.log(arg.ndArray).wrap() + override fun sqrt(arg: StructureND): Nd4jArrayStructure = Transforms.sqrt(arg.ndArray).wrap() + override fun cos(arg: StructureND): Nd4jArrayStructure = Transforms.cos(arg.ndArray).wrap() + override fun acos(arg: StructureND): Nd4jArrayStructure = Transforms.acos(arg.ndArray).wrap() + override fun cosh(arg: StructureND): Nd4jArrayStructure = Transforms.cosh(arg.ndArray).wrap() - override fun StructureND.acosh(): Nd4jArrayStructure = - Nd4j.getExecutioner().exec(ACosh(ndArray, ndArray.ulike())).wrap() + override fun acosh(arg: StructureND): Nd4jArrayStructure = + Nd4j.getExecutioner().exec(ACosh(arg.ndArray, arg.ndArray.ulike())).wrap() - override fun StructureND.sin(): Nd4jArrayStructure = Transforms.sin(ndArray).wrap() - override fun StructureND.asin(): Nd4jArrayStructure = Transforms.asin(ndArray).wrap() - override fun StructureND.sinh(): Tensor = Transforms.sinh(ndArray).wrap() + override fun sin(arg: StructureND): Nd4jArrayStructure = Transforms.sin(arg.ndArray).wrap() + override fun asin(arg: StructureND): Nd4jArrayStructure = Transforms.asin(arg.ndArray).wrap() + override fun sinh(arg: StructureND): Tensor = Transforms.sinh(arg.ndArray).wrap() - override fun StructureND.asinh(): Nd4jArrayStructure = - Nd4j.getExecutioner().exec(ASinh(ndArray, ndArray.ulike())).wrap() + override fun asinh(arg: StructureND): Nd4jArrayStructure = + Nd4j.getExecutioner().exec(ASinh(arg.ndArray, arg.ndArray.ulike())).wrap() - override fun StructureND.tan(): Nd4jArrayStructure = Transforms.tan(ndArray).wrap() - override fun StructureND.atan(): Nd4jArrayStructure = Transforms.atan(ndArray).wrap() - override fun StructureND.tanh(): Nd4jArrayStructure = Transforms.tanh(ndArray).wrap() - override fun StructureND.atanh(): Nd4jArrayStructure = Transforms.atanh(ndArray).wrap() - override fun StructureND.ceil(): Nd4jArrayStructure = Transforms.ceil(ndArray).wrap() - override fun StructureND.floor(): Nd4jArrayStructure = Transforms.floor(ndArray).wrap() - override fun StructureND.std(dim: Int, keepDim: Boolean): Nd4jArrayStructure = - ndArray.std(true, keepDim, dim).wrap() + override fun tan(arg: StructureND): Nd4jArrayStructure = Transforms.tan(arg.ndArray).wrap() + override fun atan(arg: StructureND): Nd4jArrayStructure = Transforms.atan(arg.ndArray).wrap() + override fun tanh(arg: StructureND): Nd4jArrayStructure = Transforms.tanh(arg.ndArray).wrap() + override fun atanh(arg: StructureND): Nd4jArrayStructure = Transforms.atanh(arg.ndArray).wrap() + override fun power(arg: StructureND, pow: Number): StructureND = Transforms.pow(arg.ndArray, pow).wrap() + override fun ceil(arg: StructureND): Nd4jArrayStructure = Transforms.ceil(arg.ndArray).wrap() + override fun floor(structureND: StructureND): Nd4jArrayStructure = Transforms.floor(structureND.ndArray).wrap() + override fun std(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + structureND.ndArray.std(true, keepDim, dim).wrap() override fun T.div(arg: StructureND): Nd4jArrayStructure = arg.ndArray.rdiv(this).wrap() override fun StructureND.div(arg: T): Nd4jArrayStructure = ndArray.div(arg).wrap() @@ -152,8 +160,8 @@ public sealed interface Nd4jTensorAlgebra> : AnalyticTe ndArray.divi(arg.ndArray) } - override fun StructureND.variance(dim: Int, keepDim: Boolean): Nd4jArrayStructure = - Nd4j.getExecutioner().exec(Variance(ndArray, true, true, dim)).wrap() + override fun variance(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + Nd4j.getExecutioner().exec(Variance(structureND.ndArray, true, true, dim)).wrap() private companion object { private val ndBase: ThreadLocal = ThreadLocal.withInitial(::NDBase) @@ -169,9 +177,10 @@ public object DoubleNd4jTensorAlgebra : Nd4jTensorAlgebra { override fun INDArray.wrap(): Nd4jArrayStructure = asDoubleStructure() - override fun structureND(shape: Shape, initializer: DoubleField.(IntArray) -> Double): Nd4jArrayStructure { - val array: INDArray = Nd4j.zeros(*shape) - val indices = DefaultStrides(shape) + @OptIn(UnsafeKMathAPI::class) + override fun structureND(shape: ShapeND, initializer: DoubleField.(IntArray) -> Double): Nd4jArrayStructure { + val array: INDArray = Nd4j.zeros(*shape.asArray()) + val indices = ColumnStrides(shape) indices.asSequence().forEach { index -> array.putScalar(index, elementAlgebra.initializer(index)) } @@ -179,21 +188,21 @@ public object DoubleNd4jTensorAlgebra : Nd4jTensorAlgebra { } - @OptIn(PerformancePitfall::class) + @OptIn(PerformancePitfall::class, UnsafeKMathAPI::class) override val StructureND.ndArray: INDArray get() = when (this) { is Nd4jArrayStructure -> ndArray - else -> Nd4j.zeros(*shape).also { + else -> Nd4j.zeros(*shape.asArray()).also { elements().forEach { (idx, value) -> it.putScalar(idx, value) } } } override fun StructureND.valueOrNull(): Double? = - if (shape contentEquals intArrayOf(1)) ndArray.getDouble(0) else null + if (shape contentEquals ShapeND(1)) ndArray.getDouble(0) else null // TODO rewrite override fun diagonalEmbedding( - diagonalEntries: Tensor, + diagonalEntries: StructureND, offset: Int, dim1: Int, dim2: Int, @@ -202,7 +211,7 @@ public object DoubleNd4jTensorAlgebra : Nd4jTensorAlgebra { override fun StructureND.sum(): Double = ndArray.sumNumber().toDouble() override fun StructureND.min(): Double = ndArray.minNumber().toDouble() override fun StructureND.max(): Double = ndArray.maxNumber().toDouble() - override fun StructureND.mean(): Double = ndArray.meanNumber().toDouble() - override fun StructureND.std(): Double = ndArray.stdNumber().toDouble() - override fun StructureND.variance(): Double = ndArray.varNumber().toDouble() + override fun mean(structureND: StructureND): Double = structureND.ndArray.meanNumber().toDouble() + override fun std(structureND: StructureND): Double = structureND.ndArray.stdNumber().toDouble() + override fun variance(structureND: StructureND): Double = structureND.ndArray.varNumber().toDouble() } diff --git a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/arrays.kt b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/arrays.kt index 3ca756600..401c57a7b 100644 --- a/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/arrays.kt +++ b/kmath-nd4j/src/main/kotlin/space/kscience/kmath/nd4j/arrays.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebraTest.kt b/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebraTest.kt index 9d30c2027..708778e77 100644 --- a/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebraTest.kt +++ b/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayAlgebraTest.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.nd4j import org.nd4j.linalg.factory.Nd4j -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.nd.StructureND import space.kscience.kmath.nd.one import space.kscience.kmath.nd.structureND diff --git a/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructureTest.kt b/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructureTest.kt index 30d01338f..d57eb2e2d 100644 --- a/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructureTest.kt +++ b/kmath-nd4j/src/test/kotlin/space/kscience/kmath/nd4j/Nd4jArrayStructureTest.kt @@ -1,12 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.nd4j import org.nd4j.linalg.factory.Nd4j -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.asList import space.kscience.kmath.nd.get import kotlin.test.Test import kotlin.test.assertEquals @@ -27,7 +28,7 @@ internal class Nd4jArrayStructureTest { fun testShape() { val nd = Nd4j.rand(10, 2, 3, 6) ?: fail() val struct = nd.asDoubleStructure() - assertEquals(intArrayOf(10, 2, 3, 6).toList(), struct.shape.toList()) + assertEquals(intArrayOf(10, 2, 3, 6).toList(), struct.shape.asList()) } @Test diff --git a/kmath-optimization/README.md b/kmath-optimization/README.md index d7441ebd1..79a4f5d24 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-optimization:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-optimization:0.3.1-dev-1' + implementation 'space.kscience:kmath-optimization:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-optimization:0.3.1-dev-1") + implementation("space.kscience:kmath-optimization:0.4.0-dev-1") } ``` diff --git a/kmath-optimization/build.gradle.kts b/kmath-optimization/build.gradle.kts index 2e5bf6005..7250d1f72 100644 --- a/kmath-optimization/build.gradle.kts +++ b/kmath-optimization/build.gradle.kts @@ -1,21 +1,23 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") +} + +kscience{ + jvm() + js() + native() } kotlin.sourceSets { - all { - languageSettings.optIn("space.kscience.kmath.misc.UnstableKMathAPI") - } commonMain { dependencies { api(project(":kmath-coroutines")) - api(npmlibs.atomicfu) + api(spclibs.atomicfu) } } } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/FunctionOptimization.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/FunctionOptimization.kt index 02602b068..07146625c 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/FunctionOptimization.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/FunctionOptimization.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationBuilder.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationBuilder.kt index 416d0195d..0459d46ee 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationBuilder.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationBuilder.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.optimization +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.expressions.DifferentiableExpression import space.kscience.kmath.expressions.Symbol @@ -69,6 +70,7 @@ public suspend fun DifferentiableExpression.optimizeWith( } +@OptIn(UnstableKMathAPI::class) public class XYOptimizationBuilder( public val data: XYColumnarData, public val model: DifferentiableExpression, @@ -86,6 +88,7 @@ public class XYOptimizationBuilder( ) } +@OptIn(UnstableKMathAPI::class) public fun XYOptimization( data: XYColumnarData, model: DifferentiableExpression, diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationProblem.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationProblem.kt index b42be4035..9fdcfc53d 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationProblem.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/OptimizationProblem.kt @@ -1,13 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.optimization import space.kscience.kmath.expressions.DifferentiableExpression +import space.kscience.kmath.expressions.NamedMatrix import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.linear.Matrix import space.kscience.kmath.misc.* import kotlin.reflect.KClass @@ -32,7 +32,10 @@ public interface OptimizationPrior : OptimizationFeature, DifferentiableExpre override val key: FeatureKey get() = OptimizationPrior::class } -public class OptimizationCovariance(public val covariance: Matrix) : OptimizationFeature { +/** + * Covariance matrix for + */ +public class OptimizationCovariance(public val covariance: NamedMatrix) : OptimizationFeature { override fun toString(): String = "Covariance($covariance)" } @@ -57,10 +60,20 @@ public class OptimizationLog(private val loggable: Loggable) : Loggable by logga override fun toString(): String = "Log($loggable)" } +/** + * Free parameters of the optimization + */ public class OptimizationParameters(public val symbols: List) : OptimizationFeature { public constructor(vararg symbols: Symbol) : this(listOf(*symbols)) override fun toString(): String = "Parameters($symbols)" } +/** + * Maximum allowed number of iterations + */ +public class OptimizationIterations(public val maxIterations: Int) : OptimizationFeature { + override fun toString(): String = "Iterations($maxIterations)" +} + diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/Optimizer.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/Optimizer.kt index 78385a99b..41dcbf770 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/Optimizer.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/Optimizer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/QowOptimizer.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/QowOptimizer.kt index babbaf6cd..b698584aa 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/QowOptimizer.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/QowOptimizer.kt @@ -1,21 +1,19 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.optimization -import space.kscience.kmath.expressions.DifferentiableExpression -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.expressions.SymbolIndexer -import space.kscience.kmath.expressions.derivative +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.expressions.* import space.kscience.kmath.linear.* -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.misc.log import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.DoubleL2Norm import space.kscience.kmath.operations.algebra import space.kscience.kmath.structures.DoubleBuffer +import kotlin.math.abs public class QowRuns(public val runs: Int) : OptimizationFeature { @@ -40,18 +38,24 @@ public object QowOptimizer : Optimizer { @OptIn(UnstableKMathAPI::class) private class QoWeight( val problem: XYFit, - val parameters: Map, - ) : Map by parameters, SymbolIndexer { - override val symbols: List = parameters.keys.toList() + val freeParameters: Map, + ) : SymbolIndexer { + val size get() = freeParameters.size + + override val symbols: List = freeParameters.keys.toList() val data get() = problem.data + val allParameters by lazy { + problem.startPoint + freeParameters + } + /** * Derivatives of the spectrum over parameters. First index in the point number, second one - index of parameter */ val derivs: Matrix by lazy { linearSpace.buildMatrix(problem.data.size, symbols.size) { d, s -> - problem.distance(d).derivative(symbols[s])(parameters) + problem.distance(d).derivative(symbols[s]).invoke(allParameters) } } @@ -60,29 +64,31 @@ public object QowOptimizer : Optimizer { */ val dispersion: Point by lazy { DoubleBuffer(problem.data.size) { d -> - 1.0/problem.weight(d).invoke(parameters) + 1.0 / problem.weight(d).invoke(allParameters) } } - val prior: DifferentiableExpression? get() = problem.getFeature>() + val prior: DifferentiableExpression? + get() = problem.getFeature>()?.withDefaultArgs(allParameters) - override fun toString(): String = parameters.toString() + override fun toString(): String = freeParameters.toString() } /** * The signed distance from the model to the [d]-th point of data. */ - private fun QoWeight.distance(d: Int, parameters: Map): Double = problem.distance(d)(parameters) + private fun QoWeight.distance(d: Int, parameters: Map): Double = + problem.distance(d)(allParameters + parameters) /** * The derivative of [distance] */ private fun QoWeight.distanceDerivative(symbol: Symbol, d: Int, parameters: Map): Double = - problem.distance(d).derivative(symbol)(parameters) + problem.distance(d).derivative(symbol).invoke(allParameters + parameters) /** - * Теоретическая ковариация весовых функций. + * Theoretical covariance of weight functions * * D(\phi)=E(\phi_k(\theta_0) \phi_l(\theta_0))= disDeriv_k * disDeriv_l /sigma^2 */ @@ -92,7 +98,7 @@ public object QowOptimizer : Optimizer { } /** - * Экспериментальная ковариация весов. Формула (22) из + * Experimental covariance Eq (22) from * http://arxiv.org/abs/physics/0604127 */ private fun QoWeight.covarFExp(theta: Map): Matrix = @@ -115,10 +121,9 @@ public object QowOptimizer : Optimizer { * Equation derivatives for Newton run */ private fun QoWeight.getEqDerivValues( - theta: Map = parameters, + theta: Map = freeParameters, ): Matrix = with(linearSpace) { - //Возвращает производную k-того Eq по l-тому параметру - //val res = Array(fitDim) { DoubleArray(fitDim) } + //Derivative of k Eq over l parameter val sderiv = buildMatrix(data.size, size) { d, s -> distanceDerivative(symbols[s], d, theta) } @@ -140,16 +145,15 @@ public object QowOptimizer : Optimizer { /** - * Значения уравнений метода квазиоптимальных весов + * Quasi optimal weights equations values */ - private fun QoWeight.getEqValues(theta: Map = this): Point { + private fun QoWeight.getEqValues(theta: Map): Point { val distances = DoubleBuffer(data.size) { d -> distance(d, theta) } - return DoubleBuffer(size) { s -> val base = (0 until data.size).sumOf { d -> distances[d] * derivs[d, s] / dispersion[d] } - //Поправка на априорную вероятность + //Prior probability correction prior?.let { prior -> - base - prior.derivative(symbols[s])(theta) / prior(theta) + base - prior.derivative(symbols[s]).invoke(theta) / prior(theta) } ?: base } } @@ -157,15 +161,13 @@ public object QowOptimizer : Optimizer { private fun QoWeight.newtonianStep( theta: Map, - eqvalues: Point, + eqValues: Point, ): QoWeight = linearSpace { - with(this@newtonianStep) { - val start = theta.toPoint() - val invJacob = solver.inverse(this@newtonianStep.getEqDerivValues(theta)) + val start = theta.toPoint() + val invJacob = solver.inverse(getEqDerivValues(theta)) - val step = invJacob.dot(eqvalues) - return QoWeight(problem, theta + (start - step).toMap()) - } + val step = invJacob.dot(eqValues) + return QoWeight(problem, theta + (start - step).toMap()) } private fun QoWeight.newtonianRun( @@ -177,10 +179,10 @@ public object QowOptimizer : Optimizer { val logger = problem.getFeature() var dis: Double //discrepancy value - // Working with the full set of parameters - var par = problem.startPoint - logger?.log { "Starting newtonian iteration from: \n\t$par" } + var par = freeParameters + + logger?.log { "Starting newtonian iteration from: \n\t$allParameters" } var eqvalues = getEqValues(par) //Values of the weight functions @@ -193,48 +195,48 @@ public object QowOptimizer : Optimizer { logger?.log { "Starting step number $i" } val currentSolution = if (fast) { - //Берет значения матрицы в той точке, где считается вес - newtonianStep(this, eqvalues) + //Matrix values in the point of weight computation + newtonianStep(freeParameters, eqvalues) } else { - //Берет значения матрицы в точке par + //Matrix values in a current point newtonianStep(par, eqvalues) } // здесь должен стоять учет границ параметров logger?.log { "Parameter values after step are: \n\t$currentSolution" } - eqvalues = getEqValues(currentSolution) - val currentDis = DoubleL2Norm.norm(eqvalues)// невязка после шага + eqvalues = getEqValues(currentSolution.freeParameters) + val currentDis = DoubleL2Norm.norm(eqvalues)// discrepancy after the step logger?.log { "The discrepancy after step is: $currentDis." } if (currentDis >= dis && i > 1) { - //дополнительно проверяем, чтобы был сделан хотя бы один шаг + //Check if one step is made flag = true logger?.log { "The discrepancy does not decrease. Stopping iteration." } + } else if (abs(dis - currentDis) <= tolerance) { + flag = true + par = currentSolution.freeParameters + logger?.log { "Relative discrepancy tolerance threshold is reached. Stopping iteration." } } else { - par = currentSolution + par = currentSolution.freeParameters dis = currentDis } if (i >= maxSteps) { flag = true logger?.log { "Maximum number of iterations reached. Stopping iteration." } } - if (dis <= tolerance) { - flag = true - logger?.log { "Tolerance threshold is reached. Stopping iteration." } - } } return QoWeight(problem, par) } - private fun QoWeight.covariance(): Matrix { + private fun QoWeight.covariance(): NamedMatrix { val logger = problem.getFeature() logger?.log { """ - Starting errors estimation using quasioptimal weights method. The starting weight is: - ${problem.startPoint} + Starting errors estimation using quasi-optimal weights method. The starting weight is: + $allParameters """.trimIndent() } @@ -248,19 +250,27 @@ public object QowOptimizer : Optimizer { // valid = false // } // } - return covar + logger?.log { + "Covariance matrix:" + "\n" + NamedMatrix.toStringWithSymbols(covar, this) + } + return covar.named(symbols) } override suspend fun optimize(problem: XYFit): XYFit { val qowRuns = problem.getFeature()?.runs ?: 2 + val iterations = problem.getFeature()?.maxIterations ?: 50 + val freeParameters: Map = problem.getFeature()?.let { op -> + problem.startPoint.filterKeys { it in op.symbols } + } ?: problem.startPoint - var qow = QoWeight(problem, problem.startPoint) - var res = qow.newtonianRun() + var qow = QoWeight(problem, freeParameters) + var res = qow.newtonianRun(maxSteps = iterations) repeat(qowRuns - 1) { - qow = QoWeight(problem, res.parameters) - res = qow.newtonianRun() + qow = QoWeight(problem, res.freeParameters) + res = qow.newtonianRun(maxSteps = iterations) } - return res.problem.withFeature(OptimizationResult(res.parameters)) + val covariance = res.covariance() + return res.problem.withFeature(OptimizationResult(res.freeParameters), OptimizationCovariance(covariance)) } } \ No newline at end of file diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/XYFit.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/XYFit.kt index 07fea3126..9e5396491 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/XYFit.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/XYFit.kt @@ -1,17 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.optimization +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.data.indices import space.kscience.kmath.expressions.* import space.kscience.kmath.misc.FeatureSet import space.kscience.kmath.misc.Loggable -import space.kscience.kmath.misc.UnstableKMathAPI import space.kscience.kmath.operations.ExtendedField import space.kscience.kmath.operations.bindSymbol import kotlin.math.pow @@ -30,7 +30,7 @@ public interface PointToCurveDistance : OptimizationFeature { return object : DifferentiableExpression { override fun derivativeOrNull( - symbols: List + symbols: List, ): Expression? = problem.model.derivativeOrNull(symbols)?.let { derivExpression -> Expression { arguments -> derivExpression.invoke(arguments + (Symbol.x to x)) @@ -93,24 +93,15 @@ public fun XYFit.withFeature(vararg features: OptimizationFeature): XYFit { return XYFit(data, model, this.features.with(*features), pointToCurveDistance, pointWeight) } -/** - * Fit given dta with - */ -public suspend fun XYColumnarData.fitWith( +public suspend fun XYColumnarData.fitWith( optimizer: Optimizer, - processor: AutoDiffProcessor, + modelExpression: DifferentiableExpression, startingPoint: Map, vararg features: OptimizationFeature = emptyArray(), xSymbol: Symbol = Symbol.x, pointToCurveDistance: PointToCurveDistance = PointToCurveDistance.byY, pointWeight: PointWeight = PointWeight.byYSigma, - model: A.(I) -> I -): XYFit where A : ExtendedField, A : ExpressionAlgebra { - val modelExpression = processor.differentiate { - val x = bindSymbol(xSymbol) - model(x) - } - +): XYFit { var actualFeatures = FeatureSet.of(*features, OptimizationStartPoint(startingPoint)) if (actualFeatures.getFeature() == null) { @@ -127,20 +118,53 @@ public suspend fun XYColumnarData.fitWith( return optimizer.optimize(problem) } +/** + * Fit given data with a model provided as an expression + */ +public suspend fun XYColumnarData.fitWith( + optimizer: Optimizer, + processor: AutoDiffProcessor, + startingPoint: Map, + vararg features: OptimizationFeature = emptyArray(), + xSymbol: Symbol = Symbol.x, + pointToCurveDistance: PointToCurveDistance = PointToCurveDistance.byY, + pointWeight: PointWeight = PointWeight.byYSigma, + model: A.(I) -> I, +): XYFit where A : ExtendedField, A : ExpressionAlgebra { + val modelExpression: DifferentiableExpression = processor.differentiate { + val x = bindSymbol(xSymbol) + model(x) + } + + return fitWith( + optimizer = optimizer, + modelExpression = modelExpression, + startingPoint = startingPoint, + features = features, + xSymbol = xSymbol, + pointToCurveDistance = pointToCurveDistance, + pointWeight = pointWeight + ) +} + /** * Compute chi squared value for completed fit. Return null for incomplete fit */ -public val XYFit.chiSquaredOrNull: Double? get() { - val result = resultPointOrNull ?: return null +public val XYFit.chiSquaredOrNull: Double? + get() { + val result = startPoint + (resultPointOrNull ?: return null) - return data.indices.sumOf { index-> + return data.indices.sumOf { index -> - val x = data.x[index] - val y = data.y[index] - val yErr = data[Symbol.yError]?.get(index) ?: 1.0 + val x = data.x[index] + val y = data.y[index] + val yErr = data[Symbol.yError]?.get(index) ?: 1.0 - val mu = model.invoke(result + (xSymbol to x) ) + val mu = model.invoke(result + (xSymbol to x)) - ((y - mu)/yErr).pow(2) + ((y - mu) / yErr).pow(2) + } } -} \ No newline at end of file + +public val XYFit.dof: Int + get() = data.size - (getFeature()?.symbols?.size ?: startPoint.size) \ No newline at end of file diff --git a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/logLikelihood.kt b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/logLikelihood.kt index b4cb2f1cf..8ab9de48d 100644 --- a/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/logLikelihood.kt +++ b/kmath-optimization/src/commonMain/kotlin/space/kscience/kmath/optimization/logLikelihood.kt @@ -1,17 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.optimization +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.data.XYColumnarData import space.kscience.kmath.data.indices import space.kscience.kmath.expressions.DifferentiableExpression import space.kscience.kmath.expressions.Expression import space.kscience.kmath.expressions.Symbol import space.kscience.kmath.expressions.derivative -import space.kscience.kmath.misc.UnstableKMathAPI import kotlin.math.PI import kotlin.math.ln import kotlin.math.pow diff --git a/kmath-optimization/src/commonMain/tmp/minuit/HessianGradientCalculator.kt b/kmath-optimization/src/commonMain/tmp/minuit/HessianGradientCalculator.kt index 150d192f9..4ef743955 100644 --- a/kmath-optimization/src/commonMain/tmp/minuit/HessianGradientCalculator.kt +++ b/kmath-optimization/src/commonMain/tmp/minuit/HessianGradientCalculator.kt @@ -33,7 +33,7 @@ internal class HessianGradientCalculator(fcn: MnFcn, par: MnUserTransformation, val g2: RealVector = gradient.getGradientDerivative() val gstep: RealVector = gradient.getStep() val fcnmin: Double = par.fval() - // std::cout<<"fval: "< prec.eps()) { return e } - // std::cout<<"MnPosDef init matrix= "< -@PublishedApi -internal constructor( - /** - * Map that contains coefficients of the polynomial. - * - * Every monomial \(a x_1^{d_1} ... x_n^{d_n}\) is stored as a pair "key-value" in the map, where the value is the - * coefficient \(a\) and the key is a map that associates variables in the monomial with their degree in the monomial. - * For example, coefficients of a polynomial \(5 a^2 c^3 - 6 b\) can be represented as - * ``` - * mapOf( - * mapOf( - * a to 2, - * c to 3 - * ) to 5, - * mapOf( - * b to 1 - * ) to (-6) - * ) - * ``` - * and also as - * ``` - * mapOf( - * mapOf( - * a to 2, - * c to 3 - * ) to 5, - * mapOf( - * b to 1 - * ) to (-6), - * mapOf( - * b to 1, - * c to 1 - * ) to 0 - * ) - * ``` - * where \(a\), \(b\) and \(c\) are corresponding [Symbol] objects. - * - * It is not prohibited to put extra zero monomials into the map (as for \(0 b c\) in the example). But the - * bigger the coefficients map the worse performance of arithmetical operations performed on it. Thus, it is - * recommended not to put (or even to remove) extra (or useless) monomials in the coefficients map. - * @usesMathJax - */ - public val coefficients: Map, C> -) { - override fun toString(): String = "LabeledPolynomial$coefficients" -} - -/** - * Arithmetic context for multivariate polynomials with coefficients stored as a [Map] and terms' signatures stored as a - * [Map] constructed with the provided [ring] of constants. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class LabeledPolynomialSpace>( - public override val ring: A, -) : MultivariatePolynomialSpace>, PolynomialSpaceOverRing, A> { - /** - * Returns sum of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - public override operator fun Symbol.plus(other: Int): LabeledPolynomial = - if (other == 0) LabeledPolynomialAsIs( - mapOf(this@plus to 1U) to constantOne, - ) - else LabeledPolynomialAsIs( - mapOf(this@plus to 1U) to constantOne, - emptyMap() to other.asConstant(), - ) - /** - * Returns difference between the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - public override operator fun Symbol.minus(other: Int): LabeledPolynomial = - if (other == 0) LabeledPolynomialAsIs( - mapOf(this@minus to 1U) to constantOne, - ) - else LabeledPolynomialAsIs( - mapOf(this@minus to 1U) to constantOne, - emptyMap() to (-other).asConstant(), - ) - /** - * Returns product of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - public override operator fun Symbol.times(other: Int): LabeledPolynomial = - if (other == 0) zero - else LabeledPolynomialAsIs( - mapOf(this to 1U) to other.asConstant(), - ) - - /** - * Returns sum of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun Int.plus(other: Symbol): LabeledPolynomial = - if (this == 0) LabeledPolynomialAsIs( - mapOf(other to 1U) to constantOne, - ) - else LabeledPolynomialAsIs( - mapOf(other to 1U) to constantOne, - emptyMap() to this@plus.asConstant(), - ) - /** - * Returns difference between the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun Int.minus(other: Symbol): LabeledPolynomial = - if (this == 0) LabeledPolynomialAsIs( - mapOf(other to 1U) to -constantOne, - ) - else LabeledPolynomialAsIs( - mapOf(other to 1U) to -constantOne, - emptyMap() to constantOne * this@minus, - ) - /** - * Returns product of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun Int.times(other: Symbol): LabeledPolynomial = - if (this == 0) zero - else LabeledPolynomialAsIs( - mapOf(other to 1U) to this@times.asConstant(), - ) - - /** - * Returns sum of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public override operator fun LabeledPolynomial.plus(other: Int): LabeledPolynomial = - when { - other == 0 -> this - coefficients.isEmpty() -> other.asPolynomial() - else -> LabeledPolynomialAsIs( - coefficients.withPutOrChanged(emptyMap(), other.asConstant()) { it -> it + other } - ) - } - /** - * Returns difference between the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public override operator fun LabeledPolynomial.minus(other: Int): LabeledPolynomial = - when { - other == 0 -> this - coefficients.isEmpty() -> other.asPolynomial() - else -> LabeledPolynomialAsIs( - coefficients.withPutOrChanged(emptyMap(), (-other).asConstant()) { it -> it - other } - ) - } - /** - * Returns product of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public override operator fun LabeledPolynomial.times(other: Int): LabeledPolynomial = - when(other) { - 0 -> zero - 1 -> this - else -> LabeledPolynomialAsIs( - coefficients.mapValues { (_, value) -> value * other } - ) - } - - /** - * Returns sum of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public override operator fun Int.plus(other: LabeledPolynomial): LabeledPolynomial = - when { - this == 0 -> other - other.coefficients.isEmpty() -> this@plus.asPolynomial() - else -> LabeledPolynomialAsIs( - other.coefficients.withPutOrChanged(emptyMap(), this@plus.asConstant()) { it -> this@plus + it } - ) - } - /** - * Returns difference between the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public override operator fun Int.minus(other: LabeledPolynomial): LabeledPolynomial = - when { - this == 0 -> -other - other.coefficients.isEmpty() -> this@minus.asPolynomial() - else -> LabeledPolynomialAsIs( - buildMap(other.coefficients.size + 1) { - put(emptyMap(), asConstant()) - other.coefficients.copyMapToBy(this, { _, c -> -c }, { currentC, newC -> currentC - newC }) - } - ) - } - /** - * Returns product of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public override operator fun Int.times(other: LabeledPolynomial): LabeledPolynomial = - when(this) { - 0 -> zero - 1 -> other - else -> LabeledPolynomialAsIs( - other.coefficients.mapValues { (_, value) -> this@times * value } - ) - } - - /** - * Returns sum of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - public override operator fun Symbol.plus(other: C): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(this@plus to 1U) to constantOne, - emptyMap() to other, - ) - /** - * Returns difference between the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - public override operator fun Symbol.minus(other: C): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(this@minus to 1U) to constantOne, - emptyMap() to -other, - ) - /** - * Returns product of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - public override operator fun Symbol.times(other: C): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(this@times to 1U) to other, - ) - - /** - * Returns sum of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun C.plus(other: Symbol): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(other to 1U) to constantOne, - emptyMap() to this@plus, - ) - /** - * Returns difference between the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun C.minus(other: Symbol): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(other to 1U) to -constantOne, - emptyMap() to this@minus, - ) - /** - * Returns product of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - public override operator fun C.times(other: Symbol): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(other to 1U) to this@times, - ) - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - override operator fun C.plus(other: LabeledPolynomial): LabeledPolynomial = - if (other.coefficients.isEmpty()) this@plus.asLabeledPolynomial() - else LabeledPolynomialAsIs( - other.coefficients.withPutOrChanged(emptyMap(), this@plus) { it -> this@plus + it } - ) - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - override operator fun C.minus(other: LabeledPolynomial): LabeledPolynomial = - if (other.coefficients.isEmpty()) this@minus.asPolynomial() - else LabeledPolynomialAsIs( - buildMap(other.coefficients.size + 1) { - put(emptyMap(), this@minus) - other.coefficients.copyMapToBy(this, { _, c -> -c }, { currentC, newC -> currentC - newC }) - } - ) - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - override operator fun C.times(other: LabeledPolynomial): LabeledPolynomial = - LabeledPolynomialAsIs( - other.coefficients.mapValues { this@times * it.value } - ) - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - override operator fun LabeledPolynomial.plus(other: C): LabeledPolynomial = - if (coefficients.isEmpty()) other.asLabeledPolynomial() - else LabeledPolynomialAsIs( - coefficients.withPutOrChanged(emptyMap(), other) { it -> it + other } - ) - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - override operator fun LabeledPolynomial.minus(other: C): LabeledPolynomial = - if (coefficients.isEmpty()) other.asLabeledPolynomial() - else LabeledPolynomialAsIs( - coefficients.withPutOrChanged(emptyMap(), -other) { it -> it - other } - ) - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - override operator fun LabeledPolynomial.times(other: C): LabeledPolynomial = - LabeledPolynomialAsIs( - coefficients.mapValues { it.value * other } - ) - - /** - * Converts the constant [value] to polynomial. - */ - public override fun number(value: C): LabeledPolynomial = value.asLabeledPolynomial() - - /** - * Represents the variable as a monic monomial. - */ - public override operator fun Symbol.unaryPlus(): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(this to 1U) to constantOne, - ) - /** - * Returns negation of representation of the variable as a monic monomial. - */ - public override operator fun Symbol.unaryMinus(): LabeledPolynomial = - LabeledPolynomialAsIs( - mapOf(this to 1U) to -constantOne, - ) - /** - * Returns sum of the variables represented as monic monomials. - */ - public override operator fun Symbol.plus(other: Symbol): LabeledPolynomial = - if (this == other) LabeledPolynomialAsIs( - mapOf(this to 1U) to constantOne * 2 - ) - else LabeledPolynomialAsIs( - mapOf(this to 1U) to constantOne, - mapOf(other to 1U) to constantOne, - ) - /** - * Returns difference between the variables represented as monic monomials. - */ - public override operator fun Symbol.minus(other: Symbol): LabeledPolynomial = - if (this == other) zero - else LabeledPolynomialAsIs( - mapOf(this to 1U) to constantOne, - mapOf(other to 1U) to -constantOne, - ) - /** - * Returns product of the variables represented as monic monomials. - */ - public override operator fun Symbol.times(other: Symbol): LabeledPolynomial = - if (this == other) LabeledPolynomialAsIs( - mapOf(this to 2U) to constantOne - ) - else LabeledPolynomialAsIs( - mapOf(this to 1U, other to 1U) to constantOne, - ) - - /** - * Returns sum of the variable represented as a monic monomial and the polynomial. - */ - public override operator fun Symbol.plus(other: LabeledPolynomial): LabeledPolynomial = - if (other.coefficients.isEmpty()) this@plus.asPolynomial() - else LabeledPolynomialAsIs( - other.coefficients.withPutOrChanged(mapOf(this@plus to 1U), constantOne) { it -> constantOne + it } - ) - /** - * Returns difference between the variable represented as a monic monomial and the polynomial. - */ - public override operator fun Symbol.minus(other: LabeledPolynomial): LabeledPolynomial = - if (other.coefficients.isEmpty()) this@minus.asPolynomial() - else LabeledPolynomialAsIs( - buildMap(other.coefficients.size + 1) { - put(mapOf(this@minus to 1U), constantOne) - other.coefficients.copyMapToBy(this, { _, c -> -c }) { currentC, newC -> currentC - newC } - } - ) - /** - * Returns product of the variable represented as a monic monomial and the polynomial. - */ - public override operator fun Symbol.times(other: LabeledPolynomial): LabeledPolynomial = - LabeledPolynomialAsIs( - other.coefficients - .mapKeys { (degs, _) -> degs.withPutOrChanged(this, 1u) { it -> it + 1u } } - ) - - /** - * Returns sum of the polynomial and the variable represented as a monic monomial. - */ - public override operator fun LabeledPolynomial.plus(other: Symbol): LabeledPolynomial = - if (coefficients.isEmpty()) other.asPolynomial() - else LabeledPolynomialAsIs( - coefficients.withPutOrChanged(mapOf(other to 1U), constantOne) { it -> it + constantOne } - ) - /** - * Returns difference between the polynomial and the variable represented as a monic monomial. - */ - public override operator fun LabeledPolynomial.minus(other: Symbol): LabeledPolynomial = - if (coefficients.isEmpty()) other.asPolynomial() - else LabeledPolynomialAsIs( - coefficients.withPutOrChanged(mapOf(other to 1U), -constantOne) { it -> it - constantOne } - ) - /** - * Returns product of the polynomial and the variable represented as a monic monomial. - */ - public override operator fun LabeledPolynomial.times(other: Symbol): LabeledPolynomial = - LabeledPolynomialAsIs( - coefficients - .mapKeys { (degs, _) -> degs.withPutOrChanged(other, 1u) { it -> it + 1u } } - ) - - /** - * Returns negation of the polynomial. - */ - override fun LabeledPolynomial.unaryMinus(): LabeledPolynomial = - LabeledPolynomialAsIs( - coefficients.mapValues { -it.value } - ) - /** - * Returns sum of the polynomials. - */ - override operator fun LabeledPolynomial.plus(other: LabeledPolynomial): LabeledPolynomial = - LabeledPolynomialAsIs( - mergeBy(coefficients, other.coefficients) { c1, c2 -> c1 + c2 } - ) - /** - * Returns difference of the polynomials. - */ - override operator fun LabeledPolynomial.minus(other: LabeledPolynomial): LabeledPolynomial = - LabeledPolynomialAsIs( - buildMap(coefficients.size + other.coefficients.size) { - coefficients.copyTo(this) - other.coefficients.copyMapToBy(this, { _, c -> -c }, { currentC, newC -> currentC - newC }) - } - ) - /** - * Returns product of the polynomials. - */ - override operator fun LabeledPolynomial.times(other: LabeledPolynomial): LabeledPolynomial = - LabeledPolynomialAsIs( - buildMap(coefficients.size * other.coefficients.size) { - for ((degs1, c1) in coefficients) for ((degs2, c2) in other.coefficients) { - val degs = mergeBy(degs1, degs2) { deg1, deg2 -> deg1 + deg2 } - val c = c1 * c2 - this.putOrChange(degs, c) { it -> it + c } - } - } - ) - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - override val zero: LabeledPolynomial = LabeledPolynomialAsIs() - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - override val one: LabeledPolynomial = constantOne.asLabeledPolynomial() - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - override val LabeledPolynomial.degree: Int - get() = coefficients.entries.maxOfOrNull { (degs, _) -> degs.values.sum().toInt() } ?: -1 - /** - * Map that associates variables (that appear in the polynomial in positive exponents) with their most exponents - * in which they are appeared in the polynomial. - * - * As consequence all values in the map are positive integers. Also, if the polynomial is constant, the map is empty. - * And keys of the map is the same as in [variables]. - */ - public override val LabeledPolynomial.degrees: Map - get() = - buildMap { - coefficients.keys.forEach { degs -> - degs.copyToBy(this, ::max) - } - } - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public override fun LabeledPolynomial.degreeBy(variable: Symbol): UInt = - coefficients.entries.maxOfOrNull { (degs, _) -> degs.getOrElse(variable) { 0u } } ?: 0u - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public override fun LabeledPolynomial.degreeBy(variables: Collection): UInt = - coefficients.entries.maxOfOrNull { (degs, _) -> degs.filterKeys { it in variables }.values.sum() } ?: 0u - /** - * Set of all variables that appear in the polynomial in positive exponents. - */ - public override val LabeledPolynomial.variables: Set - get() = - buildSet { - coefficients.entries.forEach { (degs, _) -> addAll(degs.keys) } - } - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public override val LabeledPolynomial.countOfVariables: Int get() = variables.size - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - public inline fun LabeledPolynomial.substitute(arguments: Map): LabeledPolynomial = substitute(ring, arguments) - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun LabeledPolynomial.substitute(arguments: Map>) : LabeledPolynomial = substitute(ring, arguments) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/LabeledRationalFunction.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/LabeledRationalFunction.kt deleted file mode 100644 index e4f2b6c37..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/LabeledRationalFunction.kt +++ /dev/null @@ -1,92 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.operations.Ring -import kotlin.jvm.JvmName - - -/** - * Represents multivariate rational function that stores its numerator and denominator as [LabeledPolynomial]s. - */ -public data class LabeledRationalFunction( - public override val numerator: LabeledPolynomial, - public override val denominator: LabeledPolynomial -) : RationalFunction> { - override fun toString(): String = "LabeledRationalFunction${numerator.coefficients}/${denominator.coefficients}" -} - -/** - * Arithmetic context for univariate rational functions with numerator and denominator represented as [LabeledPolynomial]s. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class LabeledRationalFunctionSpace>( - public val ring: A, -) : - MultivariateRationalFunctionSpaceOverMultivariatePolynomialSpace< - C, - Symbol, - LabeledPolynomial, - LabeledRationalFunction, - LabeledPolynomialSpace, - >, - MultivariatePolynomialSpaceOfFractions< - C, - Symbol, - LabeledPolynomial, - LabeledRationalFunction, - >() { - - /** - * Underlying polynomial ring. Its polynomial operations are inherited by local polynomial operations. - */ - override val polynomialRing : LabeledPolynomialSpace = LabeledPolynomialSpace(ring) - /** - * Constructor of rational functions (of type [LabeledRationalFunction]) from numerator and denominator (of type [LabeledPolynomial]). - */ - override fun constructRationalFunction( - numerator: LabeledPolynomial, - denominator: LabeledPolynomial - ): LabeledRationalFunction = - LabeledRationalFunction(numerator, denominator) - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Substitutes provided constant [argument] into [this] polynomial. - */ - public inline fun LabeledPolynomial.substitute(argument: Map): LabeledPolynomial = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun LabeledPolynomial.substitute(argument: Map>): LabeledPolynomial = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] polynomial. - */ - @JvmName("substituteRationalFunction") - public inline fun LabeledPolynomial.substitute(argument: Map>): LabeledRationalFunction = substitute(ring, argument) - /** - * Substitutes provided constant [argument] into [this] rational function. - */ - public inline fun LabeledRationalFunction.substitute(argument: Map): LabeledRationalFunction = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] rational function. - */ - @JvmName("substitutePolynomial") - public inline fun LabeledRationalFunction.substitute(argument: Map>): LabeledRationalFunction = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] rational function. - */ - @JvmName("substituteRationalFunction") - public inline fun LabeledRationalFunction.substitute(argument: Map>): LabeledRationalFunction = substitute(ring, argument) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListPolynomial.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListPolynomial.kt deleted file mode 100644 index 6ab660b63..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListPolynomial.kt +++ /dev/null @@ -1,374 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.ScaleOperations -import space.kscience.kmath.operations.invoke -import kotlin.math.max -import kotlin.math.min - - -/** - * Represents univariate polynomial that stores its coefficients in a [List]. - * - * @param C the type of constants. - */ -public data class ListPolynomial( - /** - * List that contains coefficients of the polynomial. - * - * Every monomial \(a x^d\) is stored as a coefficient \(a\) placed - * into the list at index \(d\). For example, coefficients of a polynomial \(5 x^2 - 6\) can be represented as - * ``` - * listOf( - * -6, // -6 + - * 0, // 0 x + - * 5, // 5 x^2 - * ) - * ``` - * and also as - * ``` - * listOf( - * -6, // -6 + - * 0, // 0 x + - * 5, // 5 x^2 - * 0, // 0 x^3 - * 0, // 0 x^4 - * ) - * ``` - * It is not prohibited to put extra zeros at end of the list (as for \(0x^3\) and \(0x^4\) in the example). But the - * longer the coefficients list the worse performance of arithmetical operations performed on it. Thus, it is - * recommended not to put (or even to remove) extra (or useless) coefficients at the end of the coefficients list. - * @usesMathJax - */ - public val coefficients: List -) { - override fun toString(): String = "ListPolynomial$coefficients" -} - -/** - * Arithmetic context for univariate polynomials with coefficients stored as a [List] constructed with the provided - * [ring] of constants. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public open class ListPolynomialSpace>( - public override val ring: A, -) : PolynomialSpaceOverRing, A> { - /** - * Returns sum of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public override operator fun ListPolynomial.plus(other: Int): ListPolynomial = - if (other == 0) this - else - ListPolynomial( - coefficients - .toMutableList() - .apply { - val result = getOrElse(0) { constantZero } + other - - if(size == 0) add(result) - else this[0] = result - } - ) - /** - * Returns difference between the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public override operator fun ListPolynomial.minus(other: Int): ListPolynomial = - if (other == 0) this - else - ListPolynomial( - coefficients - .toMutableList() - .apply { - val result = getOrElse(0) { constantZero } - other - - if(size == 0) add(result) - else this[0] = result - } - ) - /** - * Returns product of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public override operator fun ListPolynomial.times(other: Int): ListPolynomial = - when (other) { - 0 -> zero - 1 -> this - else -> ListPolynomial( - coefficients.map { it * other } - ) - } - - /** - * Returns sum of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public override operator fun Int.plus(other: ListPolynomial): ListPolynomial = - if (this == 0) other - else - ListPolynomial( - other.coefficients - .toMutableList() - .apply { - val result = this@plus + getOrElse(0) { constantZero } - - if(size == 0) add(result) - else this[0] = result - } - ) - /** - * Returns difference between the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public override operator fun Int.minus(other: ListPolynomial): ListPolynomial = - ListPolynomial( - other.coefficients - .toMutableList() - .apply { - if (this@minus == 0) { - indices.forEach { this[it] = -this[it] } - } else { - (1..lastIndex).forEach { this[it] = -this[it] } - - val result = this@minus - getOrElse(0) { constantZero } - - if (size == 0) add(result) - else this[0] = result - } - } - ) - /** - * Returns product of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public override operator fun Int.times(other: ListPolynomial): ListPolynomial = - when (this) { - 0 -> zero - 1 -> other - else -> ListPolynomial( - other.coefficients.map { this@times * it } - ) - } - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - public override operator fun C.plus(other: ListPolynomial): ListPolynomial = - with(other.coefficients) { - if (isEmpty()) ListPolynomial(listOf(this@plus)) - else ListPolynomial( - toMutableList() - .apply { - val result = if (size == 0) this@plus else this@plus + get(0) - - if(size == 0) add(result) - else this[0] = result - } - ) - } - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - public override operator fun C.minus(other: ListPolynomial): ListPolynomial = - with(other.coefficients) { - if (isEmpty()) ListPolynomial(listOf(this@minus)) - else ListPolynomial( - toMutableList() - .apply { - (1 .. lastIndex).forEach { this[it] = -this[it] } - - val result = if (size == 0) this@minus else this@minus - get(0) - - if(size == 0) add(result) - else this[0] = result - } - ) - } - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - public override operator fun C.times(other: ListPolynomial): ListPolynomial = - ListPolynomial( - other.coefficients.map { this@times * it } - ) - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - public override operator fun ListPolynomial.plus(other: C): ListPolynomial = - with(coefficients) { - if (isEmpty()) ListPolynomial(listOf(other)) - else ListPolynomial( - toMutableList() - .apply { - val result = if (size == 0) other else get(0) + other - - if(size == 0) add(result) - else this[0] = result - } - ) - } - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - public override operator fun ListPolynomial.minus(other: C): ListPolynomial = - with(coefficients) { - if (isEmpty()) ListPolynomial(listOf(-other)) - else ListPolynomial( - toMutableList() - .apply { - val result = if (size == 0) other else get(0) - other - - if(size == 0) add(result) - else this[0] = result - } - ) - } - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - public override operator fun ListPolynomial.times(other: C): ListPolynomial = - ListPolynomial( - coefficients.map { it * other } - ) - - /** - * Converts the constant [value] to polynomial. - */ - public override fun number(value: C): ListPolynomial = ListPolynomial(listOf(value)) - - /** - * Returns negation of the polynomial. - */ - public override operator fun ListPolynomial.unaryMinus(): ListPolynomial = - ListPolynomial(coefficients.map { -it }) - /** - * Returns sum of the polynomials. - */ - public override operator fun ListPolynomial.plus(other: ListPolynomial): ListPolynomial { - val thisDegree = degree - val otherDegree = other.degree - return ListPolynomial( - List(max(thisDegree, otherDegree) + 1) { - when { - it > thisDegree -> other.coefficients[it] - it > otherDegree -> coefficients[it] - else -> coefficients[it] + other.coefficients[it] - } - } - ) - } - /** - * Returns difference of the polynomials. - */ - public override operator fun ListPolynomial.minus(other: ListPolynomial): ListPolynomial { - val thisDegree = degree - val otherDegree = other.degree - return ListPolynomial( - List(max(thisDegree, otherDegree) + 1) { - when { - it > thisDegree -> -other.coefficients[it] - it > otherDegree -> coefficients[it] - else -> coefficients[it] - other.coefficients[it] - } - } - ) - } - /** - * Returns product of the polynomials. - */ - public override operator fun ListPolynomial.times(other: ListPolynomial): ListPolynomial { - val thisDegree = degree - val otherDegree = other.degree - return ListPolynomial( - List(thisDegree + otherDegree + 1) { d -> - (max(0, d - otherDegree)..min(thisDegree, d)) - .map { coefficients[it] * other.coefficients[d - it] } - .reduce { acc, rational -> acc + rational } - } - ) - } - /** - * Raises [arg] to the integer power [exponent]. - */ // TODO: To optimize boxing - override fun power(arg: ListPolynomial, exponent: UInt): ListPolynomial = super.power(arg, exponent) - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - override val zero: ListPolynomial = ListPolynomial(emptyList()) - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - override val one: ListPolynomial by lazy { ListPolynomial(listOf(constantOne)) } - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public override val ListPolynomial.degree: Int get() = coefficients.lastIndex - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Evaluates value of [this] polynomial on provided [argument]. - */ - public inline fun ListPolynomial.substitute(argument: C): C = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] polynomial. - */ - public inline fun ListPolynomial.substitute(argument: ListPolynomial): ListPolynomial = substitute(ring, argument) - - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunction(): (C) -> C = asFunctionOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunctionOfConstant(): (C) -> C = asFunctionOfConstantOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunctionOfPolynomial(): (ListPolynomial) -> ListPolynomial = asFunctionOfPolynomialOver(ring) - - /** - * Evaluates value of [this] polynomial on provided [argument]. - */ - public inline operator fun ListPolynomial.invoke(argument: C): C = substitute(ring, argument) - /** - * Evaluates value of [this] polynomial on provided [argument]. - */ - public inline operator fun ListPolynomial.invoke(argument: ListPolynomial): ListPolynomial = substitute(ring, argument) -} - -/** - * Space of polynomials constructed over ring. - * - * @param C the type of constants. Polynomials have them as a coefficients in their terms. - * @param A type of underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class ScalableListPolynomialSpace( - ring: A, -) : ListPolynomialSpace(ring), ScaleOperations> where A : Ring, A : ScaleOperations { - override fun scale(a: ListPolynomial, value: Double): ListPolynomial = - ring { ListPolynomial(a.coefficients.map { scale(it, value) }) } -} diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListRationalFunction.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListRationalFunction.kt deleted file mode 100644 index b744afc51..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/ListRationalFunction.kt +++ /dev/null @@ -1,123 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.operations.Ring - - -/** - * Represents univariate rational function that stores its numerator and denominator as [ListPolynomial]s. - */ -public data class ListRationalFunction( - public override val numerator: ListPolynomial, - public override val denominator: ListPolynomial -) : RationalFunction> { - override fun toString(): String = "ListRationalFunction${numerator.coefficients}/${denominator.coefficients}" -} - -/** - * Arithmetic context for univariate rational functions with numerator and denominator represented as [ListPolynomial]s. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class ListRationalFunctionSpace> ( - public val ring: A, -) : - RationalFunctionSpaceOverPolynomialSpace< - C, - ListPolynomial, - ListRationalFunction, - ListPolynomialSpace, - >, - PolynomialSpaceOfFractions< - C, - ListPolynomial, - ListRationalFunction, - >() { - - /** - * Underlying polynomial ring. Its polynomial operations are inherited by local polynomial operations. - */ - override val polynomialRing : ListPolynomialSpace = ListPolynomialSpace(ring) - /** - * Constructor of [ListRationalFunction] from numerator and denominator [ListPolynomial]. - */ - override fun constructRationalFunction(numerator: ListPolynomial, denominator: ListPolynomial): ListRationalFunction = - ListRationalFunction(numerator, denominator) - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Evaluates value of [this] polynomial on provided argument. - */ - public inline fun ListPolynomial.substitute(argument: C): C = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] polynomial. - */ - public inline fun ListPolynomial.substitute(argument: ListPolynomial): ListPolynomial = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] polynomial. - */ - public inline fun ListPolynomial.substitute(argument: ListRationalFunction): ListRationalFunction = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] rational function. - */ - public inline fun ListRationalFunction.substitute(argument: ListPolynomial): ListRationalFunction = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] rational function. - */ - public inline fun ListRationalFunction.substitute(argument: ListRationalFunction): ListRationalFunction = substitute(ring, argument) - - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunction(): (C) -> C = { substitute(ring, it) } - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunctionOfConstant(): (C) -> C = { substitute(ring, it) } - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunctionOfPolynomial(): (ListPolynomial) -> ListPolynomial = { substitute(ring, it) } - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun ListPolynomial.asFunctionOfRationalFunction(): (ListRationalFunction) -> ListRationalFunction = { substitute(ring, it) } - /** - * Represent [this] rational function as a regular context-less function. - */ - public inline fun ListRationalFunction.asFunctionOfPolynomial(): (ListPolynomial) -> ListRationalFunction = { substitute(ring, it) } - /** - * Represent [this] rational function as a regular context-less function. - */ - public inline fun ListRationalFunction.asFunctionOfRationalFunction(): (ListRationalFunction) -> ListRationalFunction = { substitute(ring, it) } - - /** - * Evaluates value of [this] polynomial on provided argument. - */ - public inline operator fun ListPolynomial.invoke(argument: C): C = substitute(ring, argument) - /** - * Evaluates value of [this] polynomial on provided argument. - */ - public inline operator fun ListPolynomial.invoke(argument: ListPolynomial): ListPolynomial = substitute(ring, argument) - /** - * Evaluates value of [this] polynomial on provided argument. - */ - public inline operator fun ListPolynomial.invoke(argument: ListRationalFunction): ListRationalFunction = substitute(ring, argument) - /** - * Evaluates value of [this] rational function on provided argument. - */ - public inline operator fun ListRationalFunction.invoke(argument: ListPolynomial): ListRationalFunction = substitute(ring, argument) - /** - * Evaluates value of [this] rational function on provided argument. - */ - public inline operator fun ListRationalFunction.invoke(argument: ListRationalFunction): ListRationalFunction = substitute(ring, argument) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedPolynomial.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedPolynomial.kt deleted file mode 100644 index 267bbd91d..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedPolynomial.kt +++ /dev/null @@ -1,350 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.structures.Buffer -import kotlin.jvm.JvmName -import kotlin.math.max - - -/** - * Represents multivariate polynomial that stores its coefficients in a [Map] and terms' signatures in a [List]. - * - * @param C the type of constants. - */ -public data class NumberedPolynomial -@PublishedApi -internal constructor( - /** - * Map that contains coefficients of the polynomial. - * - * Every monomial \(a x_1^{d_1} ... x_n^{d_n}\) is stored as a pair "key-value" in the map, where the value is the - * coefficient \(a\) and the key is a list that associates index of every variable in the monomial with their degree - * in the monomial. For example, coefficients of a polynomial \(5 x_1^2 x_3^3 - 6 x_2\) can be represented as - * ``` - * mapOf( - * listOf(2, 0, 3) to 5, // 5 x_1^2 x_3^3 + - * listOf(0, 1) to (-6), // (-6) x_2^1 - * ) - * ``` - * and also as - * ``` - * mapOf( - * listOf(2, 0, 3) to 5, // 5 x_1^2 x_3^3 + - * listOf(0, 1) to (-6), // (-6) x_2^1 - * listOf(0, 1, 1) to 0, // 0 x_2^1 x_3^1 - * ) - * ``` - * It is not prohibited to put extra zero monomials into the map (as for \(0 x_2 x_3\) in the example). But the - * bigger the coefficients map the worse performance of arithmetical operations performed on it. Thus, it is - * recommended not to put (or even to remove) extra (or useless) monomials in the coefficients map. - * @usesMathJax - */ - public val coefficients: Map, C> -) { - override fun toString(): String = "NumberedPolynomial$coefficients" -} - -/** - * Arithmetic context for multivariate polynomials with coefficients stored as a [Map] and terms' signatures stored as a - * [List] constructed with the provided [ring] of constants. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class NumberedPolynomialSpace>( - public override val ring: A, -) : PolynomialSpaceOverRing, A> { - /** - * Returns sum of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public override operator fun NumberedPolynomial.plus(other: Int): NumberedPolynomial = - if (other == 0) this - else NumberedPolynomialAsIs( - coefficients.withPutOrChanged(emptyList(), other.asConstant()) { it -> it + other } - ) - /** - * Returns difference between the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public override operator fun NumberedPolynomial.minus(other: Int): NumberedPolynomial = - if (other == 0) this - else NumberedPolynomialAsIs( - coefficients.withPutOrChanged(emptyList(), (-other).asConstant()) { it -> it - other } - ) - /** - * Returns product of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public override operator fun NumberedPolynomial.times(other: Int): NumberedPolynomial = - when (other) { - 0 -> zero - 1 -> this - else -> NumberedPolynomialAsIs( - coefficients.mapValues { it.value * other } - ) - } - - /** - * Returns sum of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public override operator fun Int.plus(other: NumberedPolynomial): NumberedPolynomial = - if (this == 0) other - else NumberedPolynomialAsIs( - other.coefficients.withPutOrChanged(emptyList(), this@plus.asConstant()) { it -> this@plus + it } - ) - /** - * Returns difference between the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public override operator fun Int.minus(other: NumberedPolynomial): NumberedPolynomial = - when { - this == 0 -> -other - other.coefficients.isEmpty() -> this.asPolynomial() - else -> NumberedPolynomialAsIs( - buildMap(other.coefficients.size + 1) { - put(emptyList(), other.coefficients.computeOnOrElse(emptyList(), { this@minus.asConstant() }, { it -> this@minus - it})) - other.coefficients.copyMapToBy(this, { _, c -> -c }) { currentC, _ -> currentC } - } - ) - } - /** - * Returns product of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public override operator fun Int.times(other: NumberedPolynomial): NumberedPolynomial = - when (this) { - 0 -> zero - 1 -> other - else -> NumberedPolynomialAsIs( - other.coefficients.mapValues { this@times * it.value } - ) - } - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - override operator fun C.plus(other: NumberedPolynomial): NumberedPolynomial = - if (other.coefficients.isEmpty()) this@plus.asPolynomial() - else NumberedPolynomialAsIs( - other.coefficients.withPutOrChanged(emptyList(), this@plus) { it -> this@plus + it } - ) - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - override operator fun C.minus(other: NumberedPolynomial): NumberedPolynomial = - if (other.coefficients.isEmpty()) this@minus.asPolynomial() - else NumberedPolynomialAsIs( - buildMap(other.coefficients.size) { - put(emptyList(), other.coefficients.computeOnOrElse(emptyList(), this@minus) { it -> this@minus - it }) - other.coefficients.copyMapToBy(this, { _, c -> -c }, { currentC, _ -> currentC }) - } - ) - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - override operator fun C.times(other: NumberedPolynomial): NumberedPolynomial = - NumberedPolynomialAsIs( - other.coefficients.mapValues { this@times * it.value } - ) - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - override operator fun NumberedPolynomial.plus(other: C): NumberedPolynomial = - if (coefficients.isEmpty()) other.asPolynomial() - else NumberedPolynomialAsIs( - coefficients.withPutOrChanged(emptyList(), other) { it -> it + other } - ) - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - override operator fun NumberedPolynomial.minus(other: C): NumberedPolynomial = - if (coefficients.isEmpty()) other.asPolynomial() - else NumberedPolynomialAsIs( - coefficients.withPutOrChanged(emptyList(), -other) { it -> it - other } - ) - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - override operator fun NumberedPolynomial.times(other: C): NumberedPolynomial = - NumberedPolynomialAsIs( - coefficients.mapValues { it.value * other } - ) - - /** - * Converts the constant [value] to polynomial. - */ - public override fun number(value: C): NumberedPolynomial = - NumberedPolynomialAsIs(mapOf(emptyList() to value)) - - /** - * Returns negation of the polynomial. - */ - override fun NumberedPolynomial.unaryMinus(): NumberedPolynomial = - NumberedPolynomialAsIs( - coefficients.mapValues { -it.value } - ) - /** - * Returns sum of the polynomials. - */ - override operator fun NumberedPolynomial.plus(other: NumberedPolynomial): NumberedPolynomial = - NumberedPolynomialAsIs( - mergeBy(coefficients, other.coefficients) { c1, c2 -> c1 + c2 } - ) - /** - * Returns difference of the polynomials. - */ - override operator fun NumberedPolynomial.minus(other: NumberedPolynomial): NumberedPolynomial = - NumberedPolynomialAsIs( - buildMap(coefficients.size + other.coefficients.size) { - coefficients.copyTo(this) - other.coefficients.copyMapToBy(this, { _, c -> -c }, { currentC, newC -> currentC - newC }) - } - ) - /** - * Returns product of the polynomials. - */ - override operator fun NumberedPolynomial.times(other: NumberedPolynomial): NumberedPolynomial = - NumberedPolynomialAsIs( - buildMap(coefficients.size * other.coefficients.size) { - for ((degs1, c1) in coefficients) for ((degs2, c2) in other.coefficients) { - val degs = - (0..max(degs1.lastIndex, degs2.lastIndex)) - .map { degs1.getOrElse(it) { 0U } + degs2.getOrElse(it) { 0U } } - val c = c1 * c2 - putOrChange(degs, c) { it -> it + c } - } - } - ) - /** - * Raises [arg] to the integer power [exponent]. - */ // TODO: To optimize boxing - override fun power(arg: NumberedPolynomial, exponent: UInt): NumberedPolynomial = super.power(arg, exponent) - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - override val zero: NumberedPolynomial = NumberedPolynomialAsIs(emptyMap()) - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - override val one: NumberedPolynomial by lazy { NumberedPolynomialAsIs(mapOf(emptyList() to constantOne)) } - - /** - * Maximal index (ID) of variable occurring in the polynomial with positive power. If there is no such variable, - * the result is -1. - */ - public val NumberedPolynomial.lastVariable: Int - get() = coefficients.keys.maxOfOrNull { degs -> degs.lastIndex } ?: -1 - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - override val NumberedPolynomial.degree: Int - get() = coefficients.keys.maxOfOrNull { degs -> degs.sum().toInt() } ?: -1 - /** - * List that associates indices of variables (that appear in the polynomial in positive exponents) with their most - * exponents in which the variables are appeared in the polynomial. - * - * As consequence all values in the list are non-negative integers. Also, if the polynomial is constant, the list is empty. - * And last index of the list is [lastVariable]. - */ - public val NumberedPolynomial.degrees: List - get() = - MutableList(lastVariable + 1) { 0u }.apply { - coefficients.keys.forEach { degs -> - degs.forEachIndexed { index, deg -> - this[index] = max(this[index], deg) - } - } - } - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public fun NumberedPolynomial.degreeBy(variable: Int): UInt = - coefficients.keys.maxOfOrNull { degs -> degs.getOrElse(variable) { 0u } } ?: 0u - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public fun NumberedPolynomial.degreeBy(variables: Collection): UInt = - coefficients.keys.maxOfOrNull { degs -> - degs.withIndex().fold(0u) { acc, (index, value) -> if (index in variables) acc + value else acc } - } ?: 0u - /** - * Count of variables occurring in the polynomial with positive power. If there is no such variable, - * the result is 0. - */ - public val NumberedPolynomial.countOfVariables: Int - get() = - MutableList(lastVariable + 1) { false }.apply { - coefficients.entries.forEach { (degs, _) -> - degs.forEachIndexed { index, deg -> - if (deg != 0u) this[index] = true - } - } - }.count { it } - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substitute(arguments: Map): NumberedPolynomial = substitute(ring, arguments) - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedPolynomial.substitute(arguments: Map>) : NumberedPolynomial = substitute(ring, arguments) - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substitute(arguments: Buffer): NumberedPolynomial = substitute(ring, arguments) - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedPolynomial.substitute(arguments: Buffer>) : NumberedPolynomial = substitute(ring, arguments) - /** - * Substitutes provided arguments [arguments] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substituteFully(arguments: Buffer): C = this.substituteFully(ring, arguments) - - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunction(): (Buffer) -> C = asFunctionOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunctionOfConstant(): (Buffer) -> C = asFunctionOfConstantOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunctionOfPolynomial(): (Buffer>) -> NumberedPolynomial = asFunctionOfPolynomialOver(ring) - - /** - * Evaluates value of [this] polynomial on provided [arguments]. - */ - public inline operator fun NumberedPolynomial.invoke(arguments: Buffer): C = substituteFully(ring, arguments) - /** - * Substitutes provided [arguments] into [this] polynomial. - */ - @JvmName("invokePolynomial") - public inline operator fun NumberedPolynomial.invoke(arguments: Buffer>): NumberedPolynomial = substitute(ring, arguments) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedRationalFunction.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedRationalFunction.kt deleted file mode 100644 index 0f3c1ced9..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/NumberedRationalFunction.kt +++ /dev/null @@ -1,225 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.invoke -import space.kscience.kmath.structures.Buffer -import kotlin.jvm.JvmName -import kotlin.math.max - - -/** - * Represents multivariate rational function that stores its numerator and denominator as [NumberedPolynomial]s. - */ -public data class NumberedRationalFunction( - public override val numerator: NumberedPolynomial, - public override val denominator: NumberedPolynomial -) : RationalFunction> { - override fun toString(): String = "NumberedRationalFunction${numerator.coefficients}/${denominator.coefficients}" -} - -/** - * Arithmetic context for univariate rational functions with numerator and denominator represented as [NumberedPolynomial]s. - * - * @param C the type of constants. Polynomials have them a coefficients in their terms. - * @param A type of provided underlying ring of constants. It's [Ring] of [C]. - * @param ring underlying ring of constants of type [A]. - */ -public class NumberedRationalFunctionSpace> ( - public val ring: A, -) : - RationalFunctionSpaceOverPolynomialSpace< - C, - NumberedPolynomial, - NumberedRationalFunction, - NumberedPolynomialSpace, - >, - PolynomialSpaceOfFractions< - C, - NumberedPolynomial, - NumberedRationalFunction, - >() { - - /** - * Underlying polynomial ring. Its polynomial operations are inherited by local polynomial operations. - */ - public override val polynomialRing : NumberedPolynomialSpace = NumberedPolynomialSpace(ring) - /** - * Constructor of rational functions (of type [NumberedRationalFunction]) from numerator and denominator (of type [NumberedPolynomial]). - */ - protected override fun constructRationalFunction( - numerator: NumberedPolynomial, - denominator: NumberedPolynomial - ): NumberedRationalFunction = - NumberedRationalFunction(numerator, denominator) - - /** - * Maximal index (ID) of variable occurring in the polynomial with positive power. If there is no such variable, - * the result is `-1`. - */ - public val NumberedPolynomial.lastVariable: Int get() = polynomialRing { lastVariable } - /** - * List that associates indices of variables (that appear in the polynomial in positive exponents) with their most - * exponents in which the variables are appeared in the polynomial. - * - * As consequence all values in the list are non-negative integers. Also, if the polynomial is constant, the list is empty. - * And last index of the list is [lastVariable]. - */ - public val NumberedPolynomial.degrees: List get() = polynomialRing { degrees } - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public fun NumberedPolynomial.degreeBy(variable: Int): UInt = polynomialRing { degreeBy(variable) } - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public fun NumberedPolynomial.degreeBy(variables: Collection): UInt = polynomialRing { degreeBy(variables) } - /** - * Count of variables occurring in the polynomial with positive power. If there is no such variable, - * the result is `0`. - */ - public val NumberedPolynomial.countOfVariables: Int get() = polynomialRing { countOfVariables } - - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public val NumberedRationalFunction.lastVariable: Int - get() = polynomialRing { max(numerator.lastVariable, denominator.lastVariable) } - /** - * Count of variables occurring in the rational function with positive power. If there is no such variable, - * the result is `0`. - */ - public val NumberedRationalFunction.countOfVariables: Int - get() = - MutableList(lastVariable + 1) { false }.apply { - numerator.coefficients.entries.forEach { (degs, _) -> - degs.forEachIndexed { index, deg -> - if (deg != 0u) this[index] = true - } - } - denominator.coefficients.entries.forEach { (degs, _) -> - degs.forEachIndexed { index, deg -> - if (deg != 0u) this[index] = true - } - } - }.count { it } - - // TODO: When context receivers will be ready move all of this substitutions and invocations to utilities with - // [ListPolynomialSpace] as a context receiver - /** - * Substitutes provided constant [argument] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substitute(argument: Map): NumberedPolynomial = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedPolynomial.substitute(argument: Map>): NumberedPolynomial = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] polynomial. - */ - @JvmName("substituteRationalFunction") - public inline fun NumberedPolynomial.substitute(argument: Map>): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided constant [argument] into [this] rational function. - */ - public inline fun NumberedRationalFunction.substitute(argument: Map): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] rational function. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedRationalFunction.substitute(argument: Map>): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] rational function. - */ - @JvmName("substituteRationalFunction") - public inline fun NumberedRationalFunction.substitute(argument: Map>): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided constant [argument] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substitute(argument: Buffer): NumberedPolynomial = substitute(ring, argument) - /** - * Substitutes provided polynomial [argument] into [this] polynomial. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedPolynomial.substitute(argument: Buffer>): NumberedPolynomial = substitute(ring, argument) - /** - * Substitutes provided rational function [argument] into [this] polynomial. - */ - @JvmName("substituteRationalFunction") - public inline fun NumberedPolynomial.substitute(argument: Buffer>): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided constant [argument] into [this] rational function. - */ - public inline fun NumberedRationalFunction.substitute(argument: Buffer): NumberedRationalFunction = substitute(ring, argument) - /** - * Substitutes provided polynomial [arguments] into [this] rational function. - */ - @JvmName("substitutePolynomial") - public inline fun NumberedRationalFunction.substitute(arguments: Buffer>): NumberedRationalFunction = substitute(ring, arguments) - /** - * Substitutes provided rational function [arguments] into [this] rational function. - */ - @JvmName("substituteRationalFunction") - public inline fun NumberedRationalFunction.substitute(arguments: Buffer>): NumberedRationalFunction = substitute(ring, arguments) - /** - * Substitutes provided constant [arguments] into [this] polynomial. - */ - public inline fun NumberedPolynomial.substituteFully(arguments: Buffer): C = substituteFully(ring, arguments) - - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunction(): (Buffer) -> C = asFunctionOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunctionOfConstant(): (Buffer) -> C = asFunctionOfConstantOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunctionOfPolynomial(): (Buffer>) -> NumberedPolynomial = asFunctionOfPolynomialOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedPolynomial.asFunctionOfRationalFunction(): (Buffer>) -> NumberedRationalFunction = asFunctionOfRationalFunctionOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedRationalFunction.asFunctionOfPolynomial(): (Buffer>) -> NumberedRationalFunction = asFunctionOfPolynomialOver(ring) - /** - * Represent [this] polynomial as a regular context-less function. - */ - public inline fun NumberedRationalFunction.asFunctionOfRationalFunction(): (Buffer>) -> NumberedRationalFunction = asFunctionOfRationalFunctionOver(ring) - - /** - * Evaluates value of [this] polynomial on provided [arguments]. - */ - public inline operator fun NumberedPolynomial.invoke(arguments: Buffer): C = substituteFully(ring, arguments) - /** - * Substitutes provided [arguments] into [this] polynomial. - */ - @JvmName("invokePolynomial") - public inline operator fun NumberedPolynomial.invoke(arguments: Buffer>): NumberedPolynomial = substitute(ring, arguments) - /** - * Substitutes provided [arguments] into [this] polynomial. - */ - @JvmName("invokeRationalFunction") - public inline operator fun NumberedPolynomial.invoke(arguments: Buffer>): NumberedRationalFunction = substitute(ring, arguments) - /** - * Substitutes provided [arguments] into [this] rational function. - */ - @JvmName("invokePolynomial") - public inline operator fun NumberedRationalFunction.invoke(arguments: Buffer>): NumberedRationalFunction = substitute(ring, arguments) - /** - * Substitutes provided [arguments] into [this] rational function. - */ - @JvmName("invokeRationalFunction") - public inline operator fun NumberedRationalFunction.invoke(arguments: Buffer>): NumberedRationalFunction = substitute(ring, arguments) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt deleted file mode 100644 index 6a11eb1bd..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/Polynomial.kt +++ /dev/null @@ -1,527 +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.functions - -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.invoke -import kotlin.js.JsName -import kotlin.jvm.JvmName - - -/** - * Abstraction of ring of polynomials of type [P] over ring of constants of type [C]. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. - */ -@Suppress("INAPPLICABLE_JVM_NAME", "PARAMETER_NAME_CHANGED_ON_OVERRIDE") // FIXME: Waiting for KT-31420 -public interface PolynomialSpace : Ring

{ - /** - * Returns sum of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to adding [other] copies of unit of underlying ring to [this]. - */ - @JvmName("plusConstantInt") - public operator fun C.plus(other: Int): C - /** - * Returns difference between the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to subtraction [other] copies of unit of underlying ring from [this]. - */ - @JvmName("minusConstantInt") - public operator fun C.minus(other: Int): C - /** - * Returns product of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesConstantInt") - public operator fun C.times(other: Int): C - - /** - * Returns sum of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to adding [this] copies of unit of underlying ring to [other]. - */ - @JvmName("plusIntConstant") - public operator fun Int.plus(other: C): C - /** - * Returns difference between the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit of underlying ring from [other]. - */ - @JvmName("minusIntConstant") - public operator fun Int.minus(other: C): C - /** - * Returns product of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntConstant") - public operator fun Int.times(other: C): C - - /** - * Converts the integer [value] to constant. - */ - public fun constantNumber(value: Int): C = constantOne * value - /** - * Converts the integer to constant. - */ - public fun Int.asConstant(): C = constantNumber(this) - - /** - * Returns sum of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public operator fun P.plus(other: Int): P = addMultipliedByDoubling(this, one, other) - /** - * Returns difference between the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public operator fun P.minus(other: Int): P = addMultipliedByDoubling(this, one, -other) - /** - * Returns product of the polynomial and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public operator fun P.times(other: Int): P = multiplyByDoubling(this, other) - - /** - * Returns sum of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public operator fun Int.plus(other: P): P = addMultipliedByDoubling(other, one, this) - /** - * Returns difference between the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public operator fun Int.minus(other: P): P = addMultipliedByDoubling(-other, one, this) - /** - * Returns product of the integer represented as a polynomial and the polynomial. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public operator fun Int.times(other: P): P = multiplyByDoubling(other, this) - - /** - * Converts the integer [value] to polynomial. - */ - public fun number(value: Int): P = number(constantNumber(value)) - /** - * Converts the integer to polynomial. - */ - public fun Int.asPolynomial(): P = number(this) - - /** - * Returns the same constant. - */ - @JvmName("unaryPlusConstant") - @JsName("unaryPlusConstant") - public operator fun C.unaryPlus(): C = this - /** - * Returns negation of the constant. - */ - @JvmName("unaryMinusConstant") - @JsName("unaryMinusConstant") - public operator fun C.unaryMinus(): C - /** - * Returns sum of the constants. - */ - @JvmName("plusConstantConstant") - @JsName("plusConstantConstant") - public operator fun C.plus(other: C): C - /** - * Returns difference of the constants. - */ - @JvmName("minusConstantConstant") - @JsName("minusConstantConstant") - public operator fun C.minus(other: C): C - /** - * Returns product of the constants. - */ - @JvmName("timesConstantConstant") - @JsName("timesConstantConstant") - public operator fun C.times(other: C): C - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerConstant") - @JsName("powerConstant") - public fun power(arg: C, exponent: UInt) : C - - /** - * Instance of zero constant (zero of the underlying ring). - */ - public val constantZero: C - /** - * Instance of unit constant (unit of the underlying ring). - */ - public val constantOne: C - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusConstantPolynomial") - public operator fun C.plus(other: P): P - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusConstantPolynomial") - public operator fun C.minus(other: P): P - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesConstantPolynomial") - public operator fun C.times(other: P): P - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusPolynomialConstant") - public operator fun P.plus(other: C): P - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusPolynomialConstant") - public operator fun P.minus(other: C): P - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesPolynomialConstant") - public operator fun P.times(other: C): P - - /** - * Converts the constant [value] to polynomial. - */ - public fun number(value: C): P = one * value - /** - * Converts the constant to polynomial. - */ - public fun C.asPolynomial(): P = number(this) - - /** - * Returns the same polynomial. - */ - public override operator fun P.unaryPlus(): P = this - /** - * Returns negation of the polynomial. - */ - public override operator fun P.unaryMinus(): P - /** - * Returns sum of the polynomials. - */ - public override operator fun P.plus(other: P): P - /** - * Returns difference of the polynomials. - */ - public override operator fun P.minus(other: P): P - /** - * Returns product of the polynomials. - */ - public override operator fun P.times(other: P): P - /** - * Raises [arg] to the integer power [exponent]. - */ - public override fun power(arg: P, exponent: UInt) : P = exponentiateBySquaring(arg, exponent) - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - public override val zero: P - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - public override val one: P - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public val P.degree: Int - - override fun add(left: P, right: P): P = left + right - override fun multiply(left: P, right: P): P = left * right -} - -/** - * Abstraction of ring of polynomials of type [P] over ring of constants of type [C]. It also assumes that there is - * provided [ring] (of type [A]), that provides constant-wise operations. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. - * @param A the type of algebraic structure (precisely, of ring) provided for constants. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface PolynomialSpaceOverRing> : PolynomialSpace { - - /** - * Underlying ring of constants. Its operations on constants are inherited by local operations on constants. - */ - public val ring: A - - /** - * Returns sum of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to adding [other] copies of unit of underlying ring to [this]. - */ - @JvmName("plusConstantInt") - public override operator fun C.plus(other: Int): C = ring { addMultipliedByDoubling(this@plus, one, other) } - /** - * Returns difference between the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to subtraction [other] copies of unit of underlying ring from [this]. - */ - @JvmName("minusConstantInt") - public override operator fun C.minus(other: Int): C = ring { addMultipliedByDoubling(this@minus, one, -other) } - /** - * Returns product of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesConstantInt") - public override operator fun C.times(other: Int): C = ring { multiplyByDoubling(this@times, other) } - - /** - * Returns sum of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to adding [this] copies of unit of underlying ring to [other]. - */ - @JvmName("plusIntConstant") - public override operator fun Int.plus(other: C): C = ring { addMultipliedByDoubling(other, one, this@plus) } - /** - * Returns difference between the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit of underlying ring from [other]. - */ - @JvmName("minusIntConstant") - public override operator fun Int.minus(other: C): C = ring { addMultipliedByDoubling(-other, one, this@minus) } - /** - * Returns product of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntConstant") - public override operator fun Int.times(other: C): C = ring { multiplyByDoubling(other, this@times) } - - /** - * Returns negation of the constant. - */ - @JvmName("unaryMinusConstant") - public override operator fun C.unaryMinus(): C = ring { -this@unaryMinus } - /** - * Returns sum of the constants. - */ - @JvmName("plusConstantConstant") - public override operator fun C.plus(other: C): C = ring { this@plus + other } - /** - * Returns difference of the constants. - */ - @JvmName("minusConstantConstant") - public override operator fun C.minus(other: C): C = ring { this@minus - other } - /** - * Returns product of the constants. - */ - @JvmName("timesConstantConstant") - public override operator fun C.times(other: C): C = ring { this@times * other } - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerConstant") - override fun power(arg: C, exponent: UInt): C = ring { power(arg, exponent) } - - /** - * Instance of zero constant (zero of the underlying ring). - */ - public override val constantZero: C get() = ring.zero - /** - * Instance of unit constant (unit of the underlying ring). - */ - public override val constantOne: C get() = ring.one -} - -/** - * Abstraction of ring of polynomials of type [P] of variables of type [V] and over ring of constants of type [C]. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param V the type of variables. Polynomials have them in representations of terms. - * @param P the type of polynomials. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface MultivariatePolynomialSpace: PolynomialSpace { - /** - * Returns sum of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("plusVariableInt") - @JsName("plusVariableInt") - public operator fun V.plus(other: Int): P - /** - * Returns difference between the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("minusVariableInt") - @JsName("minusVariableInt") - public operator fun V.minus(other: Int): P - /** - * Returns product of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("timesVariableInt") - @JsName("timesVariableInt") - public operator fun V.times(other: Int): P - - /** - * Returns sum of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusIntVariable") - @JsName("plusIntVariable") - public operator fun Int.plus(other: V): P - /** - * Returns difference between the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusIntVariable") - @JsName("minusIntVariable") - public operator fun Int.minus(other: V): P - /** - * Returns product of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesIntVariable") - @JsName("timesIntVariable") - public operator fun Int.times(other: V): P - - /** - * Returns sum of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("plusVariableConstant") - @JsName("plusVariableConstant") - public operator fun V.plus(other: C): P - /** - * Returns difference between the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("minusVariableConstant") - @JsName("minusVariableConstant") - public operator fun V.minus(other: C): P - /** - * Returns product of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("timesVariableConstant") - @JsName("timesVariableConstant") - public operator fun V.times(other: C): P - - /** - * Returns sum of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusConstantVariable") - @JsName("plusConstantVariable") - public operator fun C.plus(other: V): P - /** - * Returns difference between the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusConstantVariable") - @JsName("minusConstantVariable") - public operator fun C.minus(other: V): P - /** - * Returns product of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesConstantVariable") - @JsName("timesConstantVariable") - public operator fun C.times(other: V): P - - /** - * Represents the variable as a monic monomial. - */ - @JvmName("unaryPlusVariable") - public operator fun V.unaryPlus(): P - /** - * Returns negation of representation of the variable as a monic monomial. - */ - @JvmName("unaryMinusVariable") - public operator fun V.unaryMinus(): P - /** - * Returns sum of the variables represented as monic monomials. - */ - @JvmName("plusVariableVariable") - public operator fun V.plus(other: V): P - /** - * Returns difference between the variables represented as monic monomials. - */ - @JvmName("minusVariableVariable") - public operator fun V.minus(other: V): P - /** - * Returns product of the variables represented as monic monomials. - */ - @JvmName("timesVariableVariable") - public operator fun V.times(other: V): P - - /** - * Represents the [variable] as a monic monomial. - */ - @JvmName("numberVariable") - public fun number(variable: V): P = +variable - /** - * Represents the variable as a monic monomial. - */ - @JvmName("asPolynomialVariable") - public fun V.asPolynomial(): P = number(this) - - /** - * Returns sum of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("plusVariablePolynomial") - public operator fun V.plus(other: P): P - /** - * Returns difference between the variable represented as a monic monomial and the polynomial. - */ - @JvmName("minusVariablePolynomial") - public operator fun V.minus(other: P): P - /** - * Returns product of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("timesVariablePolynomial") - public operator fun V.times(other: P): P - - /** - * Returns sum of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusPolynomialVariable") - public operator fun P.plus(other: V): P - /** - * Returns difference between the polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusPolynomialVariable") - public operator fun P.minus(other: V): P - /** - * Returns product of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesPolynomialVariable") - public operator fun P.times(other: V): P - - /** - * Map that associates variables (that appear in the polynomial in positive exponents) with their most exponents - * in which they are appeared in the polynomial. - * - * As consequence all values in the map are positive integers. Also, if the polynomial is constant, the map is empty. - * And keys of the map is the same as in [variables]. - */ - public val P.degrees: Map - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public fun P.degreeBy(variable: V): UInt = degrees.getOrElse(variable) { 0u } - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public fun P.degreeBy(variables: Collection): UInt - /** - * Set of all variables that appear in the polynomial in positive exponents. - */ - public val P.variables: Set get() = degrees.keys - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public val P.countOfVariables: Int get() = variables.size -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/RationalFunction.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/RationalFunction.kt deleted file mode 100644 index 3c1548516..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/RationalFunction.kt +++ /dev/null @@ -1,1689 +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.functions - -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.invoke -import kotlin.js.JsName -import kotlin.jvm.JvmName - - -/** - * Abstraction of rational function. - */ -public interface RationalFunction { - public val numerator: P - public val denominator: P - public operator fun component1(): P = numerator - public operator fun component2(): P = denominator -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] and constants of type - * [C]. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators. - * @param R the type of rational functions. - */ -@Suppress("INAPPLICABLE_JVM_NAME", "PARAMETER_NAME_CHANGED_ON_OVERRIDE") // FIXME: Waiting for KT-31420 -public interface RationalFunctionSpace> : Ring { - /** - * Returns sum of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to adding [other] copies of unit of underlying ring to [this]. - */ - @JvmName("plusConstantInt") - public operator fun C.plus(other: Int): C - /** - * Returns difference between the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to subtraction [other] copies of unit of underlying ring from [this]. - */ - @JvmName("minusConstantInt") - public operator fun C.minus(other: Int): C - /** - * Returns product of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesConstantInt") - public operator fun C.times(other: Int): C - - /** - * Returns sum of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to adding [this] copies of unit of underlying ring to [other]. - */ - @JvmName("plusIntConstant") - public operator fun Int.plus(other: C): C - /** - * Returns difference between the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit of underlying ring from [other]. - */ - @JvmName("minusIntConstant") - public operator fun Int.minus(other: C): C - /** - * Returns product of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntConstant") - public operator fun Int.times(other: C): C - - /** - * Converts the integer [value] to constant. - */ - public fun constantNumber(value: Int): C = constantOne * value - /** - * Converts the integer to constant. - */ - public fun Int.asConstant(): C = constantNumber(this) - - /** - * Returns sum of the constant and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - @JvmName("plusPolynomialInt") - public operator fun P.plus(other: Int): P - /** - * Returns difference between the constant and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - @JvmName("minusPolynomialInt") - public operator fun P.minus(other: Int): P - /** - * Returns product of the constant and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesPolynomialInt") - public operator fun P.times(other: Int): P - - /** - * Returns sum of the integer represented as a polynomial and the constant. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - @JvmName("plusIntPolynomial") - public operator fun Int.plus(other: P): P - /** - * Returns difference between the integer represented as a polynomial and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - @JvmName("minusIntPolynomial") - public operator fun Int.minus(other: P): P - /** - * Returns product of the integer represented as a polynomial and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntPolynomial") - public operator fun Int.times(other: P): P - - /** - * Converts the integer [value] to polynomial. - */ - public fun polynomialNumber(value: Int): P = polynomialOne * value - /** - * Converts the integer to polynomial. - */ - public fun Int.asPolynomial(): P = polynomialNumber(this) - - /** - * Returns sum of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public operator fun R.plus(other: Int): R = addMultipliedByDoubling(this, one, other) - /** - * Returns difference between the rational function and the integer represented as a rational function. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public operator fun R.minus(other: Int): R = addMultipliedByDoubling(this, one, -other) - /** - * Returns product of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public operator fun R.times(other: Int): R = multiplyByDoubling(this, other) - /** - * Returns quotient of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to creating a new rational function by preserving numerator of [this] and - * multiplication denominator of [this] to [other]. - */ - public operator fun R.div(other: Int): R = this / multiplyByDoubling(one, other) - - /** - * Returns sum of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public operator fun Int.plus(other: R): R = addMultipliedByDoubling(other, one, this) - /** - * Returns difference between the integer represented as a rational function and the rational function. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public operator fun Int.minus(other: R): R = addMultipliedByDoubling(-other, one, this) - /** - * Returns product of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public operator fun Int.times(other: R): R = multiplyByDoubling(other, this) - /** - * Returns quotient of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to creating a new rational function which numerator is [this] times denominator of - * [other] and which denominator is [other]'s numerator. - */ - public operator fun Int.div(other: R): R = multiplyByDoubling(one / other, this) - - /** - * Converts the integer [value] to rational function. - */ - public fun number(value: Int): R = one * value - /** - * Converts the integer to rational function. - */ - public fun Int.asRationalFunction(): R = number(this) - - /** - * Returns the same constant. - */ - @JvmName("unaryPlusConstant") - @JsName("unaryPlusConstant") - public operator fun C.unaryPlus(): C = this - /** - * Returns negation of the constant. - */ - @JvmName("unaryMinusConstant") - @JsName("unaryMinusConstant") - public operator fun C.unaryMinus(): C - /** - * Returns sum of the constants. - */ - @JvmName("plusConstantConstant") - @JsName("plusConstantConstant") - public operator fun C.plus(other: C): C - /** - * Returns difference of the constants. - */ - @JvmName("minusConstantConstant") - @JsName("minusConstantConstant") - public operator fun C.minus(other: C): C - /** - * Returns product of the constants. - */ - @JvmName("timesConstantConstant") - @JsName("timesConstantConstant") - public operator fun C.times(other: C): C - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerConstant") - @JsName("powerConstant") - public fun power(arg: C, exponent: UInt) : C - - /** - * Instance of zero constant (zero of the underlying ring). - */ - public val constantZero: C - /** - * Instance of unit constant (unit of the underlying ring). - */ - public val constantOne: C - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusConstantPolynomial") - public operator fun C.plus(other: P): P - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusConstantPolynomial") - public operator fun C.minus(other: P): P - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesConstantPolynomial") - public operator fun C.times(other: P): P - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusPolynomialConstant") - public operator fun P.plus(other: C): P - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusPolynomialConstant") - public operator fun P.minus(other: C): P - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesPolynomialConstant") - public operator fun P.times(other: C): P - - /** - * Converts the constant [value] to polynomial. - */ - public fun polynomialNumber(value: C): P = polynomialOne * value - /** - * Converts the constant to polynomial. - */ - public fun C.asPolynomial(): P = polynomialNumber(this) - - /** - * Returns the same polynomial. - */ - @JvmName("unaryPlusPolynomial") - public operator fun P.unaryPlus(): P = this - /** - * Returns negation of the polynomial. - */ - @JvmName("unaryMinusPolynomial") - public operator fun P.unaryMinus(): P - /** - * Returns sum of the polynomials. - */ - @JvmName("plusPolynomialPolynomial") - public operator fun P.plus(other: P): P - /** - * Returns difference of the polynomials. - */ - @JvmName("minusPolynomialPolynomial") - public operator fun P.minus(other: P): P - /** - * Returns product of the polynomials. - */ - @JvmName("timesPolynomialPolynomial") - public operator fun P.times(other: P): P - /** - * Returns quotient of the polynomials as rational function. - */ - @JvmName("divPolynomialPolynomial") - public operator fun P.div(other: P): R - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerPolynomial") - public fun power(arg: P, exponent: UInt) : P - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - public val polynomialZero: P - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - public val polynomialOne: P - - /** - * Returns sum of the constant represented as a rational function and the rational function. - */ - @JvmName("plusConstantRational") - public operator fun C.plus(other: R): R - /** - * Returns difference between the constant represented as a polynomial and the rational function. - */ - @JvmName("minusConstantRational") - public operator fun C.minus(other: R): R - /** - * Returns product of the constant represented as a polynomial and the rational function. - */ - @JvmName("timesConstantRational") - public operator fun C.times(other: R): R - /** - * Returns quotient of the constant represented as a polynomial and the rational function. - */ - @JvmName("divConstantRational") - public operator fun C.div(other: R): R - - /** - * Returns sum of the rational function and the constant represented as a rational function. - */ - @JvmName("plusRationalConstant") - public operator fun R.plus(other: C): R - /** - * Returns difference between the rational function and the constant represented as a rational function. - */ - @JvmName("minusRationalConstant") - public operator fun R.minus(other: C): R - /** - * Returns product of the rational function and the constant represented as a rational function. - */ - @JvmName("timesRationalConstant") - public operator fun R.times(other: C): R - /** - * Returns quotient of the rational function and the constant represented as a rational function. - */ - @JvmName("divRationalConstant") - public operator fun R.div(other: C): R - - /** - * Converts the constant [value] to rational function. - */ - @JvmName("numberConstant") - public fun number(value: C): R = one * value - /** - * Converts the constant to rational function. - */ - @JvmName("asRationalFunctionConstant") - public fun C.asRationalFunction(): R = number(this) - - /** - * Returns sum of the polynomial represented as a rational function and the rational function. - */ - @JvmName("plusPolynomialRational") - public operator fun P.plus(other: R): R - /** - * Returns difference between the polynomial represented as a polynomial and the rational function. - */ - @JvmName("minusPolynomialRational") - public operator fun P.minus(other: R): R - /** - * Returns product of the polynomial represented as a polynomial and the rational function. - */ - @JvmName("timesPolynomialRational") - public operator fun P.times(other: R): R - /** - * Returns quotient of the polynomial represented as a polynomial and the rational function. - */ - @JvmName("divPolynomialRational") - public operator fun P.div(other: R): R - - /** - * Returns sum of the rational function and the polynomial represented as a rational function. - */ - @JvmName("plusRationalPolynomial") - public operator fun R.plus(other: P): R - /** - * Returns difference between the rational function and the polynomial represented as a rational function. - */ - @JvmName("minusRationalPolynomial") - public operator fun R.minus(other: P): R - /** - * Returns product of the rational function and the polynomial represented as a rational function. - */ - @JvmName("timesRationalPolynomial") - public operator fun R.times(other: P): R - /** - * Returns quotient of the rational function and the polynomial represented as a rational function. - */ - @JvmName("divRationalPolynomial") - public operator fun R.div(other: P): R - - /** - * Converts the polynomial [value] to rational function. - */ - @JvmName("numberPolynomial") - public fun number(value: P): R = one * value - /** - * Converts the polynomial to rational function. - */ - @JvmName("asRationalFunctionPolynomial") - public fun P.asRationalFunction(): R = number(this) - - /** - * Returns the same rational function. - */ - public override operator fun R.unaryPlus(): R = this - /** - * Returns negation of the rational function. - */ - public override operator fun R.unaryMinus(): R - /** - * Returns sum of the rational functions. - */ - public override operator fun R.plus(other: R): R - /** - * Returns difference of the rational functions. - */ - public override operator fun R.minus(other: R): R - /** - * Returns product of the rational functions. - */ - public override operator fun R.times(other: R): R - /** - * Returns quotient of the rational functions. - */ - public operator fun R.div(other: R): R - /** - * Raises [arg] to the integer power [exponent]. - */ - public override fun power(arg: R, exponent: UInt) : R = exponentiateBySquaring(arg, exponent) - - /** - * Instance of zero rational function (zero of the rational functions ring). - */ - public override val zero: R - /** - * Instance of unit polynomial (unit of the rational functions ring). - */ - public override val one: R - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public val P.degree: Int - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public val R.numeratorDegree: Int get() = numerator.degree - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public val R.denominatorDegree: Int get() = denominator.degree - - override fun add(left: R, right: R): R = left + right - override fun multiply(left: R, right: R): R = left * right -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] and constants of type - * [C]. It also assumes that there is provided [ring] (of type [A]), that provides constant-wise operations. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - * @param A the type of algebraic structure (precisely, of ring) provided for constants. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface RationalFunctionSpaceOverRing< - C, - P, - R: RationalFunction, - out A: Ring - > : RationalFunctionSpace { - - /** - * Underlying ring of constants. Its operations on constants are inherited by local operations on constants. - */ - public val ring: A - - /** - * Returns sum of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to adding [other] copies of unit of underlying ring to [this]. - */ - @JvmName("plusConstantInt") - public override operator fun C.plus(other: Int): C = ring { addMultipliedByDoubling(this@plus, one, other) } - /** - * Returns difference between the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to subtraction [other] copies of unit of underlying ring from [this]. - */ - @JvmName("minusConstantInt") - public override operator fun C.minus(other: Int): C = ring { addMultipliedByDoubling(this@minus, one, -other) } - /** - * Returns product of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesConstantInt") - public override operator fun C.times(other: Int): C = ring { multiplyByDoubling(this@times, other) } - - /** - * Returns sum of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to adding [this] copies of unit of underlying ring to [other]. - */ - @JvmName("plusIntConstant") - public override operator fun Int.plus(other: C): C = ring { addMultipliedByDoubling(other, one, this@plus) } - /** - * Returns difference between the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit of underlying ring from [other]. - */ - @JvmName("minusIntConstant") - public override operator fun Int.minus(other: C): C = ring { addMultipliedByDoubling(-other, one, this@minus) } - /** - * Returns product of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntConstant") - public override operator fun Int.times(other: C): C = ring { multiplyByDoubling(other, this@times) } - - /** - * Returns the same constant. - */ - @JvmName("unaryPlusConstant") - public override operator fun C.unaryPlus(): C = ring { +this@unaryPlus } - /** - * Returns negation of the constant. - */ - @JvmName("unaryMinusConstant") - public override operator fun C.unaryMinus(): C = ring { -this@unaryMinus } - /** - * Returns sum of the constants. - */ - @JvmName("plusConstantConstant") - public override operator fun C.plus(other: C): C = ring { this@plus + other } - /** - * Returns difference of the constants. - */ - @JvmName("minusConstantConstant") - public override operator fun C.minus(other: C): C = ring { this@minus - other } - /** - * Returns product of the constants. - */ - @JvmName("timesConstantConstant") - public override operator fun C.times(other: C): C = ring { this@times * other } - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerConstant") - public override fun power(arg: C, exponent: UInt) : C = ring { power(arg, exponent) } - - /** - * Instance of zero constant (zero of the underlying ring). - */ - public override val constantZero: C get() = ring.zero - /** - * Instance of unit constant (unit of the underlying ring). - */ - public override val constantOne: C get() = ring.one -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] and constants of type - * [C]. It also assumes that there is provided [polynomialRing] (of type [AP]), that provides constant- and - * polynomial-wise operations. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - * @param AP the type of algebraic structure (precisely, of ring) provided for polynomials. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface RationalFunctionSpaceOverPolynomialSpace< - C, - P, - R: RationalFunction, - out AP: PolynomialSpace, - > : RationalFunctionSpace { - - /** - * Underlying polynomial ring. Its polynomial operations are inherited by local polynomial operations. - */ - public val polynomialRing: AP - - /** - * Returns sum of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to adding [other] copies of unit of underlying ring to [this]. - */ - @JvmName("plusConstantInt") - public override operator fun C.plus(other: Int): C = polynomialRing { this@plus + other } - /** - * Returns difference between the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to subtraction [other] copies of unit of underlying ring from [this]. - */ - @JvmName("minusConstantInt") - public override operator fun C.minus(other: Int): C = polynomialRing { this@minus - other } - /** - * Returns product of the constant and the integer represented as a constant (member of underlying ring). - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesConstantInt") - public override operator fun C.times(other: Int): C = polynomialRing { this@times * other } - - /** - * Returns sum of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to adding [this] copies of unit of underlying ring to [other]. - */ - @JvmName("plusIntConstant") - public override operator fun Int.plus(other: C): C = polynomialRing { this@plus + other } - /** - * Returns difference between the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit of underlying ring from [other]. - */ - @JvmName("minusIntConstant") - public override operator fun Int.minus(other: C): C = polynomialRing { this@minus - other } - /** - * Returns product of the integer represented as a constant (member of underlying ring) and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntConstant") - public override operator fun Int.times(other: C): C = polynomialRing { this@times * other } - - /** - * Converts the integer [value] to constant. - */ - public override fun constantNumber(value: Int): C = polynomialRing { constantNumber(value) } - /** - * Converts the integer to constant. - */ - override fun Int.asConstant(): C = polynomialRing { asConstant() } - - /** - * Returns sum of the constant and the integer represented as a polynomial. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - @JvmName("plusPolynomialInt") - public override operator fun P.plus(other: Int): P = polynomialRing { this@plus + other } - /** - * Returns difference between the constant and the integer represented as a polynomial. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - @JvmName("minusPolynomialInt") - public override operator fun P.minus(other: Int): P = polynomialRing { this@minus - other } - /** - * Returns product of the constant and the integer represented as a polynomial. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - @JvmName("timesPolynomialInt") - public override operator fun P.times(other: Int): P = polynomialRing { this@times * other } - - /** - * Returns sum of the integer represented as a polynomial and the constant. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - @JvmName("plusIntPolynomial") - public override operator fun Int.plus(other: P): P = polynomialRing { this@plus + other } - /** - * Returns difference between the integer represented as a polynomial and the constant. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - @JvmName("minusIntPolynomial") - public override operator fun Int.minus(other: P): P = polynomialRing { this@minus - other } - /** - * Returns product of the integer represented as a polynomial and the constant. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - @JvmName("timesIntPolynomial") - public override operator fun Int.times(other: P): P = polynomialRing { this@times * other } - - /** - * Converts the integer [value] to polynomial. - */ - public override fun polynomialNumber(value: Int): P = polynomialRing { number(value) } - /** - * Converts the integer to polynomial. - */ - public override fun Int.asPolynomial(): P = polynomialRing { asPolynomial() } - - /** - * Returns the same constant. - */ - @JvmName("unaryPlusConstant") - public override operator fun C.unaryPlus(): C = polynomialRing { +this@unaryPlus } - /** - * Returns negation of the constant. - */ - @JvmName("unaryMinusConstant") - public override operator fun C.unaryMinus(): C = polynomialRing { -this@unaryMinus } - /** - * Returns sum of the constants. - */ - @JvmName("plusConstantConstant") - public override operator fun C.plus(other: C): C = polynomialRing { this@plus + other } - /** - * Returns difference of the constants. - */ - @JvmName("minusConstantConstant") - public override operator fun C.minus(other: C): C = polynomialRing { this@minus - other } - /** - * Returns product of the constants. - */ - @JvmName("timesConstantConstant") - public override operator fun C.times(other: C): C = polynomialRing { this@times * other } - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerConstant") - public override fun power(arg: C, exponent: UInt) : C = polynomialRing { power(arg, exponent) } - - /** - * Instance of zero constant (zero of the underlying ring). - */ - public override val constantZero: C get() = polynomialRing.constantZero - /** - * Instance of unit constant (unit of the underlying ring). - */ - public override val constantOne: C get() = polynomialRing.constantOne - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusConstantPolynomial") - public override operator fun C.plus(other: P): P = polynomialRing { this@plus + other } - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusConstantPolynomial") - public override operator fun C.minus(other: P): P = polynomialRing { this@minus - other } - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesConstantPolynomial") - public override operator fun C.times(other: P): P = polynomialRing { this@times * other } - - /** - * Returns sum of the constant represented as a polynomial and the polynomial. - */ - @JvmName("plusPolynomialConstant") - public override operator fun P.plus(other: C): P = polynomialRing { this@plus + other } - /** - * Returns difference between the constant represented as a polynomial and the polynomial. - */ - @JvmName("minusPolynomialConstant") - public override operator fun P.minus(other: C): P = polynomialRing { this@minus - other } - /** - * Returns product of the constant represented as a polynomial and the polynomial. - */ - @JvmName("timesPolynomialConstant") - public override operator fun P.times(other: C): P = polynomialRing { this@times * other } - - /** - * Converts the constant [value] to polynomial. - */ - public override fun polynomialNumber(value: C): P = polynomialRing { number(value) } - /** - * Converts the constant to polynomial. - */ - public override fun C.asPolynomial(): P = polynomialRing { asPolynomial() } - - /** - * Returns the same polynomial. - */ - @JvmName("unaryPlusPolynomial") - public override operator fun P.unaryPlus(): P = polynomialRing { +this@unaryPlus } - /** - * Returns negation of the polynomial. - */ - @JvmName("unaryMinusPolynomial") - public override operator fun P.unaryMinus(): P = polynomialRing { -this@unaryMinus } - /** - * Returns sum of the polynomials. - */ - @JvmName("plusPolynomialPolynomial") - public override operator fun P.plus(other: P): P = polynomialRing { this@plus + other } - /** - * Returns difference of the polynomials. - */ - @JvmName("minusPolynomialPolynomial") - public override operator fun P.minus(other: P): P = polynomialRing { this@minus - other } - /** - * Returns product of the polynomials. - */ - @JvmName("timesPolynomialPolynomial") - public override operator fun P.times(other: P): P = polynomialRing { this@times * other } - /** - * Raises [arg] to the integer power [exponent]. - */ - @JvmName("powerPolynomial") - public override fun power(arg: P, exponent: UInt) : P = polynomialRing { power(arg, exponent) } - - /** - * Instance of zero polynomial (zero of the polynomial ring). - */ - public override val polynomialZero: P get() = polynomialRing.zero - /** - * Instance of unit polynomial (unit of the polynomial ring). - */ - public override val polynomialOne: P get() = polynomialRing.one - - /** - * Degree of the polynomial, [see also](https://en.wikipedia.org/wiki/Degree_of_a_polynomial). If the polynomial is - * zero, degree is -1. - */ - public override val P.degree: Int get() = polynomialRing { this@degree.degree } -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] and constants of type - * [C]. It also assumes that there is provided constructor [constructRationalFunction] of rational functions from - * polynomial numerator and denominator. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public abstract class PolynomialSpaceOfFractions< - C, - P, - R: RationalFunction, - > : RationalFunctionSpace { - - /** - * Constructor of rational functions (of type [R]) from numerator and denominator (of type [P]). - */ - protected abstract fun constructRationalFunction(numerator: P, denominator: P = polynomialOne) : R - - /** - * Returns sum of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to adding [other] copies of unit polynomial to [this]. - */ - public override operator fun R.plus(other: Int): R = - constructRationalFunction( - numerator + denominator * other, - denominator - ) - /** - * Returns difference between the rational function and the integer represented as a rational function. - * - * The operation is equivalent to subtraction [other] copies of unit polynomial from [this]. - */ - public override operator fun R.minus(other: Int): R = - constructRationalFunction( - numerator - denominator * other, - denominator - ) - /** - * Returns product of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to sum of [other] copies of [this]. - */ - public override operator fun R.times(other: Int): R = - constructRationalFunction( - numerator * other, - denominator - ) - /** - * Returns quotient of the rational function and the integer represented as a rational function. - * - * The operation is equivalent to creating a new rational function by preserving numerator of [this] and - * multiplication denominator of [this] to [other]. - */ - public override operator fun R.div(other: Int): R = - constructRationalFunction( - numerator, - denominator * other - ) - - /** - * Returns sum of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to adding [this] copies of unit polynomial to [other]. - */ - public override operator fun Int.plus(other: R): R = - constructRationalFunction( - other.denominator * this + other.numerator, - other.denominator - ) - /** - * Returns difference between the integer represented as a rational function and the rational function. - * - * The operation is equivalent to subtraction [this] copies of unit polynomial from [other]. - */ - public override operator fun Int.minus(other: R): R = - constructRationalFunction( - other.denominator * this - other.numerator, - other.denominator - ) - /** - * Returns product of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to sum of [this] copies of [other]. - */ - public override operator fun Int.times(other: R): R = - constructRationalFunction( - this * other.numerator, - other.denominator - ) - /** - * Returns quotient of the integer represented as a rational function and the rational function. - * - * The operation is equivalent to creating a new rational function which numerator is [this] times denominator of - * [other] and which denominator is [other]'s numerator. - */ - public override operator fun Int.div(other: R): R = - constructRationalFunction( - this * other.denominator, - other.numerator - ) - - /** - * Converts the integer [value] to rational function. - */ - public override fun number(value: Int): R = constructRationalFunction(polynomialNumber(value)) - - /** - * Returns quotient of the polynomials as rational function. - */ - @JvmName("divPolynomialPolynomial") - public override operator fun P.div(other: P): R = constructRationalFunction(this, other) - - /** - * Returns sum of the constant represented as a rational function and the rational function. - */ - @JvmName("plusConstantRational") - public override operator fun C.plus(other: R): R = - constructRationalFunction( - other.denominator * this + other.numerator, - other.denominator - ) - /** - * Returns difference between the constant represented as a polynomial and the rational function. - */ - @JvmName("minusConstantRational") - public override operator fun C.minus(other: R): R = - constructRationalFunction( - other.denominator * this - other.numerator, - other.denominator - ) - /** - * Returns product of the constant represented as a polynomial and the rational function. - */ - @JvmName("timesConstantRational") - public override operator fun C.times(other: R): R = - constructRationalFunction( - this * other.numerator, - other.denominator - ) - /** - * Returns quotient of the constant represented as a polynomial and the rational function. - */ - @JvmName("divConstantRational") - public override operator fun C.div(other: R): R = - constructRationalFunction( - this * other.denominator, - other.numerator - ) - - /** - * Returns sum of the constant represented as a rational function and the rational function. - */ - @JvmName("plusRationalConstant") - public override operator fun R.plus(other: C): R = - constructRationalFunction( - numerator + denominator * other, - denominator - ) - /** - * Returns difference between the constant represented as a rational function and the rational function. - */ - @JvmName("minusRationalConstant") - public override operator fun R.minus(other: C): R = - constructRationalFunction( - numerator - denominator * other, - denominator - ) - /** - * Returns product of the constant represented as a rational function and the rational function. - */ - @JvmName("timesRationalConstant") - public override operator fun R.times(other: C): R = - constructRationalFunction( - numerator * other, - denominator - ) - /** - * Returns quotient of the rational function and the constant represented as a rational function. - */ - @JvmName("divRationalConstant") - public override operator fun R.div(other: C): R = - constructRationalFunction( - numerator, - denominator * other - ) - - /** - * Converts the constant [value] to rational function. - */ - @JvmName("numberConstant") - public override fun number(value: C): R = constructRationalFunction(polynomialNumber(value)) - - /** - * Returns sum of the polynomial represented as a rational function and the rational function. - */ - @JvmName("plusPolynomialRational") - public override operator fun P.plus(other: R): R = - constructRationalFunction( - other.denominator * this + other.numerator, - other.denominator - ) - /** - * Returns difference between the polynomial represented as a polynomial and the rational function. - */ - @JvmName("minusPolynomialRational") - public override operator fun P.minus(other: R): R = - constructRationalFunction( - other.denominator * this - other.numerator, - other.denominator - ) - /** - * Returns product of the polynomial represented as a polynomial and the rational function. - */ - @JvmName("timesPolynomialRational") - public override operator fun P.times(other: R): R = - constructRationalFunction( - this * other.numerator, - other.denominator - ) - /** - * Returns quotient of the polynomial represented as a polynomial and the rational function. - */ - @JvmName("divPolynomialRational") - public override operator fun P.div(other: R): R = - constructRationalFunction( - this * other.denominator, - other.numerator - ) - - /** - * Returns sum of the polynomial represented as a rational function and the rational function. - */ - @JvmName("plusRationalPolynomial") - public override operator fun R.plus(other: P): R = - constructRationalFunction( - numerator + denominator * other, - denominator - ) - /** - * Returns difference between the polynomial represented as a rational function and the rational function. - */ - @JvmName("minusRationalPolynomial") - public override operator fun R.minus(other: P): R = - constructRationalFunction( - numerator - denominator * other, - denominator - ) - /** - * Returns product of the polynomial represented as a rational function and the rational function. - */ - @JvmName("timesRationalPolynomial") - public override operator fun R.times(other: P): R = - constructRationalFunction( - numerator * other, - denominator - ) - /** - * Returns quotient of the rational function and the polynomial represented as a rational function. - */ - @JvmName("divRationalPolynomial") - public override operator fun R.div(other: P): R = - constructRationalFunction( - numerator, - denominator * other - ) - - /** - * Converts the polynomial [value] to rational function. - */ - @JvmName("numberPolynomial") - public override fun number(value: P): R = constructRationalFunction(value) - - /** - * Returns negation of the rational function. - */ - public override operator fun R.unaryMinus(): R = constructRationalFunction(-numerator, denominator) - /** - * Returns sum of the rational functions. - */ - public override operator fun R.plus(other: R): R = - constructRationalFunction( - numerator * other.denominator + denominator * other.numerator, - denominator * other.denominator - ) - /** - * Returns difference of the rational functions. - */ - public override operator fun R.minus(other: R): R = - constructRationalFunction( - numerator * other.denominator - denominator * other.numerator, - denominator * other.denominator - ) - /** - * Returns product of the rational functions. - */ - public override operator fun R.times(other: R): R = - constructRationalFunction( - numerator * other.numerator, - denominator * other.denominator - ) - /** - * Returns quotient of the rational functions. - */ - public override operator fun R.div(other: R): R = - constructRationalFunction( - numerator * other.denominator, - denominator * other.numerator - ) - /** - * Raises [arg] to the integer power [exponent]. - */ - public override fun power(arg: R, exponent: UInt): R = - constructRationalFunction( - power(arg.numerator, exponent), - power(arg.denominator, exponent), - ) - - /** - * Instance of zero rational function (zero of the rational functions ring). - */ - public override val zero: R by lazy { constructRationalFunction(polynomialZero) } - - /** - * Instance of unit polynomial (unit of the rational functions ring). - */ - public override val one: R by lazy { constructRationalFunction(polynomialOne) } -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] of variables of type - * [V] and over ring of constants of type [C]. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param V the type of variables. Polynomials have them in representations of terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface MultivariateRationalFunctionSpace< - C, - V, - P, - R: RationalFunction - >: RationalFunctionSpace { - /** - * Returns sum of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("plusVariableInt") - @JsName("plusVariableInt") - public operator fun V.plus(other: Int): P - /** - * Returns difference between the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("minusVariableInt") - @JsName("minusVariableInt") - public operator fun V.minus(other: Int): P - /** - * Returns product of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("timesVariableInt") - @JsName("timesVariableInt") - public operator fun V.times(other: Int): P - - /** - * Returns sum of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusIntVariable") - @JsName("plusIntVariable") - public operator fun Int.plus(other: V): P - /** - * Returns difference between the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusIntVariable") - @JsName("minusIntVariable") - public operator fun Int.minus(other: V): P - /** - * Returns product of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesIntVariable") - @JsName("timesIntVariable") - public operator fun Int.times(other: V): P - - /** - * Returns sum of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("plusVariableConstant") - @JsName("plusVariableConstant") - public operator fun V.plus(other: C): P - /** - * Returns difference between the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("minusVariableConstant") - @JsName("minusVariableConstant") - public operator fun V.minus(other: C): P - /** - * Returns product of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("timesVariableConstant") - @JsName("timesVariableConstant") - public operator fun V.times(other: C): P - - /** - * Returns sum of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusConstantVariable") - @JsName("plusConstantVariable") - public operator fun C.plus(other: V): P - /** - * Returns difference between the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusConstantVariable") - @JsName("minusConstantVariable") - public operator fun C.minus(other: V): P - /** - * Returns product of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesConstantVariable") - @JsName("timesConstantVariable") - public operator fun C.times(other: V): P - - /** - * Represents the variable as a monic monomial. - */ - @JvmName("unaryPlusVariable") - @JsName("unaryPlusVariable") - public operator fun V.unaryPlus(): P - /** - * Returns negation of representation of the variable as a monic monomial. - */ - @JvmName("unaryMinusVariable") - @JsName("unaryMinusVariable") - public operator fun V.unaryMinus(): P - /** - * Returns sum of the variables represented as monic monomials. - */ - @JvmName("plusVariableVariable") - @JsName("plusVariableVariable") - public operator fun V.plus(other: V): P - /** - * Returns difference between the variables represented as monic monomials. - */ - @JvmName("minusVariableVariable") - @JsName("minusVariableVariable") - public operator fun V.minus(other: V): P - /** - * Returns product of the variables represented as monic monomials. - */ - @JvmName("timesVariableVariable") - @JsName("timesVariableVariable") - public operator fun V.times(other: V): P - - /** - * Represents the [variable] as a monic monomial. - */ - @JvmName("polynomialNumberVariable") - public fun polynomialNumber(variable: V): P = +variable - /** - * Represents the variable as a monic monomial. - */ - @JvmName("asPolynomialVariable") - public fun V.asPolynomial(): P = polynomialNumber(this) - - /** - * Represents the [variable] as a rational function. - */ - @JvmName("numberVariable") - @JsName("numberVariable") - public fun number(variable: V): R = number(polynomialNumber(variable)) - /** - * Represents the variable as a rational function. - */ - @JvmName("asRationalFunctionVariable") - @JsName("asRationalFunctionVariable") - public fun V.asRationalFunction(): R = number(this) - - /** - * Returns sum of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("plusVariablePolynomial") - public operator fun V.plus(other: P): P - /** - * Returns difference between the variable represented as a monic monomial and the polynomial. - */ - @JvmName("minusVariablePolynomial") - public operator fun V.minus(other: P): P - /** - * Returns product of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("timesVariablePolynomial") - public operator fun V.times(other: P): P - - /** - * Returns sum of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusPolynomialVariable") - public operator fun P.plus(other: V): P - /** - * Returns difference between the polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusPolynomialVariable") - public operator fun P.minus(other: V): P - /** - * Returns product of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesPolynomialVariable") - public operator fun P.times(other: V): P - - /** - * Returns sum of the variable represented as a rational function and the rational function. - */ - @JvmName("plusVariableRational") - public operator fun V.plus(other: R): R - /** - * Returns difference between the variable represented as a rational function and the rational function. - */ - @JvmName("minusVariableRational") - public operator fun V.minus(other: R): R - /** - * Returns product of the variable represented as a rational function and the rational function. - */ - @JvmName("timesVariableRational") - public operator fun V.times(other: R): R - - /** - * Returns sum of the rational function and the variable represented as a rational function. - */ - @JvmName("plusRationalVariable") - public operator fun R.plus(other: V): R - /** - * Returns difference between the rational function and the variable represented as a rational function. - */ - @JvmName("minusRationalVariable") - public operator fun R.minus(other: V): R - /** - * Returns product of the rational function and the variable represented as a rational function. - */ - @JvmName("timesRationalVariable") - public operator fun R.times(other: V): R - - /** - * Map that associates variables (that appear in the polynomial in positive exponents) with their most exponents - * in which they are appeared in the polynomial. - * - * As consequence all values in the map are positive integers. Also, if the polynomial is constant, the map is empty. - * And keys of the map is the same as in [variables]. - */ - public val P.degrees: Map - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public fun P.degreeBy(variable: V): UInt = degrees.getOrElse(variable) { 0u } - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public fun P.degreeBy(variables: Collection): UInt - /** - * Set of all variables that appear in the polynomial in positive exponents. - */ - public val P.variables: Set get() = degrees.keys - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public val P.countOfVariables: Int get() = variables.size - - /** - * Set of all variables that appear in the polynomial in positive exponents. - */ - public val R.variables: Set get() = numerator.variables union denominator.variables - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public val R.countOfVariables: Int get() = variables.size -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] of variables of type - * [V] and over ring of constants of type [C]. It also assumes that there is provided [polynomialRing] (of type [AP]), - * that provides constant-, variable- and polynomial-wise operations. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param V the type of variables. Polynomials have them in representations of terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - * @param AP the type of algebraic structure (precisely, of ring) provided for polynomials. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public interface MultivariateRationalFunctionSpaceOverMultivariatePolynomialSpace< - C, - V, - P, - R: RationalFunction, - out AP: MultivariatePolynomialSpace, - > : RationalFunctionSpaceOverPolynomialSpace, MultivariateRationalFunctionSpace { - /** - * Returns sum of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("plusVariableInt") - public override operator fun V.plus(other: Int): P = polynomialRing { this@plus + other } - /** - * Returns difference between the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("minusVariableInt") - public override operator fun V.minus(other: Int): P = polynomialRing { this@minus - other } - /** - * Returns product of the variable represented as a monic monomial and the integer represented as a constant polynomial. - */ - @JvmName("timesVariableInt") - public override operator fun V.times(other: Int): P = polynomialRing { this@times * other } - - /** - * Returns sum of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusIntVariable") - public override operator fun Int.plus(other: V): P = polynomialRing { this@plus + other } - /** - * Returns difference between the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusIntVariable") - public override operator fun Int.minus(other: V): P = polynomialRing { this@minus - other } - /** - * Returns product of the integer represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesIntVariable") - public override operator fun Int.times(other: V): P = polynomialRing { this@times * other } - - /** - * Returns sum of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("plusVariableConstant") - public override operator fun V.plus(other: C): P = polynomialRing { this@plus + other } - /** - * Returns difference between the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("minusVariableConstant") - public override operator fun V.minus(other: C): P = polynomialRing { this@minus - other } - /** - * Returns product of the variable represented as a monic monomial and the constant represented as a constant polynomial. - */ - @JvmName("timesVariableConstant") - public override operator fun V.times(other: C): P = polynomialRing { this@times * other } - - /** - * Returns sum of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusConstantVariable") - public override operator fun C.plus(other: V): P = polynomialRing { this@plus + other } - /** - * Returns difference between the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusConstantVariable") - public override operator fun C.minus(other: V): P = polynomialRing { this@minus - other } - /** - * Returns product of the constant represented as a constant polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesConstantVariable") - public override operator fun C.times(other: V): P = polynomialRing { this@times * other } - - /** - * Represents the variable as a monic monomial. - */ - @JvmName("unaryPlusVariable") - public override operator fun V.unaryPlus(): P = polynomialRing { +this@unaryPlus } - /** - * Returns negation of representation of the variable as a monic monomial. - */ - @JvmName("unaryMinusVariable") - public override operator fun V.unaryMinus(): P = polynomialRing { -this@unaryMinus } - /** - * Returns sum of the variables represented as monic monomials. - */ - @JvmName("plusVariableVariable") - public override operator fun V.plus(other: V): P = polynomialRing { this@plus + other } - /** - * Returns difference between the variables represented as monic monomials. - */ - @JvmName("minusVariableVariable") - public override operator fun V.minus(other: V): P = polynomialRing { this@minus - other } - /** - * Returns product of the variables represented as monic monomials. - */ - @JvmName("timesVariableVariable") - public override operator fun V.times(other: V): P = polynomialRing { this@times * other } - - /** - * Represents the [variable] as a monic monomial. - */ - @JvmName("polynomialNumberVariable") - public override fun polynomialNumber(variable: V): P = polynomialRing { number(variable) } - /** - * Represents the variable as a monic monomial. - */ - @JvmName("asPolynomialVariable") - public override fun V.asPolynomial(): P = polynomialRing { this@asPolynomial.asPolynomial() } - - /** - * Returns sum of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("plusVariablePolynomial") - public override operator fun V.plus(other: P): P = polynomialRing { this@plus + other } - /** - * Returns difference between the variable represented as a monic monomial and the polynomial. - */ - @JvmName("minusVariablePolynomial") - public override operator fun V.minus(other: P): P = polynomialRing { this@minus - other } - /** - * Returns product of the variable represented as a monic monomial and the polynomial. - */ - @JvmName("timesVariablePolynomial") - public override operator fun V.times(other: P): P = polynomialRing { this@times * other } - - /** - * Returns sum of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("plusPolynomialVariable") - public override operator fun P.plus(other: V): P = polynomialRing { this@plus + other } - /** - * Returns difference between the polynomial and the variable represented as a monic monomial. - */ - @JvmName("minusPolynomialVariable") - public override operator fun P.minus(other: V): P = polynomialRing { this@minus - other } - /** - * Returns product of the polynomial and the variable represented as a monic monomial. - */ - @JvmName("timesPolynomialVariable") - public override operator fun P.times(other: V): P = polynomialRing { this@times * other } - - /** - * Map that associates variables (that appear in the polynomial in positive exponents) with their most exponents - * in which they are appeared in the polynomial. - * - * As consequence all values in the map are positive integers. Also, if the polynomial is constant, the map is empty. - * And keys of the map is the same as in [variables]. - */ - public override val P.degrees: Map get() = polynomialRing { degrees } - /** - * Counts degree of the polynomial by the specified [variable]. - */ - public override fun P.degreeBy(variable: V): UInt = polynomialRing { degreeBy(variable) } - /** - * Counts degree of the polynomial by the specified [variables]. - */ - public override fun P.degreeBy(variables: Collection): UInt = polynomialRing { degreeBy(variables) } - /** - * Set of all variables that appear in the polynomial in positive exponents. - */ - public override val P.variables: Set get() = polynomialRing { variables } - /** - * Count of all variables that appear in the polynomial in positive exponents. - */ - public override val P.countOfVariables: Int get() = polynomialRing { countOfVariables } -} - -/** - * Abstraction of field of rational functions of type [R] with respect to polynomials of type [P] of variables of type - * [V] and over ring of constants of type [C]. It also assumes that there is provided constructor - * [constructRationalFunction] of rational functions from polynomial numerator and denominator. - * - * @param C the type of constants. Polynomials have them as coefficients in their terms. - * @param V the type of variables. Polynomials have them in representations of terms. - * @param P the type of polynomials. Rational functions have them as numerators and denominators in them. - * @param R the type of rational functions. - */ -@Suppress("INAPPLICABLE_JVM_NAME") // FIXME: Waiting for KT-31420 -public abstract class MultivariatePolynomialSpaceOfFractions< - C, - V, - P, - R: RationalFunction, - > : MultivariateRationalFunctionSpace, PolynomialSpaceOfFractions() { - /** - * Returns sum of the variable represented as a rational function and the rational function. - */ - @JvmName("plusVariableRational") - public override operator fun V.plus(other: R): R = - constructRationalFunction( - this * other.denominator + other.numerator, - other.denominator - ) - /** - * Returns difference between the variable represented as a rational function and the rational function. - */ - @JvmName("minusVariableRational") - public override operator fun V.minus(other: R): R = - constructRationalFunction( - this * other.denominator - other.numerator, - other.denominator - ) - /** - * Returns product of the variable represented as a rational function and the rational function. - */ - @JvmName("timesVariableRational") - public override operator fun V.times(other: R): R = - constructRationalFunction( - this * other.numerator, - other.denominator - ) - - /** - * Returns sum of the rational function and the variable represented as a rational function. - */ - @JvmName("plusRationalVariable") - public override operator fun R.plus(other: V): R = - constructRationalFunction( - numerator + denominator * other, - denominator - ) - /** - * Returns difference between the rational function and the variable represented as a rational function. - */ - @JvmName("minusRationalVariable") - public override operator fun R.minus(other: V): R = - constructRationalFunction( - numerator - denominator * other, - denominator - ) - /** - * Returns product of the rational function and the variable represented as a rational function. - */ - public override operator fun R.times(other: V): R = - constructRationalFunction( - numerator * other, - denominator - ) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/algebraicStub.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/algebraicStub.kt deleted file mode 100644 index b40aa4775..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/algebraicStub.kt +++ /dev/null @@ -1,146 +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.functions - -import space.kscience.kmath.operations.* - - -// TODO: All of this should be moved to algebraic structures' place for utilities -// FIXME: Move receiver to context receiver -/** - * Returns product of [arg] and integer [multiplier]. - * - * @param arg the multiplicand. - * @param multiplier the integer multiplier. - * @return product of the multiplicand [arg] and the multiplier [multiplier]. - * @author Gleb Minaev - */ -internal fun Group.multiplyByDoubling(arg: C, multiplier: Int): C = - if (multiplier >= 0) multiplyByDoubling(arg, multiplier.toUInt()) - else multiplyByDoubling(-arg, (-multiplier).toUInt()) - -// FIXME: Move receiver to context receiver -/** - * Adds product of [arg] and [multiplier] to [base]. - * - * @param base the augend. - * @param arg the multiplicand. - * @param multiplier the integer multiplier. - * @return sum of the augend [base] and product of the multiplicand [arg] and the multiplier [multiplier]. - * @author Gleb Minaev - */ -internal fun GroupOps.addMultipliedByDoubling(base: C, arg: C, multiplier: Int): C = - if (multiplier >= 0) addMultipliedByDoubling(base, arg, multiplier.toUInt()) - else addMultipliedByDoubling(base, -arg, (-multiplier).toUInt()) - -// FIXME: Move receiver to context receiver -/** - * Returns product of [arg] and integer [multiplier]. - * - * This is implementation of variation of [exponentiation by squaring](https://en.wikipedia.org/wiki/Exponentiation_by_squaring) - * - * @param arg the multiplicand. - * @param multiplier the integer multiplier. - * @return product of the multiplicand [arg] and the multiplier [multiplier]. - * @author Gleb Minaev - */ -internal tailrec fun Group.multiplyByDoubling(arg: C, multiplier: UInt): C = - when { - multiplier == 0u -> zero - multiplier == 1u -> arg - multiplier and 1u == 0u -> multiplyByDoubling(arg + arg, multiplier shr 1) - multiplier and 1u == 1u -> addMultipliedByDoubling(arg, arg + arg, multiplier shr 1) - else -> error("Error in multiplication group instant by unsigned integer: got reminder by division by 2 different from 0 and 1") - } - -// FIXME: Move receiver to context receiver -/** - * Adds product of [arg] and [multiplier] to [base]. - * - * This is implementation of variation of [exponentiation by squaring](https://en.wikipedia.org/wiki/Exponentiation_by_squaring) - * - * @param base the augend. - * @param arg the multiplicand. - * @param multiplier the integer multiplier. - * @return sum of the augend [base] and product of the multiplicand [arg] and the multiplier [multiplier]. - * @author Gleb Minaev - */ -internal tailrec fun GroupOps.addMultipliedByDoubling(base: C, arg: C, multiplier: UInt): C = - when { - multiplier == 0u -> base - multiplier == 1u -> base + arg - multiplier and 1u == 0u -> addMultipliedByDoubling(base, arg + arg, multiplier shr 1) - multiplier and 1u == 1u -> addMultipliedByDoubling(base + arg, arg + arg, multiplier shr 1) - else -> error("Error in multiplication group instant by unsigned integer: got reminder by division by 2 different from 0 and 1") - } - -// FIXME: Move receiver to context receiver -/** - * Raises [arg] to the integer power [exponent]. - * - * @param arg the base of the power. - * @param exponent the exponent of the power. - * @return [arg] raised to the power [exponent]. - * @author Gleb Minaev - */ -internal fun Field.exponentiateBySquaring(arg: C, exponent: Int): C = - if (exponent >= 0) exponentiateBySquaring(arg, exponent.toUInt()) - else exponentiateBySquaring(one / arg, (-exponent).toUInt()) - -// FIXME: Move receiver to context receiver -/** - * Multiplies [base] and [arg] raised to the integer power [exponent]. - * - * @param base the multiplicand. - * @param arg the base of the power. - * @param exponent the exponent of the power. - * @return product of [base] and [arg] raised to the power [exponent]. - * @author Gleb Minaev - */ -internal fun Field.multiplyExponentiatedBySquaring(base: C, arg: C, exponent: Int): C = - if (exponent >= 0) multiplyExponentiatedBySquaring(base, arg, exponent.toUInt()) - else multiplyExponentiatedBySquaring(base, one / arg, (-exponent).toUInt()) - -// FIXME: Move receiver to context receiver -/** - * Raises [arg] to the integer power [exponent]. - * - * This is implementation of variation of [exponentiation by squaring](https://en.wikipedia.org/wiki/Exponentiation_by_squaring) - * - * @param arg the base of the power. - * @param exponent the exponent of the power. - * @return [arg] raised to the power [exponent]. - * @author Gleb Minaev - */ -internal tailrec fun Ring.exponentiateBySquaring(arg: C, exponent: UInt): C = - when { - exponent == 0u -> zero - exponent == 1u -> arg - exponent and 1u == 0u -> exponentiateBySquaring(arg * arg, exponent shr 1) - exponent and 1u == 1u -> multiplyExponentiatedBySquaring(arg, arg * arg, exponent shr 1) - else -> error("Error in multiplication group instant by unsigned integer: got reminder by division by 2 different from 0 and 1") - } - -// FIXME: Move receiver to context receiver -/** - * Multiplies [base] and [arg] raised to the integer power [exponent]. - * - * This is implementation of variation of [exponentiation by squaring](https://en.wikipedia.org/wiki/Exponentiation_by_squaring) - * - * @param base the multiplicand. - * @param arg the base of the power. - * @param exponent the exponent of the power. - * @return product of [base] and [arg] raised to the power [exponent]. - * @author Gleb Minaev - */ -internal tailrec fun RingOps.multiplyExponentiatedBySquaring(base: C, arg: C, exponent: UInt): C = - when { - exponent == 0u -> base - exponent == 1u -> base * arg - exponent and 1u == 0u -> multiplyExponentiatedBySquaring(base, arg * arg, exponent shr 1) - exponent and 1u == 1u -> multiplyExponentiatedBySquaring(base * arg, arg * arg, exponent shr 1) - else -> error("Error in multiplication group instant by unsigned integer: got reminder by division by 2 different from 0 and 1") - } \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/collectionUtils.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/collectionUtils.kt deleted file mode 100644 index c9146a493..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/collectionUtils.kt +++ /dev/null @@ -1,906 +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.functions - -import kotlin.contracts.InvocationKind.* -import kotlin.contracts.contract - - -/** - * Computes the given lambda [compute] on value corresponding to the provided [key] or `null` if the key is not present. - * - * @param key key which corresponding value will be used if it's present. - * @param compute lambda that is computed on the received value. - * @return result of the computation of the lambda. - */ -internal inline fun Map.computeOn(key: K, compute: (V?) -> R): R { - contract { - callsInPlace(compute, EXACTLY_ONCE) - } - return compute(get(key)) -} - -/** - * Computes the given lambda [compute] on value corresponding to the provided [key] or computes the given lambda - * [defaultResult] if the key is not present. - * - * @param key key which corresponding value will be used if it's present. - * @param compute lambda that is computed on the value corresponding to the [key]. - * @param defaultResult lambda that is computed if the [key] is not present. - * @return result of [compute] lambda if the [key] is present or result of [defaultResult] otherwise. - */ -internal inline fun Map.computeOnOrElse(key: K, defaultResult: () -> R, compute: (value: V) -> R): R { - contract { - callsInPlace(defaultResult, AT_MOST_ONCE) - callsInPlace(compute, AT_MOST_ONCE) - } - @Suppress("UNCHECKED_CAST") - return (if (key !in this) defaultResult() else compute(get(key) as V)) -} - -/** - * Computes the given lambda [compute] on value corresponding to the provided [key] or computes the given lambda - * [defaultResult] if the key is not present. - * - * @param key key which corresponding value will be used if it's present. - * @param compute lambda that is computed on the value corresponding to the [key]. - * @param defaultResult default result that is returned in case of the [key]'s absence. - * @return result of [compute] lambda if the [key] is present or [defaultResult] otherwise. - */ -internal inline fun Map.computeOnOrElse(key: K, defaultResult: R, compute: (value: V) -> R): R { - contract { - callsInPlace(compute, AT_MOST_ONCE) - } - return computeOnOrElse(key, { defaultResult }, compute) -} - -/** - * Computes the given lambda [compute] on value corresponding to the provided [key] or computes the given lambda - * [defaultResult] if the key is not present. - * - * @param key key which corresponding value will be used if it's present. - * @param compute lambda that is computed on the value corresponding to the [key]. - * @param defaultResult default result that is returned in case of the [key]'s absence. - * @return result of [compute] lambda if the [key] is present or [defaultResult] otherwise. - */ -internal inline fun Map.computeOnOrElse(key: K, defaultResult: R, compute: (key: K, value: V) -> R): R { - contract { - callsInPlace(compute, AT_MOST_ONCE) - } - return computeOnOrElse(key, { defaultResult }, { it -> compute(key, it) }) -} - -/** - * Applies the [transformation][transform] to the value corresponding to the given [key] or null instead if it's not - * present. - * - * @param key key to check. - * @param transform transformation to apply. - * @return result of the transformation - */ -internal inline fun MutableMap.applyToKey(key: K, transform: (currentValue: V?) -> V): V { - contract { - callsInPlace(transform, EXACTLY_ONCE) - } - return computeOn(key, transform).also { this[key] = it } -} - -/** - * Depending on presence of value corresponding to the given [key] either puts new value calculated by [valueOnPut] or - * changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut lazily calculated value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value as a parameter. - * @return result value corresponding to the [key]. - */ -internal inline fun MutableMap.putOrChange(key: K, valueOnPut: () -> V, transformOnChange: (currentValue: V) -> V): V { - contract { - callsInPlace(valueOnPut, AT_MOST_ONCE) - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return computeOnOrElse(key, valueOnPut, transformOnChange).also { this[key] = it } -} - -/** - * Depending on presence of value corresponding to the given [key] either puts new value [valueOnPut] or - * changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value as a parameter. - * @return result value corresponding to the [key]. - */ -internal inline fun MutableMap.putOrChange(key: K, valueOnPut: V, transformOnChange: (currentValue: V) -> V): V { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return putOrChange(key, { valueOnPut }, transformOnChange) -} - -/** - * Depending on presence of value corresponding to the given [key] either puts new value [valueOnPut] or - * changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value and new value as parameters. - * @return result value corresponding to the [key]. - */ -internal inline fun MutableMap.putOrChange(key: K, valueOnPut: V, transformOnChange: (currentValue: V, newValue: V) -> V): V { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return putOrChange(key, { valueOnPut }, { transformOnChange(it, valueOnPut) }) -} - -/** - * Depending on presence of value corresponding to the given [key] either puts new value [valueOnPut] or - * changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * the [key], current value, and new value as parameters. - * @return result value corresponding to the [key]. - */ -internal inline fun MutableMap.putOrChange(key: K, valueOnPut: V, transformOnChange: (key: K, currentValue: V, newValue: V) -> V): V { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return putOrChange(key, { valueOnPut }, { transformOnChange(key, it, valueOnPut) }) -} - -/** - * Creates copy of [the map][this] and applies the [transformation][transform] to the value corresponding to the given - * [key] in the copy or null instead if it's not present. - * - * @param key key to check. - * @param transform transformation to apply. - * @return the copy of [the map][this]. - */ -internal inline fun Map.withAppliedToKey(key: K, transform: (currentValue: V?) -> V): Map { - contract { - callsInPlace(transform, EXACTLY_ONCE) - } - return buildMap(size) { - putAll(this) - applyToKey(key, transform) - } -} - -/** - * Creates copy of [the map][this] and depending on presence of value corresponding to the given [key] either puts new - * value calculated by [valueOnPut] or changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut lazily calculated value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value as a parameter. - * @return the copy of [the map][this]. - */ -internal inline fun Map.withPutOrChanged(key: K, valueOnPut: () -> V, transformOnChange: (currentValue: V) -> V): Map { - contract { - callsInPlace(valueOnPut, AT_MOST_ONCE) - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return buildMap(size + 1) { - putAll(this@withPutOrChanged) - putOrChange(key, valueOnPut, transformOnChange) - } -} - -/** - * Creates copy of [the map][this] and depending on presence of value corresponding to the given [key] either puts new - * value [valueOnPut] or changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value as a parameter. - * @return the copy of [the map][this]. - */ -internal inline fun Map.withPutOrChanged(key: K, valueOnPut: V, transformOnChange: (currentValue: V) -> V): Map { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return withPutOrChanged(key, { valueOnPut }, transformOnChange) -} - -/** - * Creates copy of [the map][this] and depending on presence of value corresponding to the given [key] either puts new - * value [valueOnPut] or changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * current value and new value as parameters. - * @return the copy of [the map][this]. - */ -internal inline fun Map.withPutOrChanged(key: K, valueOnPut: V, transformOnChange: (currentValue: V, newValue: V) -> V): Map { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return withPutOrChanged(key, { valueOnPut }, { transformOnChange(it, valueOnPut) }) -} - -/** - * Creates copy of [the map][this] and depending on presence of value corresponding to the given [key] either puts new - * value [valueOnPut] or changes the present value with [transformOnChange]. - * - * @param key key to check. - * @param valueOnPut value to put in case of absence of the [key]. - * @param transformOnChange transform to apply to current value corresponding to the [key] in case of its presence. Uses - * the [key], current value, and new value as parameters. - * @return the copy of [the map][this]. - */ -internal inline fun Map.withPutOrChanged(key: K, valueOnPut: V, transformOnChange: (key: K, currentValue: V, newValue: V) -> V): Map { - contract { - callsInPlace(transformOnChange, AT_MOST_ONCE) - } - return withPutOrChanged(key, { valueOnPut }, { transformOnChange(key, it, valueOnPut) }) -} - -/** - * Copies entries of [this map][this] to the [destination] map overriding present ones if needed. - * - * @receiver map to be copied. - * @param destination map to receive copies. - * @return the [destination]. - */ -internal fun > Map.copyTo(destination: D): D { - for ((key, value) in this) { - destination[key] = value - } - return destination -} - -/** - * Copies entries of [this map][this] to the [destination] map merging present entries with new ones using [resolve] - * lambda. - * - * @receiver map to be copied. - * @param destination map to receive copies. - * @param resolve lambda function that resolves overriding. It takes a key, current value corresponding to the key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyToBy(destination: D, resolve: (key: K, currentValue: W, newValue: V) -> W): D { - for ((key, value) in this) { - destination.putOrChange(key, value) { it -> resolve(key, it, value) } - } - return destination -} - -/** - * Copies entries of [this map][this] to the [destination] map merging present entries with new ones using [resolve] - * lambda. - * - * @receiver map to be copied. - * @param destination map to receive copies. - * @param resolve lambda function that resolves overriding. It takes current value corresponding to some key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyToBy(destination: D, resolve: (currentValue: W, newValue: V) -> W): D = - copyToBy(destination) { _, currentValue, newValue -> resolve(currentValue, newValue) } - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map overriding present ones if needed. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyTo(destination) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @return the [destination]. - */ -internal inline fun > Map.copyMapTo(destination: D, transform: (Map.Entry) -> W): D { - for (entry in this) { - destination[entry.key] = transform(entry) - } - return destination -} - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map overriding present ones if needed. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyTo(destination) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @return the [destination]. - */ -internal inline fun > Map.copyMapTo(destination: D, transform: (key: K, value: V) -> W): D = - copyMapTo(destination) { (key, value) -> transform(key, value) } - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map merging present entries with new ones using [resolve] lambda. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyToBy(destination, resolve) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @param resolve lambda function that resolves overriding. It takes a key, current value corresponding to the key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyMapToBy(destination: D, transform: (Map.Entry) -> W, resolve: (key: K, currentValue: W, newValue: V) -> W): D { - for (entry in this) { - val (key, value) = entry - destination.putOrChange(key, transform(entry)) { it -> resolve(key, it, value) } - } - return destination -} - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map merging present entries with new ones using [resolve] lambda. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyToBy(destination, resolve) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @param resolve lambda function that resolves overriding. It takes a key, current value corresponding to the key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyMapToBy(destination: D, transform: (key: K, value: V) -> W, resolve: (key: K, currentValue: W, newValue: V) -> W): D = - copyMapToBy(destination, { (key, value) -> transform(key, value) }, resolve) - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map merging present entries with new ones using [resolve] lambda. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyToBy(destination, resolve) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @param resolve lambda function that resolves overriding. It takes current value corresponding to some key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyMapToBy(destination: D, transform: (Map.Entry) -> W, resolve: (currentValue: W, newValue: V) -> W): D = - copyMapToBy(destination, transform, { _, currentValue, newValue -> resolve(currentValue, newValue) }) - -/** - * Transforms values of entries of [this map][this] with [the given transformation][transform] and copies resulting - * entries to the [destination] map merging present entries with new ones using [resolve] lambda. Is equivalent to - * ```kotlin - * this.mapValues(transform).copyToBy(destination, resolve) - * ``` - * - * @receiver map to be transformed and copied. - * @param destination map to receive copies. - * @param transform generates value of transformed entry using initial entry as an argument. Key of transformed entry is - * the same as initial entry. - * @param resolve lambda function that resolves overriding. It takes current value corresponding to some key, and - * a new one and returns value to associate to the key. - * @return the [destination]. - */ -internal inline fun > Map.copyMapToBy(destination: D, transform: (key: K, value: V) -> W, resolve: (currentValue: W, newValue: V) -> W): D = - copyMapToBy(destination, { (key, value) -> transform(key, value) }, { _, currentValue, newValue -> resolve(currentValue, newValue) }) - -/** - * Merges [the first map][map1] and [the second map][map2] prioritising the second one, puts result to the [destination] - * and returns the [destination]. - * - * Precisely, corresponding keys and values of the received maps are put into the destination overriding existing values - * in the [destination] if needed. For every key appearing in both maps corresponding value from the second map is - * chosen. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @param destination the map where result of the merge is put. - * @return the destination. - */ -internal fun > mergeTo(map1: Map, map2: Map, destination: D): D { - for ((key, value) in map1) { - destination.put(key, value) - } - for ((key, value) in map2) { - destination.put(key, value) - } - return destination -} - -/** - * Merges [the first map][map1] and [the second map][map2] resolving conflicts with [resolve] lambda, puts result to the - * [destination] and returns the [destination]. - * - * Precisely, corresponding keys and values of the received maps are put into the destination overriding existing values - * in the [destination] if needed. For every key appearing in both maps corresponding value is a result of the [resolve] - * lambda calculated on the key and its corresponding values from the merged maps. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @param resolve lambda function that resolves merge conflicts. - * @param destination the map where result of the merge is put. - * @return the destination. - */ -internal inline fun > mergeToBy(map1: Map, map2: Map, destination: D, resolve: (key: K, value1: V1, value2: V2) -> W): D { - for (key in map2.keys) { - destination.remove(key) - } - for ((key, value) in map1) { - destination.put(key, value) - } - for ((key, value) in map2) { - @Suppress("UNCHECKED_CAST") - destination.putOrChange(key, value) { it -> resolve(key, it as V1, value) } - } - return destination -} - -/** - * Merges [the first map][map1] and [the second map][map2] resolving conflicts with [resolve] lambda, puts result to the - * [destination] and returns the [destination]. - * - * Precisely, corresponding keys and values of the received maps are put into the destination overriding existing values - * in the [destination] if needed. For every key appearing in both maps corresponding value is a result of the [resolve] - * lambda calculated on the key's corresponding values from the merged maps. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @param resolve lambda function that resolves merge conflicts. - * @param destination the map where result of the merge is put. - * @return the destination. - */ -internal inline fun > mergeToBy(map1: Map, map2: Map, destination: D, resolve: (value1: V1, value2: V2) -> W): D = - mergeToBy(map1, map2, destination) { _, value1, value2 -> resolve(value1, value2) } - -/** - * Merges [the first map][map1] and [the second map][map2] prioritising the second one. - * - * Precisely, corresponding keys and values of the received maps are put into a new empty map which is returned after - * afterwards. For every key appearing in both maps corresponding value from the second map is chosen. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @return the result of the merge. - */ -internal fun merge(map1: Map, map2: Map): Map { - val result = LinkedHashMap(map1.size + map2.size) - return mergeTo(map1, map2, result) -} - -/** - * Merges [the first map][map1] and [the second map][map2] resolving conflicts with [resolve] lambda. - * - * Precisely, corresponding keys and values of the received maps are put into a new empty map which is returned after - * afterwards. For every key appearing in both maps corresponding value is a result of the [resolve] lambda calculated - * on the key and its corresponding values from the merged maps. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @param resolve lambda function that resolves merge conflicts. - * @return the result of the merge. - */ -internal inline fun mergeBy(map1: Map, map2: Map, resolve: (key: K, value1: V1, value2: V2) -> W): Map { - val result = LinkedHashMap(map1.size + map2.size) - return mergeToBy(map1, map2, result, resolve) -} - -/** - * Merges [the first map][map1] and [the second map][map2] resolving conflicts with [resolve] lambda. - * - * Precisely, corresponding keys and values of the received maps are put into a new empty map which is returned after - * afterwards. For every key appearing in both maps corresponding value is a result of the [resolve] lambda calculated - * on the key's corresponding values from the merged maps. - * - * @param map1 the first (less prioritised) map to merge. - * @param map2 the second (more prioritised) map to merge. - * @param resolve lambda function that resolves merge conflicts. - * @return the result of the merge. - */ -internal inline fun mergeBy(map1: Map, map2: Map, resolve: (value1: V1, value2: V2) -> W): Map = - mergeBy(map1, map2) { _, value1, value2 -> resolve(value1, value2) } - -/** - * Populates the [destination] map with key-value pairs provided by [transform] function applied to each element of the - * given collection resolving conflicts with [resolve] function and returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each element to key-value. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateTo(destination: D, transform: (T) -> Pair, resolve: (key: K, currentValue: V, newValue: V) -> V): D { - for (element in this) { - val (key, value) = transform(element) - destination.putOrChange(key, value, resolve) - } - return destination -} - -/** - * Populates the [destination] map with key-value pairs, where key is provided by [keySelector] function and value is - * provided by [valueTransform] applied to each element of the given collection, resolving conflicts with [resolve] - * function and returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param valueTransform lambda functions that generates value for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateByTo(destination: D, keySelector: (T) -> K, valueTransform: (T) -> V, resolve: (key: K, currentValue: V, newValue: V) -> V): D { - for (element in this) { - val key = keySelector(element) - val value = valueTransform(element) - destination.putOrChange(key, value, resolve) - } - return destination -} - -/** - * Populates the [destination] map with key-value pairs, where key is provided by [keySelector] function applied to each - * element of the given collection and value is the element itself, resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateByTo(destination: D, keySelector: (T) -> K, resolve: (key: K, currentValue: T, newValue: T) -> T): D { - for (element in this) { - val key = keySelector(element) - destination.putOrChange(key, element, resolve) - } - return destination -} - -/** - * Populates the [destination] map with key-value pairs provided by [transform] function applied to each element of the - * given collection resolving conflicts with [resolve] function and returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each element to key-value pair. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateTo(destination: D, transform: (T) -> Pair, resolve: (currentValue: V, newValue: V) -> V): D = - associateTo(destination, transform) { _, currentValue, newValue -> resolve(currentValue, newValue) } - -/** - * Populates the [destination] map with key-value pairs, where key is provided by [keySelector] function and value is - * provided by [valueTransform] applied to each element of the given collection, resolving conflicts with [resolve] - * function and returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param valueTransform lambda functions that generates value for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateByTo(destination: D, keySelector: (T) -> K, valueTransform: (T) -> V, resolve: (currentValue: V, newValue: V) -> V): D = - associateByTo(destination, keySelector, valueTransform) { _, currentValue, newValue -> resolve(currentValue, newValue) } - -/** - * Populates the [destination] map with key-value pairs, where key is provided by [keySelector] function applied to each - * element of the given collection and value is the element itself, resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Iterable.associateByTo(destination: D, keySelector: (T) -> K, resolve: (currentValue: T, newValue: T) -> T): D = - associateByTo(destination, keySelector) { _, currentValue, newValue -> resolve(currentValue, newValue) } - -/** - * Returns a map containing key-value pairs provided by [transform] function applied to elements of the given collection. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with the - * key is resolved with [resolve] function which takes the key, current value corresponding to the key, and new value - * from the pair. - * - * @param transform function which transforms each element to key-value pair. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associate(transform: (T) -> Pair, resolve: (key: K, currentValue: V, newValue: V) -> V): Map = - associateTo(LinkedHashMap(), transform, resolve) - -/** - * Returns a map containing the values provided by [valueTransform] and indexed by [keySelector] functions applied to - * elements of the given collection. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with - * the key is resolved with [resolve] function which takes the key, current value corresponding to the key, and new - * value from the pair. - * - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param valueTransform lambda functions that generates value for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associateBy(keySelector: (T) -> K, valueTransform: (T) -> V, resolve: (key: K, currentValue: V, newValue: V) -> V): Map = - associateByTo(LinkedHashMap(), keySelector, valueTransform, resolve) - -/** - * Returns a map containing the elements from the given collection indexed by the key returned from [keySelector] - * function applied to each element. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with - * the key is resolved with [resolve] function which takes the key, current value corresponding to the key, and new - * value from the pair. - * - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associateBy(keySelector: (T) -> K, resolve: (key: K, currentValue: T, newValue: T) -> T): Map = - associateByTo(LinkedHashMap(), keySelector, resolve) - -/** - * Returns a map containing key-value pairs provided by [transform] function applied to elements of the given collection. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with - * the key is resolved with [resolve] function which takes current value corresponding to the key and new value from the - * pair. - * - * @param transform function which transforms each element to key-value pair. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associate(transform: (T) -> Pair, resolve: (currentValue: V, newValue: V) -> V): Map = - associateTo(LinkedHashMap(), transform, resolve) - -/** - * Returns a map containing the values provided by [valueTransform] and indexed by [keySelector] functions applied to - * elements of the given collection. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with - * the key is resolved with [resolve] function which takes current value corresponding to the key and new value from the - * pair. - * - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param valueTransform lambda functions that generates value for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associateBy(keySelector: (T) -> K, valueTransform: (T) -> V, resolve: (currentValue: V, newValue: V) -> V): Map = - associateByTo(LinkedHashMap(), keySelector, valueTransform, resolve) - -/** - * Returns a map containing the elements from the given collection indexed by the key returned from [keySelector] - * function applied to each element. - * - * All pairs are added in order of iteration. If some key is already added to the map, adding new key-value pair with - * the key is resolved with [resolve] function which takes current value corresponding to the key and new value from the - * pair. - * - * @param keySelector lambda functions that generates keys for the key-value pairs. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Iterable.associateBy(keySelector: (T) -> K, resolve: (currentValue: T, newValue: T) -> T): Map = - associateByTo(LinkedHashMap(), keySelector, resolve) - -/** - * Populates the given [destination] map with entries having the keys of this map and the values obtained - * by applying the [transform] function to each entry in this map resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new value. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Map.mapValuesTo(destination: D, transform: (Map.Entry) -> W, resolve: (key: K, currentValue: W, newValue: W) -> W): D = - entries.associateByTo(destination, { it.key }, transform, resolve) - -/** - * Populates the given [destination] map with entries having the keys of this map and the values obtained - * by applying the [transform] function to each entry in this map resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new value. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Map.mapValuesTo(destination: D, transform: (key: K, value: V) -> W, resolve: (key: K, currentValue: W, newValue: W) -> W): D = - entries.associateByTo(destination, { it.key }, { (key, value) -> transform(key, value) }, resolve) - -/** - * Populates the given [destination] map with entries having the keys of this map and the values obtained - * by applying the [transform] function to each entry in this map resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new value. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the [destination]. - */ -internal inline fun > Map.mapValuesTo(destination: D, transform: (Map.Entry) -> W, resolve: (currentValue: W, newValue: W) -> W): D = - entries.associateByTo(destination, { it.key }, transform, resolve) - -/** - * Populates the given [destination] map with entries having the keys of this map and the values obtained - * by applying the [transform] function to each entry in this map resolving conflicts with [resolve] function and - * returns the [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new value. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the [destination]. - */ -internal inline fun > Map.mapValuesTo(destination: D, transform: (key: K, value: V) -> W, resolve: (currentValue: W, newValue: W) -> W): D = - entries.associateByTo(destination, { it.key }, { (key, value) -> transform(key, value) }, resolve) - -/** - * Populates the given [destination] map with entries having the keys obtained by applying the [transform] function to - * each entry in this map and the values of this map, resolving conflicts with [resolve] function and returns the - * [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Map.mapKeysTo(destination: D, transform: (Map.Entry) -> L, resolve: (key: L, currentValue: V, newValue: V) -> V): D = - entries.associateByTo(destination, transform, { it.value }, resolve) - -/** - * Populates the given [destination] map with entries having the keys obtained by applying the [transform] function to - * each entry in this map and the values of this map, resolving conflicts with [resolve] function and returns the - * [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the [destination]. - */ -internal inline fun > Map.mapKeysTo(destination: D, transform: (key: K, value: V) -> L, resolve: (key: L, currentValue: V, newValue: V) -> V): D = - entries.associateByTo(destination, { (key, value) -> transform(key, value) }, { it.value }, resolve) - -/** - * Populates the given [destination] map with entries having the keys obtained by applying the [transform] function to - * each entry in this map and the values of this map, resolving conflicts with [resolve] function and returns the - * [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the [destination]. - */ -internal inline fun > Map.mapKeysTo(destination: D, transform: (Map.Entry) -> L, resolve: (currentValue: V, newValue: V) -> V): D = - entries.associateByTo(destination, transform, { it.value }, resolve) - -/** - * Populates the given [destination] map with entries having the keys obtained by applying the [transform] function to - * each entry in this map and the values of this map, resolving conflicts with [resolve] function and returns the - * [destination]. - * - * All pairs are added and resolved in order of iteration. - * - * @param destination the destination of the generated key-value pairs. - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the [destination]. - */ -internal inline fun > Map.mapKeysTo(destination: D, transform: (key: K, value: V) -> L, resolve: (currentValue: V, newValue: V) -> V): D = - entries.associateByTo(destination, { (key, value) -> transform(key, value) }, { it.value }, resolve) - -/** - * Returns a new map with entries having the keys obtained by applying the [transform] function to each entry in this - * map and the values of this map and resolving conflicts with [resolve] function. - * - * All pairs are added and resolved in order of iteration. - * - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Map.mapKeys(transform: (Map.Entry) -> L, resolve: (key: L, currentValue: V, newValue: V) -> V): Map = - mapKeysTo(LinkedHashMap(size), transform, resolve) - -/** - * Returns a new map with entries having the keys obtained by applying the [transform] function to each entry in this - * map and the values of this map and resolving conflicts with [resolve] function. - * - * All pairs are added and resolved in order of iteration. - * - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which receives some key, its current, and new - * corresponding values. - * @return the result map. - */ -internal inline fun Map.mapKeys(transform: (key: K, value: V) -> L, resolve: (key: L, currentValue: V, newValue: V) -> V): Map = - mapKeysTo(LinkedHashMap(size), transform, resolve) - -/** - * Returns a new map with entries having the keys obtained by applying the [transform] function to each entry in this - * map and the values of this map and resolving conflicts with [resolve] function. - * - * All pairs are added and resolved in order of iteration. - * - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the result map. - */ -internal inline fun Map.mapKeys(transform: (Map.Entry) -> L, resolve: (currentValue: V, newValue: V) -> V): Map = - mapKeysTo(LinkedHashMap(size), transform, resolve) - -/** - * Returns a new map with entries having the keys obtained by applying the [transform] function to each entry in this - * map and the values of this map and resolving conflicts with [resolve] function. - * - * All pairs are added and resolved in order of iteration. - * - * @param transform function which transforms each key-value pair to new key. - * @param resolve lambda function that resolves merge conflicts which current and new values corresponding to some key. - * @return the result map. - */ -internal inline fun Map.mapKeys(transform: (key: K, value: V) -> L, resolve: (currentValue: V, newValue: V) -> V): Map = - mapKeysTo(LinkedHashMap(size), transform, resolve) \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledConstructors.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledConstructors.kt deleted file mode 100644 index d74c0e1fb..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledConstructors.kt +++ /dev/null @@ -1,779 +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:Suppress("FunctionName", "NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.invoke - - -/** - * Returns the same degrees' description of the monomial, but without zero degrees. - */ -internal fun Map.cleanUp() = filterValues { it > 0U } - -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. The map is used as is. - */ -@PublishedApi -internal inline fun LabeledPolynomialAsIs(coefs: Map, C>) : LabeledPolynomial = LabeledPolynomial(coefs) - -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * The collections will be transformed to map with [toMap] and then will be used as is. - */ -@PublishedApi -internal inline fun LabeledPolynomialAsIs(pairs: Collection, C>>) : LabeledPolynomial = LabeledPolynomial(pairs.toMap()) - -/** - * Constructs [LabeledPolynomial] with provided array of [pairs] of pairs "term's signature — term's coefficient". - * The array will be transformed to map with [toMap] and then will be used as is. - */ -@PublishedApi -internal inline fun LabeledPolynomialAsIs(vararg pairs: Pair, C>) : LabeledPolynomial = LabeledPolynomial(pairs.toMap()) - -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. The map is used as is. - * - * **Be sure you read description of [LabeledPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun LabeledPolynomialWithoutCheck(coefs: Map, C>) : LabeledPolynomial = LabeledPolynomial(coefs) - -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * The collections will be transformed to map with [toMap] and then will be used as is. - * - * **Be sure you read description of [LabeledPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun LabeledPolynomialWithoutCheck(pairs: Collection, C>>) : LabeledPolynomial = LabeledPolynomial(pairs.toMap()) - -/** - * Constructs [LabeledPolynomial] with provided array of [pairs] of pairs "term's signature — term's coefficient". - * The array will be transformed to map with [toMap] and then will be used as is. - * - * **Be sure you read description of [LabeledPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun LabeledPolynomialWithoutCheck(vararg pairs: Pair, C>) : LabeledPolynomial = LabeledPolynomial(pairs.toMap()) - -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public fun LabeledPolynomial(coefs: Map, C>, add: (C, C) -> C) : LabeledPolynomial = - LabeledPolynomialAsIs( - coefs.mapKeys({ key, _ -> key.cleanUp() }, add) - ) - -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public fun LabeledPolynomial(pairs: Collection, C>>, add: (C, C) -> C) : LabeledPolynomial = - LabeledPolynomialAsIs( - pairs.associateBy({ it.first.cleanUp() }, { it.second }, add) - ) - -/** - * Constructs [LabeledPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public fun LabeledPolynomial(vararg pairs: Pair, C>, add: (C, C) -> C) : LabeledPolynomial = - LabeledPolynomialAsIs( - pairs.asIterable().associateBy({ it.first.cleanUp() }, { it.second }, add) - ) - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > A.LabeledPolynomial(coefs: Map, C>) : LabeledPolynomial = LabeledPolynomial(coefs, ::add) -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledPolynomialSpace.LabeledPolynomial(coefs: Map, C>) : LabeledPolynomial = LabeledPolynomial(coefs) { left: C, right: C -> left + right } - -/** - * Constructs [LabeledPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledRationalFunctionSpace.LabeledPolynomial(coefs: Map, C>) : LabeledPolynomial = LabeledPolynomial(coefs) { left: C, right: C -> left + right } - -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > A.LabeledPolynomial(pairs: Collection, C>>) : LabeledPolynomial = LabeledPolynomial(pairs, ::add) - -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledPolynomialSpace.LabeledPolynomial(pairs: Collection, C>>) : LabeledPolynomial = LabeledPolynomial(pairs) { left: C, right: C -> left + right } -/** - * Constructs [LabeledPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledRationalFunctionSpace.LabeledPolynomial(pairs: Collection, C>>) : LabeledPolynomial = LabeledPolynomial(pairs) { left: C, right: C -> left + right } - -/** - * Constructs [LabeledPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > A.LabeledPolynomial(vararg pairs: Pair, C>) : LabeledPolynomial = LabeledPolynomial(*pairs) { left: C, right: C -> left + right } -/** - * Constructs [LabeledPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledPolynomialSpace.LabeledPolynomial(vararg pairs: Pair, C>) : LabeledPolynomial = LabeledPolynomial(*pairs) { left: C, right: C -> left + right } -/** - * Constructs [LabeledPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see LabeledPolynomialWithoutCheck - */ -public inline fun > LabeledRationalFunctionSpace.LabeledPolynomial(vararg pairs: Pair, C>) : LabeledPolynomial = LabeledPolynomial(*pairs) { left: C, right: C -> left + right } - -/** - * Converts [this] constant to [LabeledPolynomial]. - */ -public inline fun C.asLabeledPolynomial() : LabeledPolynomial = LabeledPolynomialAsIs(mapOf(emptyMap() to this)) - -///** -//// * Converts [this] variable to [LabeledPolynomial]. -//// */ -//context(A) -//public inline fun > Symbol.asLabeledPolynomial() : LabeledPolynomial = LabeledPolynomial(mapOf(mapOf(this to 1u) to one)) -///** -// * Converts [this] variable to [LabeledPolynomial]. -// */ -//context(LabeledPolynomialSpace) -//public inline fun > Symbol.asLabeledPolynomial() : LabeledPolynomial = LabeledPolynomial(mapOf(mapOf(this to 1u) to constantOne)) -///** -// * Converts [this] variable to [LabeledPolynomial]. -// */ -//context(LabeledRationalFunctionSpace) -//public inline fun > Symbol.asLabeledPolynomial() : LabeledPolynomial = LabeledPolynomial(mapOf(mapOf(this to 1u) to constantOne)) - -/** - * Marks DSL that allows to more simply create [LabeledPolynomial]s with good performance. - * - * For example, polynomial \(5 a^2 c^3 - 6 b\) can be described as - * ``` - * Int.algebra { - * val labeledPolynomial : LabeledPolynomial = LabeledPolynomialDSL1 { - * 5 { a inPowerOf 2u; c inPowerOf 3u } // 5 a^2 c^3 + - * (-6) { b inPowerOf 1u } // (-6) b^1 - * } - * } - * ``` - * @usesMathJax - */ -@DslMarker -@UnstableKMathAPI -internal annotation class LabeledPolynomialConstructorDSL1 - -/** - * Builder of [LabeledPolynomial] signature. It should be used as an implicit context for lambdas that describe term signature. - */ -@UnstableKMathAPI -@LabeledPolynomialConstructorDSL1 -public class DSL1LabeledPolynomialTermSignatureBuilder { - /** - * Signature storage. Any declaration of any variable's power updates the storage by increasing corresponding value. - * Afterward the storage will be used as a resulting signature. - */ - private val signature: MutableMap = LinkedHashMap() - - /** - * Builds the resulting signature. - * - * In fact, it just returns [signature] as regular signature of type `List`. - */ - @PublishedApi - internal fun build(): Map = signature - - /** - * Declares power of [this] variable of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public infix fun Symbol.inPowerOf(deg: UInt) { - if (deg == 0u) return - signature.putOrChange(this, deg) { it -> it + deg } - } - /** - * Declares power of [this] variable of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Symbol.pow(deg: UInt): Unit = this inPowerOf deg - /** - * Declares power of [this] variable of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Symbol.`in`(deg: UInt): Unit = this inPowerOf deg - /** - * Declares power of [this] variable of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Symbol.of(deg: UInt): Unit = this inPowerOf deg -} - -/** - * Builder of [LabeledPolynomial]. It should be used as an implicit context for lambdas that describe [LabeledPolynomial]. - */ -@UnstableKMathAPI -@LabeledPolynomialConstructorDSL1 -public class DSL1LabeledPolynomialBuilder( - /** - * Summation operation that will be used to sum coefficients of monomials of same signatures. - */ - private val add: (C, C) -> C, - /** - * Initial capacity of coefficients map. - */ - initialCapacity: Int? = null -) { - /** - * Coefficients storage. Any declaration of any monomial updates the storage. - * Afterward the storage will be used as a resulting coefficients map. - */ - private val coefficients: MutableMap, C> = if (initialCapacity != null) LinkedHashMap(initialCapacity) else LinkedHashMap() - - /** - * Builds the resulting coefficients map. - * - * In fact, it just returns [coefficients] as regular coefficients map of type `Map, C>`. - */ - @PublishedApi - internal fun build(): LabeledPolynomial = LabeledPolynomial(coefficients) - - /** - * Declares monomial with [this] coefficient and provided [signature]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public infix fun C.with(signature: Map) { - coefficients.putOrChange(signature, this@with, add) - } - /** - * Declares monomial with [this] coefficient and signature constructed by [block]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public inline infix fun C.with(noinline block: DSL1LabeledPolynomialTermSignatureBuilder.() -> Unit): Unit = this.invoke(block) - /** - * Declares monomial with [this] coefficient and signature constructed by [block]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public inline operator fun C.invoke(block: DSL1LabeledPolynomialTermSignatureBuilder.() -> Unit): Unit = - this with DSL1LabeledPolynomialTermSignatureBuilder().apply(block).build() -} - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -///** -// * Creates [LabeledPolynomial] with lambda [block] in context of [this] ring of constants. -// * -// * For example, polynomial \(5 a^2 c^3 - 6 b\) can be described as -// * ``` -// * Int.algebra { -// * val labeledPolynomial : LabeledPolynomial = LabeledPolynomialDSL1 { -// * 5 { a inPowerOf 2u; c inPowerOf 3u } // 5 a^2 c^3 + -// * (-6) { b inPowerOf 1u } // (-6) b^1 -// * } -// * } -// * ``` -// * @usesMathJax -// */ -// FIXME: For now this fabric does not let next two fabrics work. (See KT-52803.) Possible feature solutions: -// 1. `LowPriorityInOverloadResolution` becomes public. Then it should be applied to this function. -// 2. Union types are implemented. Then all three functions should be rewritten -// as one with single union type as a (context) receiver. -//@UnstableKMathAPI -//public inline fun > A.LabeledPolynomialDSL1(initialCapacity: Int? = null, block: LabeledPolynomialBuilder.() -> Unit) : LabeledPolynomial = LabeledPolynomialBuilder(::add, initialCapacity).apply(block).build() -/** - * Creates [LabeledPolynomial] with lambda [block] in context of [this] ring of [LabeledPolynomial]s. - * - * For example, polynomial \(5 a^2 c^3 - 6 b\) can be described as - * ``` - * Int.algebra { - * val labeledPolynomial : LabeledPolynomial = LabeledPolynomialDSL1 { - * 5 { a inPowerOf 2u; c inPowerOf 3u } // 5 a^2 c^3 + - * (-6) { b inPowerOf 1u } // (-6) b^1 - * } - * } - * ``` - * @usesMathJax - */ -@UnstableKMathAPI -public inline fun > LabeledPolynomialSpace.LabeledPolynomialDSL1(initialCapacity: Int? = null, block: DSL1LabeledPolynomialBuilder.() -> Unit) : LabeledPolynomial = DSL1LabeledPolynomialBuilder({ left: C, right: C -> left + right }, initialCapacity).apply(block).build() -/** - * Creates [LabeledPolynomial] with lambda [block] in context of [this] field of [LabeledRationalFunction]s. - * - * For example, polynomial \(5 a^2 c^3 - 6 b\) can be described as - * ``` - * Int.algebra { - * val labeledPolynomial : LabeledPolynomial = LabeledPolynomialDSL1 { - * 5 { a inPowerOf 2u; c inPowerOf 3u } // 5 a^2 c^3 + - * (-6) { b inPowerOf 1u } // (-6) b^1 - * } - * } - * ``` - * @usesMathJax - */ -@UnstableKMathAPI -public inline fun > LabeledRationalFunctionSpace.LabeledPolynomialDSL1(initialCapacity: Int? = null, block: DSL1LabeledPolynomialBuilder.() -> Unit) : LabeledPolynomial = DSL1LabeledPolynomialBuilder({ left: C, right: C -> left + right }, initialCapacity).apply(block).build() - -/** - * Marks DSL that allows to more simply create [LabeledPolynomial]s with good performance. - * - * For example, polynomial \(5 a^2 c^3 - 6 b\) can be described as - * ``` - * Int.algebra { - * val numberedPolynomial : NumberedPolynomial = NumberedPolynomial { - * 5 { a inPowerOf 2u; c inPowerOf 3u } // 5 a^2 c^3 + - * (-6) { b inPowerOf 1u } // (-6) b^1 - * } - * } - * ``` - * @usesMathJax - */ -@DslMarker -@UnstableKMathAPI -internal annotation class LabeledPolynomialBuilderDSL2 - -/** - * Builder of [LabeledPolynomial]. It should be used as an implicit context for lambdas that describe [LabeledPolynomial]. - */ -@UnstableKMathAPI -@LabeledPolynomialBuilderDSL2 -public class DSL2LabeledPolynomialBuilder( - private val ring: Ring, - /** - * Initial capacity of coefficients map. - */ - initialCapacity: Int? = null -) { - /** - * Coefficients storage. Any declaration of any monomial updates the storage. - * Afterward the storage will be used as a resulting coefficients map. - */ - private val coefficients: MutableMap, C> = if (initialCapacity != null) LinkedHashMap(initialCapacity) else LinkedHashMap() - - /** - * Builds the resulting coefficients map. - * - * In fact, it just returns [coefficients] as regular coefficients map of type `Map, C>`. - */ - @PublishedApi - internal fun build(): LabeledPolynomial = LabeledPolynomial(coefficients) - - public inner class Term internal constructor( - internal val signature: Map = HashMap(), - internal val coefficient: C - ) - - private inline fun submit(signature: Map, onPut: Ring.() -> C, onChange: Ring.(C) -> C) { - coefficients.putOrChange<_, C>(signature, { ring.onPut() }, { ring.onChange(it) }) - } - - private inline fun submit(signature: Map, lazyCoefficient: Ring.() -> C) { - submit(signature, lazyCoefficient, { it + lazyCoefficient() }) - } - - private fun submit(signature: Map, coefficient: C) { - submit(signature) { coefficient } - } - - // TODO: `@submit` will be resolved differently. Change it to `@C`. - private fun C.submit() = submit(emptyMap(), { this@submit }) - - private fun Symbol.submit() = submit(mapOf(this to 1u), { one }) - - private fun Term.submit(): Submit { - submit(signature, coefficient) - return Submit - } - - public object Submit - - public operator fun C.unaryPlus(): Submit { - submit() - return Submit - } - - public operator fun C.unaryMinus(): Submit { - submit(emptyMap(), { -this@unaryMinus }, { it - this@unaryMinus }) - return Submit - } - - public operator fun C.plus(other: C): Submit { - submit(emptyMap(), { this@plus + other }) - return Submit - } - - public operator fun C.minus(other: C): Submit { - submit(emptyMap(), { this@minus - other }) - return Submit - } - - public operator fun C.times(other: C): C = ring { this@times * other } - - public operator fun C.plus(other: Symbol): Submit { - submit(emptyMap(), this) - submit(mapOf(other to 1u), ring.one) - return Submit - } - - public operator fun C.minus(other: Symbol): Submit { - submit(emptyMap(), this) - submit(mapOf(other to 1u), { -one }, { it - one }) - return Submit - } - - public operator fun C.times(other: Symbol): Term = Term(mapOf(other to 1u), this) - - public operator fun C.plus(other: Term): Submit { - submit(emptyMap(), this) - other.submit() - return Submit - } - - public operator fun C.minus(other: Term): Submit { - submit(emptyMap(), this) - submit(other.signature, { -other.coefficient }, { it - other.coefficient }) - return Submit - } - - public operator fun C.times(other: Term): Term = Term(other.signature, ring { this@times * other.coefficient }) - - public operator fun Symbol.plus(other: C): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Symbol.minus(other: C): Submit { - this.submit() - submit(emptyMap(), { -other }, { it - other }) - return Submit - } - - public operator fun Symbol.times(other: C): Term = Term(mapOf(this to 1u), other) - - public operator fun Symbol.unaryPlus(): Submit { - this.submit() - return Submit - } - - public operator fun Symbol.unaryMinus(): Submit { - submit(mapOf(this to 1u), { -one }, { it - one }) - return Submit - } - - public operator fun Symbol.plus(other: Symbol): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Symbol.minus(other: Symbol): Submit { - this.submit() - submit(mapOf(other to 1u), { -one }, { it - one }) - return Submit - } - - public operator fun Symbol.times(other: Symbol): Term = - if (this == other) Term(mapOf(this to 2u), ring.one) - else Term(mapOf(this to 1u, other to 1u), ring.one) - - public operator fun Symbol.plus(other: Term): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Symbol.minus(other: Term): Submit { - this.submit() - submit(other.signature, { -other.coefficient }, { it - other.coefficient }) - return Submit - } - - public operator fun Symbol.times(other: Term): Term = - Term( - other.signature.withPutOrChanged(this, 1u) { it -> it + 1u }, - other.coefficient - ) - - public operator fun Term.plus(other: C): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Term.minus(other: C): Submit { - this.submit() - submit(emptyMap(), { -other }, { it - other }) - return Submit - } - - public operator fun Term.times(other: C): Term = - Term( - signature, - ring { coefficient * other } - ) - - public operator fun Term.plus(other: Symbol): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Term.minus(other: Symbol): Submit { - this.submit() - submit(mapOf(other to 1u), { -one }, { it - one }) - return Submit - } - - public operator fun Term.times(other: Symbol): Term = - Term( - signature.withPutOrChanged(other, 1u) { it -> it + 1u }, - coefficient - ) - - public operator fun Term.unaryPlus(): Submit { - this.submit() - return Submit - } - - public operator fun Term.unaryMinus(): Submit { - submit(signature, { -coefficient }, { it - coefficient }) - return Submit - } - - public operator fun Term.plus(other: Term): Submit { - this.submit() - other.submit() - return Submit - } - - public operator fun Term.minus(other: Term): Submit { - this.submit() - submit(other.signature, { -other.coefficient }, { it - other.coefficient }) - return Submit - } - - public operator fun Term.times(other: Term): Term = - Term( - mergeBy(signature, other.signature) { deg1, deg2 -> deg1 + deg2 }, - ring { coefficient * other.coefficient } - ) -} - -//@UnstableKMathAPI -//public fun Ring.LabeledPolynomialDSL2(initialCapacity: Int? = null, block: DSL2LabeledPolynomialBuilder.() -> Unit): LabeledPolynomial = DSL2LabeledPolynomialBuilder(this, initialCapacity).apply(block).build() - -@UnstableKMathAPI -public fun > LabeledPolynomialSpace.LabeledPolynomialDSL2(initialCapacity: Int? = null, block: DSL2LabeledPolynomialBuilder.() -> Unit): LabeledPolynomial = DSL2LabeledPolynomialBuilder(ring, initialCapacity).apply(block).build() - -@UnstableKMathAPI -public fun > LabeledRationalFunctionSpace.LabeledPolynomialDSL2(initialCapacity: Int? = null, block: DSL2LabeledPolynomialBuilder.() -> Unit): LabeledPolynomial = DSL2LabeledPolynomialBuilder(ring, initialCapacity).apply(block).build() - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -/** - * Constructs [LabeledRationalFunction] with provided coefficients maps [numeratorCoefficients] and [denominatorCoefficients]. - * - * The maps will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. the maps' keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > A.LabeledRationalFunction(numeratorCoefficients: Map, C>, denominatorCoefficients: Map, C>): LabeledRationalFunction = - LabeledRationalFunction( - LabeledPolynomial(numeratorCoefficients), - LabeledPolynomial(denominatorCoefficients) - ) -/** - * Constructs [LabeledRationalFunction] with provided coefficients maps [numeratorCoefficients] and [denominatorCoefficients]. - * - * The maps will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. the maps' keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > LabeledRationalFunctionSpace.LabeledRationalFunction(numeratorCoefficients: Map, C>, denominatorCoefficients: Map, C>): LabeledRationalFunction = - LabeledRationalFunction( - LabeledPolynomial(numeratorCoefficients), - LabeledPolynomial(denominatorCoefficients) - ) - -/** - * Constructs [LabeledRationalFunction] with provided [numerator] and unit denominator. - */ -public fun > A.LabeledRationalFunction(numerator: LabeledPolynomial): LabeledRationalFunction = - LabeledRationalFunction(numerator, LabeledPolynomial(mapOf(emptyMap() to one))) -/** - * Constructs [LabeledRationalFunction] with provided [numerator] and unit denominator. - */ -public fun > LabeledRationalFunctionSpace.LabeledRationalFunction(numerator: LabeledPolynomial): LabeledRationalFunction = - LabeledRationalFunction(numerator, polynomialOne) - -/** - * Constructs [LabeledRationalFunction] with provided coefficients map [numeratorCoefficients] for numerator and unit - * denominator. - * - * [numeratorCoefficients] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [numeratorCoefficients]'s keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > LabeledRationalFunctionSpace.LabeledRationalFunction(numeratorCoefficients: Map, C>): LabeledRationalFunction = - LabeledRationalFunction( - LabeledPolynomial(numeratorCoefficients), - polynomialOne - ) -/** - * Constructs [LabeledRationalFunction] with provided coefficients map [numeratorCoefficients] for numerator and unit - * denominator. - * - * [numeratorCoefficients] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [numeratorCoefficients]'s keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > A.LabeledRationalFunction(numeratorCoefficients: Map, C>): LabeledRationalFunction = - LabeledRationalFunction( - LabeledPolynomial(numeratorCoefficients), - LabeledPolynomialAsIs(mapOf(emptyMap() to one)) - ) - -///** -// * Converts [this] constant to [LabeledRationalFunction]. -// */ -//context(A) -//public fun > C.asLabeledRationalFunction() : LabeledRationalFunction = -// LabeledRationalFunction( -// LabeledPolynomialAsIs(mapOf(emptyMap() to this)), -// LabeledPolynomialAsIs(mapOf(emptyMap() to one)) -// ) -///** -// * Converts [this] constant to [LabeledRationalFunction]. -// */ -//context(LabeledRationalFunctionSpace) -//public fun > C.asLabeledRationalFunction() : LabeledRationalFunction = -// LabeledRationalFunction( -// LabeledPolynomialAsIs(mapOf(emptyMap() to this)), -// LabeledPolynomialAsIs(mapOf(emptyMap() to constantOne)) -// ) - -///** -// * Converts [this] variable to [LabeledRationalFunction]. -// */ -//context(A) -//public fun > Symbol.asLabeledRationalFunction() : LabeledRationalFunction = -// LabeledRationalFunction( -// LabeledPolynomialAsIs(mapOf(mapOf(this to 1u) to one)), -// LabeledPolynomialAsIs(mapOf(emptyMap() to one)) -// ) -///** -// * Converts [this] variable to [LabeledRationalFunction]. -// */ -//context(LabeledRationalFunctionSpace) -//public fun > Symbol.asLabeledRationalFunction() : LabeledRationalFunction = -// LabeledRationalFunction( -// LabeledPolynomialAsIs(mapOf(mapOf(this to 1u) to constantOne)), -// LabeledPolynomialAsIs(mapOf(emptyMap() to constantOne)) -// ) \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledUtil.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledUtil.kt deleted file mode 100644 index a37a1fe39..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/labeledUtil.kt +++ /dev/null @@ -1,321 +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.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.* -import kotlin.contracts.InvocationKind -import kotlin.contracts.contract -import kotlin.jvm.JvmName - - -/** - * Creates a [LabeledPolynomialSpace] over a received ring. - */ -public inline val > A.labeledPolynomialSpace: LabeledPolynomialSpace - get() = LabeledPolynomialSpace(this) - -/** - * Creates a [LabeledPolynomialSpace]'s scope over a received ring. - */ -public inline fun , R> A.labeledPolynomialSpace(block: LabeledPolynomialSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return LabeledPolynomialSpace(this).block() -} -/** - * Creates a [LabeledRationalFunctionSpace] over a received ring. - */ -public inline val > A.labeledRationalFunctionSpace: LabeledRationalFunctionSpace - get() = LabeledRationalFunctionSpace(this) - -/** - * Creates a [LabeledRationalFunctionSpace]'s scope over a received ring. - */ -public inline fun , R> A.labeledRationalFunctionSpace(block: LabeledRationalFunctionSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return LabeledRationalFunctionSpace(this).block() -} - -/** - * Substitutes provided Double arguments [args] into [this] Double polynomial. - */ -public fun LabeledPolynomial.substitute(args: Map): LabeledPolynomial = Double.algebra { - if (coefficients.isEmpty()) return this@substitute - LabeledPolynomial( - buildMap { - coefficients.forEach { (degs, c) -> - val newDegs = degs.filterKeys { it !in args } - val newC = args.entries.fold(c) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - putOrChange(newDegs, newC, ::add) - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ -public fun LabeledPolynomial.substitute(ring: Ring, args: Map): LabeledPolynomial = ring { - if (coefficients.isEmpty()) return this@substitute - LabeledPolynomial( - buildMap { - coefficients.forEach { (degs, c) -> - val newDegs = degs.filterKeys { it !in args } - val newC = args.entries.fold(c) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - putOrChange(newDegs, newC, ::add) - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substitutePolynomial") -public fun LabeledPolynomial.substitute(ring: Ring, args: Map>) : LabeledPolynomial = - ring.labeledPolynomialSpace { - coefficients.entries.fold(zero) { acc, (degs, c) -> - val newDegs = degs.filterKeys { it !in args } - acc + args.entries.fold(LabeledPolynomial(mapOf(newDegs to c))) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - } - } - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substituteRationalFunction") -public fun LabeledPolynomial.substitute(ring: Ring, args: Map>) : LabeledRationalFunction = - ring.labeledRationalFunctionSpace { - coefficients.entries.fold(zero) { acc, (degs, c) -> - val newDegs = degs.filterKeys { it !in args } - acc + args.entries.fold(LabeledRationalFunction(LabeledPolynomial(mapOf(newDegs to c)))) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - } - } - -/** - * Substitutes provided Double arguments [args] into [this] Double rational function. - */ -public fun LabeledRationalFunction.substitute(args: Map): LabeledRationalFunction = - LabeledRationalFunction(numerator.substitute(args), denominator.substitute(args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ -public fun LabeledRationalFunction.substitute(ring: Ring, args: Map): LabeledRationalFunction = - LabeledRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substitutePolynomial") -public fun LabeledRationalFunction.substitute(ring: Ring, args: Map>) : LabeledRationalFunction = - LabeledRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substituteRationalFunction") -public fun LabeledRationalFunction.substitute(ring: Ring, args: Map>) : LabeledRationalFunction = - ring.labeledRationalFunctionSpace { - numerator.substitute(ring, args) / denominator.substitute(ring, args) - } - -/** - * Returns algebraic derivative of received polynomial with respect to provided variable. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.derivativeWithRespectTo( - algebra: A, - variable: Symbol, -): LabeledPolynomial = algebra { - LabeledPolynomial( - buildMap(coefficients.count { it.key.getOrElse(variable) { 0u } >= 1u }) { - coefficients - .forEach { (degs, c) -> - if (variable !in degs) return@forEach - put( - buildMap { - degs.forEach { (vari, deg) -> - when { - vari != variable -> put(vari, deg) - deg > 1u -> put(vari, deg - 1u) - } - } - }, - multiplyByDoubling(c, degs[variable]!!) - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variable of specified order. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.nthDerivativeWithRespectTo( - algebra: A, - variable: Symbol, - order: UInt -): LabeledPolynomial = algebra { - if (order == 0u) return this@nthDerivativeWithRespectTo - LabeledPolynomial( - buildMap(coefficients.count { it.key.getOrElse(variable) { 0u } >= order }) { - coefficients - .forEach { (degs, c) -> - if (degs.getOrElse(variable) { 0u } < order) return@forEach - put( - buildMap { - degs.forEach { (vari, deg) -> - when { - vari != variable -> put(vari, deg) - deg > order -> put(vari, deg - order) - } - } - }, - degs[variable]!!.let { deg -> - (deg downTo deg - order + 1u) - .fold(c) { acc, ord -> multiplyByDoubling(acc, ord) } - } - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variables of specified orders. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.nthDerivativeWithRespectTo( - algebra: A, - variablesAndOrders: Map, -): LabeledPolynomial = algebra { - val filteredVariablesAndOrders = variablesAndOrders.filterValues { it != 0u } - if (filteredVariablesAndOrders.isEmpty()) return this@nthDerivativeWithRespectTo - LabeledPolynomial( - buildMap( - coefficients.count { - variablesAndOrders.all { (variable, order) -> - it.key.getOrElse(variable) { 0u } >= order - } - } - ) { - coefficients - .forEach { (degs, c) -> - if (filteredVariablesAndOrders.any { (variable, order) -> degs.getOrElse(variable) { 0u } < order }) return@forEach - put( - buildMap { - degs.forEach { (vari, deg) -> - if (vari !in filteredVariablesAndOrders) put(vari, deg) - else { - val order = filteredVariablesAndOrders[vari]!! - if (deg > order) put(vari, deg - order) - } - } - }, - filteredVariablesAndOrders.entries.fold(c) { acc1, (index, order) -> - degs[index]!!.let { deg -> - (deg downTo deg - order + 1u) - .fold(acc1) { acc2, ord -> multiplyByDoubling(acc2, ord) } - } - } - ) - } - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial with respect to provided variable. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.antiderivativeWithRespectTo( - algebra: A, - variable: Symbol, -): LabeledPolynomial = algebra { - LabeledPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - val newDegs = degs.withPutOrChanged(variable, 1u) { it -> it + 1u } - put( - newDegs, - c / multiplyByDoubling(one, newDegs[variable]!!) - ) - } - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial with respect to provided variable of specified order. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.nthAntiderivativeWithRespectTo( - algebra: A, - variable: Symbol, - order: UInt -): LabeledPolynomial = algebra { - if (order == 0u) return this@nthAntiderivativeWithRespectTo - LabeledPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - val newDegs = degs.withPutOrChanged(variable, order) { it -> it + order } - put( - newDegs, - newDegs[variable]!!.let { deg -> - (deg downTo deg - order + 1u) - .fold(c) { acc, ord -> acc / multiplyByDoubling(one, ord) } - } - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variables of specified orders. - */ -@UnstableKMathAPI -public fun > LabeledPolynomial.nthAntiderivativeWithRespectTo( - algebra: A, - variablesAndOrders: Map, -): LabeledPolynomial = algebra { - val filteredVariablesAndOrders = variablesAndOrders.filterValues { it != 0u } - if (filteredVariablesAndOrders.isEmpty()) return this@nthAntiderivativeWithRespectTo - LabeledPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - val newDegs = mergeBy(degs, filteredVariablesAndOrders) { deg, order -> deg + order } - put( - newDegs, - filteredVariablesAndOrders.entries.fold(c) { acc1, (index, order) -> - newDegs[index]!!.let { deg -> - (deg downTo deg - order + 1u) - .fold(acc1) { acc2, ord -> acc2 / multiplyByDoubling(one, ord) } - } - } - ) - } - } - ) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listConstructors.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listConstructors.kt deleted file mode 100644 index e95361724..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listConstructors.kt +++ /dev/null @@ -1,92 +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.functions - -import space.kscience.kmath.operations.Ring - - -/** - * Constructs a [ListPolynomial] instance with provided [coefficients]. The collection of coefficients will be reversed - * if [reverse] parameter is true. - */ -@Suppress("FunctionName") -public fun ListPolynomial(coefficients: List, reverse: Boolean = false): ListPolynomial = - ListPolynomial(with(coefficients) { if (reverse) reversed() else this }) - -/** - * Constructs a [ListPolynomial] instance with provided [coefficients]. The collection of coefficients will be reversed - * if [reverse] parameter is true. - */ -@Suppress("FunctionName") -public fun ListPolynomial(vararg coefficients: C, reverse: Boolean = false): ListPolynomial = - ListPolynomial(with(coefficients) { if (reverse) reversed() else toList() }) - -/** - * Represents [this] constant as a [ListPolynomial]. - */ -public fun C.asListPolynomial() : ListPolynomial = ListPolynomial(listOf(this)) - - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -/** - * Constructs [ListRationalFunction] instance with numerator and denominator constructed with provided - * [numeratorCoefficients] and [denominatorCoefficients]. The both collections of coefficients will be reversed if - * [reverse] parameter is true. - */ -@Suppress("FunctionName") -public fun ListRationalFunction(numeratorCoefficients: List, denominatorCoefficients: List, reverse: Boolean = false): ListRationalFunction = - ListRationalFunction( - ListPolynomial( with(numeratorCoefficients) { if (reverse) reversed() else this } ), - ListPolynomial( with(denominatorCoefficients) { if (reverse) reversed() else this } ) - ) -/** - * Constructs [ListRationalFunction] instance with provided [numerator] and unit denominator. - */ -@Suppress("FunctionName") -public fun > A.ListRationalFunction(numerator: ListPolynomial): ListRationalFunction = - ListRationalFunction(numerator, ListPolynomial(listOf(one))) -/** - * Constructs [ListRationalFunction] instance with provided [numerator] and unit denominator. - */ -@Suppress("FunctionName") -public fun > ListRationalFunctionSpace.ListRationalFunction(numerator: ListPolynomial): ListRationalFunction = - ListRationalFunction(numerator, polynomialOne) -/** - * Constructs [ListRationalFunction] instance with numerator constructed with provided [numeratorCoefficients] and unit - * denominator. The collection of numerator coefficients will be reversed if [reverse] parameter is true. - */ -@Suppress("FunctionName") -public fun > A.ListRationalFunction(numeratorCoefficients: List, reverse: Boolean = false): ListRationalFunction = - ListRationalFunction( - ListPolynomial( with(numeratorCoefficients) { if (reverse) reversed() else this } ), - ListPolynomial(listOf(one)) - ) -/** - * Constructs [ListRationalFunction] instance with numerator constructed with provided [numeratorCoefficients] and unit - * denominator. The collection of numerator coefficients will be reversed if [reverse] parameter is true. - */ -@Suppress("FunctionName") -public fun > ListRationalFunctionSpace.ListRationalFunction(numeratorCoefficients: List, reverse: Boolean = false): ListRationalFunction = - ListRationalFunction( - ListPolynomial( with(numeratorCoefficients) { if (reverse) reversed() else this } ), - polynomialOne - ) - -/** - * Represents [this] constant as a rational function. - */ // FIXME: When context receivers will be ready, delete this function and uncomment the following two -public fun > C.asListRationalFunction(ring: A) : ListRationalFunction = ring.ListRationalFunction(asListPolynomial()) -///** -// * Represents [this] constant as a rational function. -// */ -//context(A) -//public fun > C.asListRationalFunction() : ListRationalFunction = ListRationalFunction(asListPolynomial()) -///** -// * Represents [this] constant as a rational function. -// */ -//context(ListRationalFunctionSpace) -//public fun > C.asListRationalFunction() : ListRationalFunction = ListRationalFunction(asListPolynomial()) \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listUtil.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listUtil.kt deleted file mode 100644 index 4f3f6d88e..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/listUtil.kt +++ /dev/null @@ -1,255 +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.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.* -import kotlin.contracts.InvocationKind -import kotlin.contracts.contract -import kotlin.math.max -import kotlin.math.pow - - -/** - * Creates a [ListPolynomialSpace] over a received ring. - */ -public inline val > A.listPolynomialSpace: ListPolynomialSpace - get() = ListPolynomialSpace(this) - -/** - * Creates a [ListPolynomialSpace]'s scope over a received ring. - */ // TODO: When context will be ready move [ListPolynomialSpace] and add [A] to context receivers of [block] -public inline fun , R> A.listPolynomialSpace(block: ListPolynomialSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return ListPolynomialSpace(this).block() -} - -/** - * Creates a [ScalableListPolynomialSpace] over a received scalable ring. - */ -public inline val A.scalableListPolynomialSpace: ScalableListPolynomialSpace where A : Ring, A : ScaleOperations - get() = ScalableListPolynomialSpace(this) - -/** - * Creates a [ScalableListPolynomialSpace]'s scope over a received scalable ring. - */ // TODO: When context will be ready move [ListPolynomialSpace] and add [A] to context receivers of [block] -public inline fun A.scalableListPolynomialSpace(block: ScalableListPolynomialSpace.() -> R): R where A : Ring, A : ScaleOperations { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return ScalableListPolynomialSpace(this).block() -} - -/** - * Creates a [ListRationalFunctionSpace] over a received ring. - */ -public inline val > A.listRationalFunctionSpace: ListRationalFunctionSpace - get() = ListRationalFunctionSpace(this) - -/** - * Creates a [ListRationalFunctionSpace]'s scope over a received ring. - */ // TODO: When context will be ready move [ListRationalFunctionSpace] and add [A] to context receivers of [block] -public inline fun , R> A.listRationalFunctionSpace(block: ListRationalFunctionSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return ListRationalFunctionSpace(this).block() -} - - -/** - * Evaluates value of [this] Double polynomial on provided Double argument. - */ -public fun ListPolynomial.substitute(arg: Double): Double = - coefficients.reduceIndexedOrNull { index, acc, c -> - acc + c * arg.pow(index) - } ?: .0 - -/** - * Evaluates value of [this] polynomial on provided argument. - * - * It is an implementation of [Horner's method](https://en.wikipedia.org/wiki/Horner%27s_method). - */ -public fun ListPolynomial.substitute(ring: Ring, arg: C): C = ring { - if (coefficients.isEmpty()) return zero - var result: C = coefficients.last() - for (j in coefficients.size - 2 downTo 0) { - result = (arg * result) + coefficients[j] - } - return result -} - -/** - * Substitutes provided polynomial [arg] into [this] polynomial. - * - * It is an implementation of [Horner's method](https://en.wikipedia.org/wiki/Horner%27s_method). - */ // TODO: To optimize boxing -public fun ListPolynomial.substitute(ring: Ring, arg: ListPolynomial) : ListPolynomial = - ring.listPolynomialSpace { - if (coefficients.isEmpty()) return zero - var result: ListPolynomial = coefficients.last().asPolynomial() - for (j in coefficients.size - 2 downTo 0) { - result = (arg * result) + coefficients[j] - } - return result - } - -/** - * Substitutes provided rational function [arg] into [this] polynomial. - * - * It is an implementation of [Horner's method](https://en.wikipedia.org/wiki/Horner%27s_method). - */ // TODO: To optimize boxing -public fun ListPolynomial.substitute(ring: Ring, arg: ListRationalFunction) : ListRationalFunction = - ring.listRationalFunctionSpace { - if (coefficients.isEmpty()) return zero - var result: ListRationalFunction = coefficients.last().asRationalFunction() - for (j in coefficients.size - 2 downTo 0) { - result = (arg * result) + coefficients[j] - } - return result - } - -/** - * Evaluates value of [this] Double rational function in provided Double argument. - */ -public fun ListRationalFunction.substitute(arg: Double): Double = - numerator.substitute(arg) / denominator.substitute(arg) - -/** - * Evaluates value of [this] polynomial for provided argument. - * - * It is an implementation of [Horner's method](https://en.wikipedia.org/wiki/Horner%27s_method). - */ -public fun ListRationalFunction.substitute(ring: Field, arg: C): C = ring { - numerator.substitute(ring, arg) / denominator.substitute(ring, arg) -} - -/** - * Substitutes provided polynomial [arg] into [this] rational function. - */ // TODO: To optimize boxing -public fun ListRationalFunction.substitute(ring: Ring, arg: ListPolynomial) : ListRationalFunction = - ring.listRationalFunctionSpace { - numerator.substitute(ring, arg) / denominator.substitute(ring, arg) - } - -/** - * Substitutes provided rational function [arg] into [this] rational function. - */ // TODO: To optimize boxing -public fun ListRationalFunction.substitute(ring: Ring, arg: ListRationalFunction) : ListRationalFunction = - ring.listRationalFunctionSpace { - numerator.substitute(ring, arg) / denominator.substitute(ring, arg) - } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > ListPolynomial.asFunctionOver(ring: A): (C) -> C = { substitute(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > ListPolynomial.asFunctionOfConstantOver(ring: A): (C) -> C = { substitute(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > ListPolynomial.asFunctionOfPolynomialOver(ring: A): (ListPolynomial) -> ListPolynomial = { substitute(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > ListPolynomial.asFunctionOfRationalFunctionOver(ring: A): (ListRationalFunction) -> ListRationalFunction = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > ListRationalFunction.asFunctionOver(ring: A): (C) -> C = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > ListRationalFunction.asFunctionOfConstantOver(ring: A): (C) -> C = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > ListRationalFunction.asFunctionOfPolynomialOver(ring: A): (ListPolynomial) -> ListRationalFunction = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > ListRationalFunction.asFunctionOfRationalFunctionOver(ring: A): (ListRationalFunction) -> ListRationalFunction = { substitute(ring, it) } - -/** - * Returns algebraic derivative of received polynomial. - */ -@UnstableKMathAPI -public fun ListPolynomial.derivative( - ring: A, -): ListPolynomial where A : Ring, A : NumericAlgebra = ring { - ListPolynomial( - buildList(max(0, coefficients.size - 1)) { - for (deg in 1 .. coefficients.lastIndex) add(number(deg) * coefficients[deg]) - } - ) -} - -/** - * Returns algebraic derivative of received polynomial of specified [order]. The [order] should be non-negative integer. - */ -@UnstableKMathAPI -public fun ListPolynomial.nthDerivative( - ring: A, - order: Int, -): ListPolynomial where A : Ring, A : NumericAlgebra = ring { - require(order >= 0) { "Order of derivative must be non-negative" } - ListPolynomial( - buildList(max(0, coefficients.size - order)) { - for (deg in order.. coefficients.lastIndex) - add((deg - order + 1 .. deg).fold(coefficients[deg]) { acc, d -> acc * number(d) }) - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial. - */ -@UnstableKMathAPI -public fun ListPolynomial.antiderivative( - ring: A, -): ListPolynomial where A : Field, A : NumericAlgebra = ring { - ListPolynomial( - buildList(coefficients.size + 1) { - add(zero) - coefficients.mapIndexedTo(this) { index, t -> t / number(index + 1) } - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial of specified [order]. The [order] should be non-negative integer. - */ -@UnstableKMathAPI -public fun ListPolynomial.nthAntiderivative( - ring: A, - order: Int, -): ListPolynomial where A : Field, A : NumericAlgebra = ring { - require(order >= 0) { "Order of antiderivative must be non-negative" } - ListPolynomial( - buildList(coefficients.size + order) { - repeat(order) { add(zero) } - coefficients.mapIndexedTo(this) { index, c -> (1..order).fold(c) { acc, i -> acc / number(index + i) } } - } - ) -} - -/** - * Computes a definite integral of [this] polynomial in the specified [range]. - */ -@UnstableKMathAPI -public fun > ListPolynomial.integrate( - ring: Field, - range: ClosedRange, -): C = ring { - val antiderivative = antiderivative(ring) - antiderivative.substitute(ring, range.endInclusive) - antiderivative.substitute(ring, range.start) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/misc.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/misc.kt deleted file mode 100644 index 76f1c294e..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/misc.kt +++ /dev/null @@ -1,22 +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.functions - - -/** - * Marks declarations that give access to internal entities of polynomials delicate structure. Thus, it allows to - * optimize performance a bit by skipping standard steps, but such skips may cause critical errors if something is - * implemented badly. Make sure you fully read and understand documentation and don't break internal contracts. - */ -@RequiresOptIn( - message = "This declaration gives access to delicate internal structure of polynomials. " + - "It allows to optimize performance by skipping unnecessary arguments check. " + - "But at the same time makes it easy to make a mistake " + - "that will cause wrong computation result or even runtime error. " + - "Make sure you fully read and understand documentation.", - level = RequiresOptIn.Level.ERROR -) -public annotation class DelicatePolynomialAPI \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedConstructors.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedConstructors.kt deleted file mode 100644 index ce49088ae..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedConstructors.kt +++ /dev/null @@ -1,491 +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:Suppress("FunctionName", "NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Ring - - -/** - * Returns the same degrees' description of the monomial, but without extra zero degrees on the end. - */ -internal fun List.cleanUp() = subList(0, indexOfLast { it != 0U } + 1) - -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. The map is used as is. - */ -@PublishedApi -internal inline fun NumberedPolynomialAsIs(coefs: Map, C>) : NumberedPolynomial = NumberedPolynomial(coefs) - -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * The collections will be transformed to map with [toMap] and then will be used as is. - */ -@PublishedApi -internal inline fun NumberedPolynomialAsIs(pairs: Collection, C>>) : NumberedPolynomial = NumberedPolynomial(pairs.toMap()) - -/** - * Constructs [NumberedPolynomial] with provided array of [pairs] of pairs "term's signature — term's coefficient". - * The array will be transformed to map with [toMap] and then will be used as is. - */ -@PublishedApi -internal inline fun NumberedPolynomialAsIs(vararg pairs: Pair, C>) : NumberedPolynomial = NumberedPolynomial(pairs.toMap()) - -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. The map is used as is. - * - * **Be sure you read description of [NumberedPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun NumberedPolynomialWithoutCheck(coefs: Map, C>) : NumberedPolynomial = NumberedPolynomial(coefs) - -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * The collections will be transformed to map with [toMap] and then will be used as is. - * - * **Be sure you read description of [NumberedPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun NumberedPolynomialWithoutCheck(pairs: Collection, C>>) : NumberedPolynomial = NumberedPolynomial(pairs.toMap()) - -/** - * Constructs [NumberedPolynomial] with provided array of [pairs] of pairs "term's signature — term's coefficient". - * The array will be transformed to map with [toMap] and then will be used as is. - * - * **Be sure you read description of [NumberedPolynomial.coefficients]. Otherwise, you may make a mistake that will - * cause wrong computation result or even runtime error.** - */ -@DelicatePolynomialAPI -public inline fun NumberedPolynomialWithoutCheck(vararg pairs: Pair, C>) : NumberedPolynomial = NumberedPolynomial(pairs.toMap()) - -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public fun NumberedPolynomial(coefs: Map, C>, add: (C, C) -> C) : NumberedPolynomial = - NumberedPolynomialAsIs( - coefs.mapKeys({ key, _ -> key.cleanUp() }, add) - ) - -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public fun NumberedPolynomial(pairs: Collection, C>>, add: (C, C) -> C) : NumberedPolynomial = - NumberedPolynomialAsIs( - pairs.associateBy({ it.first.cleanUp() }, { it.second }, add) - ) - -/** - * Constructs [NumberedPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public fun NumberedPolynomial(vararg pairs: Pair, C>, add: (C, C) -> C) : NumberedPolynomial = - NumberedPolynomialAsIs( - pairs.asIterable().associateBy({ it.first.cleanUp() }, { it.second }, add) - ) - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > A.NumberedPolynomial(coefs: Map, C>) : NumberedPolynomial = NumberedPolynomial(coefs, ::add) -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > NumberedPolynomialSpace.NumberedPolynomial(coefs: Map, C>) : NumberedPolynomial = NumberedPolynomial(coefs) { left: C, right: C -> left + right } - -/** - * Constructs [NumberedPolynomial] with provided coefficients map [coefs]. - * - * [coefs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [coefs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > NumberedRationalFunctionSpace.NumberedPolynomial(coefs: Map, C>) : NumberedPolynomial = NumberedPolynomial(coefs) { left: C, right: C -> left + right } - -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > A.NumberedPolynomial(pairs: Collection, C>>) : NumberedPolynomial = NumberedPolynomial(pairs, ::add) - -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > NumberedPolynomialSpace.NumberedPolynomial(pairs: Collection, C>>) : NumberedPolynomial = NumberedPolynomial(pairs) { left: C, right: C -> left + right } -/** - * Constructs [NumberedPolynomial] with provided collection of [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public inline fun > NumberedRationalFunctionSpace.NumberedPolynomial(pairs: Collection, C>>) : NumberedPolynomial = NumberedPolynomial(pairs) { left: C, right: C -> left + right } - -/** - * Constructs [NumberedPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > A.NumberedPolynomial(vararg pairs: Pair, C>) : NumberedPolynomial = NumberedPolynomial(*pairs) { left: C, right: C -> left + right } -/** - * Constructs [NumberedPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > NumberedPolynomialSpace.NumberedPolynomial(vararg pairs: Pair, C>) : NumberedPolynomial = NumberedPolynomial(*pairs) { left: C, right: C -> left + right } -/** - * Constructs [NumberedPolynomial] with provided array [pairs] of pairs "term's signature — term's coefficient". - * - * [pairs] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [pairs] keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - * - * @see NumberedPolynomialWithoutCheck - */ -public inline fun > NumberedRationalFunctionSpace.NumberedPolynomial(vararg pairs: Pair, C>) : NumberedPolynomial = NumberedPolynomial(*pairs) { left: C, right: C -> left + right } - -/** - * Converts [this] constant to [NumberedPolynomial]. - */ -public inline fun C.asNumberedPolynomial() : NumberedPolynomial = NumberedPolynomialAsIs(mapOf(emptyList() to this)) - -/** - * Marks DSL that allows to more simply create [NumberedPolynomial]s with good performance. - * - * For example, polynomial \(5 x_0^2 x_2^3 - 6 x_1\) can be described as - * ``` - * Int.algebra { - * val numberedPolynomial : NumberedPolynomial = NumberedPolynomial { - * 5 { 0 inPowerOf 2u; 2 inPowerOf 3u } // 5 x_0^2 x_2^3 + - * (-6) { 1 inPowerOf 1u } // (-6) x_1^1 - * } - * } - * ``` - * @usesMathJax - */ -@DslMarker -@UnstableKMathAPI -internal annotation class NumberedPolynomialConstructorDSL1 - -/** - * Builder of [NumberedPolynomial] signature. It should be used as an implicit context for lambdas that describe term signature. - */ -@UnstableKMathAPI -@NumberedPolynomialConstructorDSL1 -public class DSL1NumberedPolynomialTermSignatureBuilder { - /** - * Signature storage. Any declaration of any variable's power updates the storage by increasing corresponding value. - * Afterward the storage will be used as a resulting signature. - */ - private val signature: MutableList = ArrayList() - - /** - * Builds the resulting signature. - * - * In fact, it just returns [signature] as regular signature of type `List`. - */ - @PublishedApi - internal fun build(): List = signature - - /** - * Declares power of variable #[this] of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public infix fun Int.inPowerOf(deg: UInt) { - if (deg == 0u) return - val index = this - if (index > signature.lastIndex) { - signature.addAll(List(index - signature.lastIndex - 1) { 0u }) - signature.add(deg) - } else { - signature[index] += deg - } - } - /** - * Declares power of variable #[this] of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Int.pow(deg: UInt): Unit = this inPowerOf deg - /** - * Declares power of variable #[this] of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Int.`in`(deg: UInt): Unit = this inPowerOf deg - /** - * Declares power of variable #[this] of degree [deg]. - * - * Declaring another power of the same variable will increase its degree by received degree. - */ - public inline infix fun Int.of(deg: UInt): Unit = this inPowerOf deg -} - -/** - * Builder of [NumberedPolynomial]. It should be used as an implicit context for lambdas that describe [NumberedPolynomial]. - */ -@UnstableKMathAPI -@NumberedPolynomialConstructorDSL1 -public class DSL1NumberedPolynomialBuilder( - /** - * Summation operation that will be used to sum coefficients of monomials of same signatures. - */ - private val add: (C, C) -> C, - /** - * Initial capacity of coefficients map. - */ - initialCapacity: Int? = null -) { - /** - * Coefficients storage. Any declaration of any monomial updates the storage. - * Afterward the storage will be used as a resulting coefficients map. - */ - private val coefficients: MutableMap, C> = if (initialCapacity != null) LinkedHashMap(initialCapacity) else LinkedHashMap() - - /** - * Builds the resulting coefficients map. - * - * In fact, it just returns [coefficients] as regular coefficients map of type `Map, C>`. - */ - @PublishedApi - internal fun build(): NumberedPolynomial = NumberedPolynomial(coefficients) - - /** - * Declares monomial with [this] coefficient and provided [signature]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public infix fun C.with(signature: List) { - coefficients.putOrChange(signature, this@with, add) - } - /** - * Declares monomial with [this] coefficient and signature constructed by [block]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public inline infix fun C.with(noinline block: DSL1NumberedPolynomialTermSignatureBuilder.() -> Unit): Unit = this.invoke(block) - /** - * Declares monomial with [this] coefficient and signature constructed by [block]. - * - * Declaring another monomial with the same signature will add [this] coefficient to existing one. If the sum of such - * coefficients is zero at any moment the monomial won't be removed but will be left as it is. - */ - public inline operator fun C.invoke(block: DSL1NumberedPolynomialTermSignatureBuilder.() -> Unit): Unit = - this with DSL1NumberedPolynomialTermSignatureBuilder().apply(block).build() -} - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -///** -// * Creates [NumberedPolynomial] with lambda [block] in context of [this] ring of constants. -// * -// * For example, polynomial \(5 x_0^2 x_2^3 - 6 x_1\) can be described as -// * ``` -// * Int.algebra { -// * val numberedPolynomial : NumberedPolynomial = NumberedPolynomial { -// * 5 { 0 inPowerOf 2u; 2 inPowerOf 3u } // 5 x_0^2 x_2^3 + -// * (-6) { 1 inPowerOf 1u } // (-6) x_1^1 -// * } -// * } -// * ``` -// * @usesMathJax -// */ -// FIXME: For now this fabric does not let next two fabrics work. (See KT-52803.) Possible feature solutions: -// 1. `LowPriorityInOverloadResolution` becomes public. Then it should be applied to this function. -// 2. Union types are implemented. Then all three functions should be rewritten -// as one with single union type as a (context) receiver. -//@UnstableKMathAPI -//public inline fun > A.NumberedPolynomialDSL1(initialCapacity: Int? = null, block: NumberedPolynomialBuilder.() -> Unit) : NumberedPolynomial = NumberedPolynomialBuilder(::add, initialCapacity).apply(block).build() -/** - * Creates [NumberedPolynomial] with lambda [block] in context of [this] ring of [NumberedPolynomial]s. - * - * For example, polynomial \(5 x_0^2 x_2^3 - 6 x_1\) can be described as - * ``` - * Int.algebra { - * val numberedPolynomial : NumberedPolynomial = NumberedPolynomial { - * 5 { 0 inPowerOf 2u; 2 inPowerOf 3u } // 5 x_0^2 x_2^3 + - * (-6) { 1 inPowerOf 1u } // (-6) x_1^1 - * } - * } - * ``` - * @usesMathJax - */ -@UnstableKMathAPI -public inline fun > NumberedPolynomialSpace.NumberedPolynomialDSL1(initialCapacity: Int? = null, block: DSL1NumberedPolynomialBuilder.() -> Unit) : NumberedPolynomial = DSL1NumberedPolynomialBuilder({ left: C, right: C -> left + right }, initialCapacity).apply(block).build() -/** - * Creates [NumberedPolynomial] with lambda [block] in context of [this] field of [NumberedRationalFunction]s. - * - * For example, polynomial \(5 x_0^2 x_2^3 - 6 x_1\) can be described as - * ``` - * Int.algebra { - * val numberedPolynomial : NumberedPolynomial = NumberedPolynomial { - * 5 { 0 inPowerOf 2u; 2 inPowerOf 3u } // 5 x_0^2 x_2^3 + - * (-6) { 1 inPowerOf 1u } // (-6) x_1^1 - * } - * } - * ``` - * @usesMathJax - */ -@UnstableKMathAPI -public inline fun > NumberedRationalFunctionSpace.NumberedPolynomialDSL1(initialCapacity: Int? = null, block: DSL1NumberedPolynomialBuilder.() -> Unit) : NumberedPolynomial = DSL1NumberedPolynomialBuilder({ left: C, right: C -> left + right }, initialCapacity).apply(block).build() - -// Waiting for context receivers :( FIXME: Replace with context receivers when they will be available - -/** - * Constructs [NumberedRationalFunction] with provided coefficients maps [numeratorCoefficients] and [denominatorCoefficients]. - * - * The maps will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. the maps' keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > A.NumberedRationalFunction(numeratorCoefficients: Map, C>, denominatorCoefficients: Map, C>): NumberedRationalFunction = - NumberedRationalFunction( - NumberedPolynomial(numeratorCoefficients), - NumberedPolynomial(denominatorCoefficients) - ) -/** - * Constructs [NumberedRationalFunction] with provided coefficients maps [numeratorCoefficients] and [denominatorCoefficients]. - * - * The maps will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. the maps' keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > NumberedRationalFunctionSpace.NumberedRationalFunction(numeratorCoefficients: Map, C>, denominatorCoefficients: Map, C>): NumberedRationalFunction = - NumberedRationalFunction( - NumberedPolynomial(numeratorCoefficients), - NumberedPolynomial(denominatorCoefficients) - ) - -/** - * Constructs [NumberedRationalFunction] with provided [numerator] and unit denominator. - */ -public fun > A.NumberedRationalFunction(numerator: NumberedPolynomial): NumberedRationalFunction = - NumberedRationalFunction(numerator, NumberedPolynomial(mapOf(emptyList() to one))) -/** - * Constructs [NumberedRationalFunction] with provided [numerator] and unit denominator. - */ -public fun > NumberedRationalFunctionSpace.NumberedRationalFunction(numerator: NumberedPolynomial): NumberedRationalFunction = - NumberedRationalFunction(numerator, polynomialOne) - -/** - * Constructs [NumberedRationalFunction] with provided coefficients map [numeratorCoefficients] for numerator and unit - * denominator. - * - * [numeratorCoefficients] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [numeratorCoefficients]'s keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > NumberedRationalFunctionSpace.NumberedRationalFunction(numeratorCoefficients: Map, C>): NumberedRationalFunction = - NumberedRationalFunction( - NumberedPolynomial(numeratorCoefficients), - polynomialOne - ) -/** - * Constructs [NumberedRationalFunction] with provided coefficients map [numeratorCoefficients] for numerator and unit - * denominator. - * - * [numeratorCoefficients] will be "cleaned up": - * 1. Zeros at the ends of terms' signatures (e.g. [numeratorCoefficients]'s keys) will be removed. (See [cleanUp].) - * 1. Terms that happen to have the same signature will be summed up. - * 1. New map will be formed of resulting terms. - */ -public fun > A.NumberedRationalFunction(numeratorCoefficients: Map, C>): NumberedRationalFunction = - NumberedRationalFunction( - NumberedPolynomial(numeratorCoefficients), - NumberedPolynomialAsIs(mapOf(emptyList() to one)) - ) - -///** -// * Converts [this] constant to [NumberedRationalFunction]. -// */ -//context(A) -//public fun > C.asNumberedRationalFunction() : NumberedRationalFunction = -// NumberedRationalFunction( -// NumberedPolynomialAsIs(mapOf(emptyList() to this)), -// NumberedPolynomialAsIs(mapOf(emptyList() to one)) -// ) -///** -// * Converts [this] constant to [NumberedRationalFunction]. -// */ -//context(NumberedRationalFunctionSpace) -//public fun > C.asNumberedRationalFunction() : NumberedRationalFunction = -// NumberedRationalFunction( -// NumberedPolynomialAsIs(mapOf(emptyList() to this)), -// NumberedPolynomialAsIs(mapOf(emptyList() to constantOne)) -// ) \ No newline at end of file diff --git a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedUtil.kt b/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedUtil.kt deleted file mode 100644 index 9f29cf31a..000000000 --- a/kmath-polynomial/src/commonMain/kotlin/space/kscience/kmath/functions/numberedUtil.kt +++ /dev/null @@ -1,513 +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.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Field -import space.kscience.kmath.operations.Ring -import space.kscience.kmath.operations.algebra -import space.kscience.kmath.operations.invoke -import space.kscience.kmath.structures.Buffer -import kotlin.contracts.InvocationKind -import kotlin.contracts.contract -import kotlin.jvm.JvmName -import kotlin.math.max -import kotlin.math.min - - -/** - * Creates a [NumberedPolynomialSpace] over a received ring. - */ -public inline val > A.numberedPolynomialSpace: NumberedPolynomialSpace - get() = NumberedPolynomialSpace(this) - -/** - * Creates a [NumberedPolynomialSpace]'s scope over a received ring. - */ -public inline fun , R> A.numberedPolynomialSpace(block: NumberedPolynomialSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return NumberedPolynomialSpace(this).block() -} - -/** - * Creates a [NumberedRationalFunctionSpace] over a received ring. - */ -public inline val > A.numberedRationalFunctionSpace: NumberedRationalFunctionSpace - get() = NumberedRationalFunctionSpace(this) - -/** - * Creates a [NumberedRationalFunctionSpace]'s scope over a received ring. - */ -public inline fun , R> A.numberedRationalFunctionSpace(block: NumberedRationalFunctionSpace.() -> R): R { - contract { callsInPlace(block, InvocationKind.EXACTLY_ONCE) } - return NumberedRationalFunctionSpace(this).block() -} - -/** - * Substitutes provided Double arguments [args] into [this] Double polynomial. - */ -public fun NumberedPolynomial.substitute(args: Map): NumberedPolynomial = Double.algebra { - NumberedPolynomial( - buildMap(coefficients.size) { - for ((degs, c) in coefficients) { - val newDegs = degs.mapIndexed { index, deg -> if (index !in args) deg else 0u }.cleanUp() - val newC = args.entries.fold(c) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * substitution.pow(deg.toInt()) - } - putOrChange(newDegs, newC) { it -> it + newC } - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ -public fun NumberedPolynomial.substitute(ring: Ring, args: Map): NumberedPolynomial = ring { - NumberedPolynomial( - buildMap(coefficients.size) { - for ((degs, c) in coefficients) { - val newDegs = degs.mapIndexed { index, deg -> if (index !in args) deg else 0u }.cleanUp() - val newC = args.entries.fold(c) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - putOrChange(newDegs, newC) { it -> it + newC } - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substitutePolynomial") -public fun NumberedPolynomial.substitute(ring: Ring, args: Map>) : NumberedPolynomial = - ring.numberedPolynomialSpace { - coefficients.entries.fold(zero) { acc, (degs, c) -> - val newDegs = degs.mapIndexed { index, deg -> if (index !in args) deg else 0u }.cleanUp() - acc + args.entries.fold(NumberedPolynomial(mapOf(newDegs to c))) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - } - } - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substituteRationalFunction") -public fun NumberedPolynomial.substitute(ring: Ring, args: Map>) : NumberedRationalFunction = - ring.numberedRationalFunctionSpace { - coefficients.entries.fold(zero) { acc, (degs, c) -> - val newDegs = degs.mapIndexed { index, deg -> if (index !in args) deg else 0u }.cleanUp() - acc + args.entries.fold(NumberedRationalFunction(NumberedPolynomial(mapOf(newDegs to c)))) { product, (variable, substitution) -> - val deg = degs.getOrElse(variable) { 0u } - if (deg == 0u) product else product * power(substitution, deg) - } - } - } - -/** - * Substitutes provided Double arguments [args] into [this] Double rational function. - */ -public fun NumberedRationalFunction.substitute(args: Map): NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(args), denominator.substitute(args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ -public fun NumberedRationalFunction.substitute(ring: Ring, args: Map): NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substitutePolynomial") -public fun NumberedRationalFunction.substitute(ring: Ring, args: Map>) : NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substituteRationalFunction") -public fun NumberedRationalFunction.substitute(ring: Ring, args: Map>) : NumberedRationalFunction = - ring.numberedRationalFunctionSpace { - numerator.substitute(ring, args) / denominator.substitute(ring, args) - } - -/** - * Substitutes provided Double arguments [args] into [this] Double polynomial. - */ -public fun NumberedPolynomial.substitute(args: Buffer): NumberedPolynomial = Double.algebra { - val lastSubstitutionVariable = args.size - 1 - NumberedPolynomial( - buildMap(coefficients.size) { - for ((degs, c) in coefficients) { - val lastDegsIndex = degs.lastIndex - val newDegs = - if (lastDegsIndex <= lastSubstitutionVariable) emptyList() - else degs.toMutableList().apply { - for (i in 0..lastSubstitutionVariable) this[i] = 0u - } - val newC = (0..min(lastDegsIndex, lastSubstitutionVariable)).fold(c) { product, variable -> - val deg = degs[variable] - if (deg == 0u) product else product * args[variable].pow(deg.toInt()) - } - putOrChange(newDegs, newC) { it -> it + newC } - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ -public fun NumberedPolynomial.substitute(ring: Ring, args: Buffer): NumberedPolynomial = ring { - val lastSubstitutionVariable = args.size - 1 - NumberedPolynomial( - buildMap, C>(coefficients.size) { - for ((degs, c) in coefficients) { - val lastDegsIndex = degs.lastIndex - val newDegs = - if (lastDegsIndex <= lastSubstitutionVariable) emptyList() - else degs.toMutableList().apply { - for (i in 0..lastSubstitutionVariable) this[i] = 0u - } - val newC = (0..min(lastDegsIndex, lastSubstitutionVariable)).fold(c) { product, variable -> - val deg = degs[variable] - if (deg == 0u) product else product * power(args[variable], deg) - } - putOrChange(newDegs, newC) { it -> it + newC } - } - } - ) -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substitutePolynomial") -public fun NumberedPolynomial.substitute(ring: Ring, args: Buffer>) : NumberedPolynomial = - ring.numberedPolynomialSpace { - val lastSubstitutionVariable = args.size - 1 - coefficients.entries.fold(zero) { acc, (degs, c) -> - val lastDegsIndex = degs.lastIndex - val newDegs = - if (lastDegsIndex <= lastSubstitutionVariable) emptyList() - else degs.toMutableList().apply { - for (i in 0..lastSubstitutionVariable) this[i] = 0u - } - acc + (0..min(lastDegsIndex, lastSubstitutionVariable)) - .fold(NumberedPolynomial(mapOf(newDegs to c))) { product, variable -> - val deg = degs[variable] - if (deg == 0u) product else product * power(args[variable], deg) - } - } - } - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ // TODO: To optimize boxing -@JvmName("substituteRationalFunction") -public fun NumberedPolynomial.substitute(ring: Ring, args: Buffer>) : NumberedRationalFunction = - ring.numberedRationalFunctionSpace { - val lastSubstitutionVariable = args.size - 1 - coefficients.entries.fold(zero) { acc, (degs, c) -> - val lastDegsIndex = degs.lastIndex - val newDegs = - if (lastDegsIndex <= lastSubstitutionVariable) emptyList() - else degs.toMutableList().apply { - for (i in 0..lastSubstitutionVariable) this[i] = 0u - } - acc + (0..min(lastDegsIndex, lastSubstitutionVariable)) - .fold(NumberedRationalFunction(NumberedPolynomial(mapOf(newDegs to c)))) { product, variable -> - val deg = degs[variable] - if (deg == 0u) product else product * power(args[variable], deg) - } - } - } - -/** - * Substitutes provided Double arguments [args] into [this] Double rational function. - */ -public fun NumberedRationalFunction.substitute(args: Buffer): NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(args), denominator.substitute(args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ -public fun NumberedRationalFunction.substitute(ring: Ring, args: Buffer): NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substitutePolynomial") -public fun NumberedRationalFunction.substitute(ring: Ring, args: Buffer>) : NumberedRationalFunction = - NumberedRationalFunction(numerator.substitute(ring, args), denominator.substitute(ring, args)) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ // TODO: To optimize calculation -@JvmName("substituteRationalFunction") -public fun NumberedRationalFunction.substitute(ring: Ring, args: Buffer>) : NumberedRationalFunction = - ring.numberedRationalFunctionSpace { - numerator.substitute(ring, args) / denominator.substitute(ring, args) - } - -internal const val fullSubstitutionExceptionMessage: String = "Fully substituting buffer should cover all variables of the polynomial." - -/** - * Substitutes provided Double arguments [args] into [this] Double polynomial. - */ -public fun NumberedPolynomial.substituteFully(args: Buffer): Double = Double.algebra { - val lastSubstitutionVariable = args.size - 1 - require(coefficients.keys.all { it.lastIndex <= lastSubstitutionVariable }) { fullSubstitutionExceptionMessage } - coefficients.entries.fold(.0) { acc, (degs, c) -> - acc + degs.foldIndexed(c) { variable, product, deg -> - if (deg == 0u) product else product * args[variable].pow(deg.toInt()) - } - } -} - -/** - * Substitutes provided arguments [args] into [this] polynomial. - */ -public fun NumberedPolynomial.substituteFully(ring: Ring, args: Buffer): C = ring { - val lastSubstitutionVariable = args.size - 1 - require(coefficients.keys.all { it.lastIndex <= lastSubstitutionVariable }) { fullSubstitutionExceptionMessage } - coefficients.entries.fold(zero) { acc, (degs, c) -> - acc + degs.foldIndexed(c) { variable, product, deg -> - if (deg == 0u) product else product * power(args[variable], deg) - } - } -} - -/** - * Substitutes provided Double arguments [args] into [this] Double rational function. - */ -public fun NumberedRationalFunction.substituteFully(args: Buffer): Double = - numerator.substituteFully(args) / denominator.substituteFully(args) - -/** - * Substitutes provided arguments [args] into [this] rational function. - */ -public fun NumberedRationalFunction.substituteFully(ring: Field, args: Buffer): C = ring { - numerator.substituteFully(ring, args) / denominator.substituteFully(ring, args) -} - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > NumberedPolynomial.asFunctionOver(ring: A): (Buffer) -> C = { substituteFully(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > NumberedPolynomial.asFunctionOfConstantOver(ring: A): (Buffer) -> C = { substituteFully(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > NumberedPolynomial.asFunctionOfPolynomialOver(ring: A): (Buffer>) -> NumberedPolynomial = { substitute(ring, it) } - -/** - * Represent [this] polynomial as a regular context-less function. - */ -public fun > NumberedPolynomial.asFunctionOfRationalFunctionOver(ring: A): (Buffer>) -> NumberedRationalFunction = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > NumberedRationalFunction.asFunctionOver(ring: A): (Buffer) -> C = { substituteFully(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > NumberedRationalFunction.asFunctionOfConstantOver(ring: A): (Buffer) -> C = { substituteFully(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > NumberedRationalFunction.asFunctionOfPolynomialOver(ring: A): (Buffer>) -> NumberedRationalFunction = { substitute(ring, it) } - -/** - * Represent [this] rational function as a regular context-less function. - */ -public fun > NumberedRationalFunction.asFunctionOfRationalFunctionOver(ring: A): (Buffer>) -> NumberedRationalFunction = { substitute(ring, it) } - -/** - * Returns algebraic derivative of received polynomial with respect to provided variable. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.derivativeWithRespectTo( - ring: A, - variable: Int, -): NumberedPolynomial = ring { - NumberedPolynomial( - buildMap(coefficients.count { it.key.getOrElse(variable) { 0u } >= 1u }) { - coefficients - .forEach { (degs, c) -> - if (degs.lastIndex < variable) return@forEach - put( - degs.mapIndexed { index, deg -> - when { - index != variable -> deg - deg > 0u -> deg - 1u - else -> return@forEach - } - }.cleanUp(), - multiplyByDoubling(c, degs[variable]) - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variable of specified order. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.nthDerivativeWithRespectTo( - ring: A, - variable: Int, - order: UInt -): NumberedPolynomial = ring { - if (order == 0u) return this@nthDerivativeWithRespectTo - NumberedPolynomial( - buildMap(coefficients.count { it.key.getOrElse(variable) { 0u } >= order }) { - coefficients - .forEach { (degs, c) -> - if (degs.lastIndex < variable) return@forEach - put( - degs.mapIndexed { index, deg -> - when { - index != variable -> deg - deg >= order -> deg - order - else -> return@forEach - } - }.cleanUp(), - degs[variable].let { deg -> - (deg downTo deg - order + 1u) - .fold(c) { acc, ord -> multiplyByDoubling(acc, ord) } - } - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variables of specified orders. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.nthDerivativeWithRespectTo( - ring: A, - variablesAndOrders: Map, -): NumberedPolynomial = ring { - val filteredVariablesAndOrders = variablesAndOrders.filterValues { it != 0u } - if (filteredVariablesAndOrders.isEmpty()) return this@nthDerivativeWithRespectTo - val maxRespectedVariable = filteredVariablesAndOrders.keys.maxOrNull()!! - NumberedPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - if (degs.lastIndex < maxRespectedVariable) return@forEach - put( - degs.mapIndexed { index, deg -> - if (index !in filteredVariablesAndOrders) return@mapIndexed deg - val order = filteredVariablesAndOrders[index]!! - if (deg >= order) deg - order else return@forEach - }.cleanUp(), - filteredVariablesAndOrders.entries.fold(c) { acc1, (index, order) -> - degs[index].let { deg -> - (deg downTo deg - order + 1u) - .fold(acc1) { acc2, ord -> multiplyByDoubling(acc2, ord) } - } - } - ) - } - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial with respect to provided variable. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.antiderivativeWithRespectTo( - ring: A, - variable: Int, -): NumberedPolynomial = ring { - NumberedPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - put( - List(max(variable + 1, degs.size)) { degs.getOrElse(it) { 0u } + if (it != variable) 0u else 1u }, - c / multiplyByDoubling(one, degs.getOrElse(variable) { 0u } + 1u) - ) - } - } - ) -} - -/** - * Returns algebraic antiderivative of received polynomial with respect to provided variable of specified order. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.nthAntiderivativeWithRespectTo( - ring: A, - variable: Int, - order: UInt -): NumberedPolynomial = ring { - if (order == 0u) return this@nthAntiderivativeWithRespectTo - NumberedPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - put( - List(max(variable + 1, degs.size)) { degs.getOrElse(it) { 0u } + if (it != variable) 0u else order }, - degs.getOrElse(variable) { 0u }.let { deg -> - (deg + 1u .. deg + order) - .fold(c) { acc, ord -> acc / multiplyByDoubling(one, ord) } - } - ) - } - } - ) -} - -/** - * Returns algebraic derivative of received polynomial with respect to provided variables of specified orders. - */ -@UnstableKMathAPI -public fun > NumberedPolynomial.nthAntiderivativeWithRespectTo( - ring: A, - variablesAndOrders: Map, -): NumberedPolynomial = ring { - val filteredVariablesAndOrders = variablesAndOrders.filterValues { it != 0u } - if (filteredVariablesAndOrders.isEmpty()) return this@nthAntiderivativeWithRespectTo - val maxRespectedVariable = filteredVariablesAndOrders.keys.maxOrNull()!! - NumberedPolynomial( - buildMap(coefficients.size) { - coefficients - .forEach { (degs, c) -> - put( - List(max(maxRespectedVariable + 1, degs.size)) { degs.getOrElse(it) { 0u } + filteredVariablesAndOrders.getOrElse(it) { 0u } }, - filteredVariablesAndOrders.entries.fold(c) { acc1, (variable, order) -> - degs.getOrElse(variable) { 0u }.let { deg -> - (deg + 1u .. deg + order) - .fold(acc1) { acc, ord -> acc / multiplyByDoubling(one, ord) } - } - } - ) - } - } - ) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/AlgebraicStubTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/AlgebraicStubTest.kt deleted file mode 100644 index 487cd9ee1..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/AlgebraicStubTest.kt +++ /dev/null @@ -1,589 +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.functions - - -import space.kscience.kmath.operations.invoke -import space.kscience.kmath.operations.Field -import kotlin.jvm.JvmInline -import kotlin.test.Test -import kotlin.test.assertEquals - -@JvmInline -value class Expr(val expr: String) - -object ExprRing : Field { - override fun Expr.unaryMinus(): Expr = Expr("-${expr}") - override fun add(left: Expr, right: Expr): Expr = Expr("(${left.expr} + ${right.expr})") - override fun multiply(left: Expr, right: Expr): Expr = Expr("(${left.expr} * ${right.expr})") - override val zero: Expr = Expr("0") - override val one: Expr = Expr("1") - override fun divide(left: Expr, right: Expr): Expr = Expr("(${left.expr} / ${right.expr})") - override fun scale(a: Expr, value: Double): Expr = Expr("(${a.expr} / $value)") -} - -class AlgebraicStubTest { - @Test - fun test_addMultipliedBySquaring_for_UInt() { - ExprRing { - assertEquals( - "57", - addMultipliedByDoubling(Expr("57"), Expr("179"), 0u).expr, - "tried addMultipliedBySquaring(57, 179, 0u)" - ) - assertEquals( - "(57 + 179)", - addMultipliedByDoubling(Expr("57"), Expr("179"), 1u).expr, - "tried addMultipliedBySquaring(57, 179, 1u)" - ) - assertEquals( - "(57 + (179 + 179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 2u).expr, - "tried addMultipliedBySquaring(57, 179, 2u)" - ) - assertEquals( - "((57 + 179) + (179 + 179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 3u).expr, - "tried addMultipliedBySquaring(57, 179, 3u)" - ) - assertEquals( - "(57 + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 4u).expr, - "tried addMultipliedBySquaring(57, 179, 4u)" - ) - assertEquals( - "((57 + 179) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 5u).expr, - "tried addMultipliedBySquaring(57, 179, 5u)" - ) - assertEquals( - "((57 + (179 + 179)) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 6u).expr, - "tried addMultipliedBySquaring(57, 179, 6u)" - ) - assertEquals( - "(((57 + 179) + (179 + 179)) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 7u).expr, - "tried addMultipliedBySquaring(57, 179, 7u)" - ) - assertEquals( - "(57 + (((179 + 179) + (179 + 179)) + ((179 + 179) + (179 + 179))))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 8u).expr, - "tried addMultipliedBySquaring(57, 179, 8u)" - ) - } - } - @Test - fun test_multiplyBySquaring_for_UInt() { - ExprRing { - assertEquals( - "0", - multiplyByDoubling(Expr("57"), 0u).expr, - "tried multiplyBySquaring(57, 0u)" - ) - assertEquals( - "57", - multiplyByDoubling(Expr("57"), 1u).expr, - "tried multiplyBySquaring(57, 1u)" - ) - assertEquals( - "(57 + 57)", - multiplyByDoubling(Expr("57"), 2u).expr, - "tried multiplyBySquaring(57, 2u)" - ) - assertEquals( - "(57 + (57 + 57))", - multiplyByDoubling(Expr("57"), 3u).expr, - "tried multiplyBySquaring(57, 3u)" - ) - assertEquals( - "((57 + 57) + (57 + 57))", - multiplyByDoubling(Expr("57"), 4u).expr, - "tried multiplyBySquaring(57, 4u)" - ) - assertEquals( - "(57 + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 5u).expr, - "tried multiplyBySquaring(57, 5u)" - ) - assertEquals( - "((57 + 57) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 6u).expr, - "tried multiplyBySquaring(57, 6u)" - ) - assertEquals( - "((57 + (57 + 57)) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 7u).expr, - "tried multiplyBySquaring(57, 7u)" - ) - assertEquals( - "(((57 + 57) + (57 + 57)) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 8u).expr, - "tried multiplyBySquaring(57, 8u)" - ) - } - } - @Test - fun test_addMultipliedBySquaring_for_Int() { - ExprRing { - assertEquals( - "57", - addMultipliedByDoubling(Expr("57"), Expr("179"), 0).expr, - "tried addMultipliedBySquaring(57, 179, 0)" - ) - assertEquals( - "(57 + 179)", - addMultipliedByDoubling(Expr("57"), Expr("179"), 1).expr, - "tried addMultipliedBySquaring(57, 179, 1)" - ) - assertEquals( - "(57 + -179)", - addMultipliedByDoubling(Expr("57"), Expr("179"), -1).expr, - "tried addMultipliedBySquaring(57, 179, -1)" - ) - assertEquals( - "(57 + (179 + 179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 2).expr, - "tried addMultipliedBySquaring(57, 179, 2)" - ) - assertEquals( - "(57 + (-179 + -179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -2).expr, - "tried addMultipliedBySquaring(57, 179, -2)" - ) - assertEquals( - "((57 + 179) + (179 + 179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 3).expr, - "tried addMultipliedBySquaring(57, 179, 3)" - ) - assertEquals( - "((57 + -179) + (-179 + -179))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -3).expr, - "tried addMultipliedBySquaring(57, 179, -3)" - ) - assertEquals( - "(57 + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 4).expr, - "tried addMultipliedBySquaring(57, 179, 4)" - ) - assertEquals( - "(57 + ((-179 + -179) + (-179 + -179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -4).expr, - "tried addMultipliedBySquaring(57, 179, -4)" - ) - assertEquals( - "((57 + 179) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 5).expr, - "tried addMultipliedBySquaring(57, 179, 5)" - ) - assertEquals( - "((57 + -179) + ((-179 + -179) + (-179 + -179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -5).expr, - "tried addMultipliedBySquaring(57, 179, -5)" - ) - assertEquals( - "((57 + (179 + 179)) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 6).expr, - "tried addMultipliedBySquaring(57, 179, 6)" - ) - assertEquals( - "((57 + (-179 + -179)) + ((-179 + -179) + (-179 + -179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -6).expr, - "tried addMultipliedBySquaring(57, 179, -6)" - ) - assertEquals( - "(((57 + 179) + (179 + 179)) + ((179 + 179) + (179 + 179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 7).expr, - "tried addMultipliedBySquaring(57, 179, 7)" - ) - assertEquals( - "(((57 + -179) + (-179 + -179)) + ((-179 + -179) + (-179 + -179)))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -7).expr, - "tried addMultipliedBySquaring(57, 179, -7)" - ) - assertEquals( - "(57 + (((179 + 179) + (179 + 179)) + ((179 + 179) + (179 + 179))))", - addMultipliedByDoubling(Expr("57"), Expr("179"), 8).expr, - "tried addMultipliedBySquaring(57, 179, 8)" - ) - assertEquals( - "(57 + (((-179 + -179) + (-179 + -179)) + ((-179 + -179) + (-179 + -179))))", - addMultipliedByDoubling(Expr("57"), Expr("179"), -8).expr, - "tried addMultipliedBySquaring(57, 179, -8)" - ) - } - } - @Test - fun test_multiplyBySquaring_for_Int() { - ExprRing { - assertEquals( - "0", - multiplyByDoubling(Expr("57"), 0).expr, - "tried multiplyBySquaring(57, 0)" - ) - assertEquals( - "57", - multiplyByDoubling(Expr("57"), 1).expr, - "tried multiplyBySquaring(57, 1)" - ) - assertEquals( - "-57", - multiplyByDoubling(Expr("57"), -1).expr, - "tried multiplyBySquaring(57, -1)" - ) - assertEquals( - "(57 + 57)", - multiplyByDoubling(Expr("57"), 2).expr, - "tried multiplyBySquaring(57, 2)" - ) - assertEquals( - "(-57 + -57)", - multiplyByDoubling(Expr("57"), -2).expr, - "tried multiplyBySquaring(57, -2)" - ) - assertEquals( - "(57 + (57 + 57))", - multiplyByDoubling(Expr("57"), 3).expr, - "tried multiplyBySquaring(57, 3)" - ) - assertEquals( - "(-57 + (-57 + -57))", - multiplyByDoubling(Expr("57"), -3).expr, - "tried multiplyBySquaring(57, -3)" - ) - assertEquals( - "((57 + 57) + (57 + 57))", - multiplyByDoubling(Expr("57"), 4).expr, - "tried multiplyBySquaring(57, 4)" - ) - assertEquals( - "((-57 + -57) + (-57 + -57))", - multiplyByDoubling(Expr("57"), -4).expr, - "tried multiplyBySquaring(57, -4)" - ) - assertEquals( - "(57 + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 5).expr, - "tried multiplyBySquaring(57, 5)" - ) - assertEquals( - "(-57 + ((-57 + -57) + (-57 + -57)))", - multiplyByDoubling(Expr("57"), -5).expr, - "tried multiplyBySquaring(57, -5)" - ) - assertEquals( - "((57 + 57) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 6).expr, - "tried multiplyBySquaring(57, 6)" - ) - assertEquals( - "((-57 + -57) + ((-57 + -57) + (-57 + -57)))", - multiplyByDoubling(Expr("57"), -6).expr, - "tried multiplyBySquaring(57, -6)" - ) - assertEquals( - "((57 + (57 + 57)) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 7).expr, - "tried multiplyBySquaring(57, 7)" - ) - assertEquals( - "((-57 + (-57 + -57)) + ((-57 + -57) + (-57 + -57)))", - multiplyByDoubling(Expr("57"), -7).expr, - "tried multiplyBySquaring(57, -7)" - ) - assertEquals( - "(((57 + 57) + (57 + 57)) + ((57 + 57) + (57 + 57)))", - multiplyByDoubling(Expr("57"), 8).expr, - "tried multiplyBySquaring(57, 8)" - ) - assertEquals( - "(((-57 + -57) + (-57 + -57)) + ((-57 + -57) + (-57 + -57)))", - multiplyByDoubling(Expr("57"), -8).expr, - "tried multiplyBySquaring(57, -8)" - ) - } - } - @Test - fun test_multiplyExponentiationBySquaring_for_UInt() { - ExprRing { - assertEquals( - "57", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 0u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 0u)" - ) - assertEquals( - "(57 * 179)", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 1u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 1u)" - ) - assertEquals( - "(57 * (179 * 179))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 2u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 2u)" - ) - assertEquals( - "((57 * 179) * (179 * 179))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 3u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 3u)" - ) - assertEquals( - "(57 * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 4u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 4u)" - ) - assertEquals( - "((57 * 179) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 5u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 5u)" - ) - assertEquals( - "((57 * (179 * 179)) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 6u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 6u)" - ) - assertEquals( - "(((57 * 179) * (179 * 179)) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 7u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 7u)" - ) - assertEquals( - "(57 * (((179 * 179) * (179 * 179)) * ((179 * 179) * (179 * 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 8u).expr, - "tried multiplyExponentiationBySquaring(57, 179, 8u)" - ) - } - } - @Test - fun test_exponentiationBySquaring_for_UInt() { - ExprRing { - assertEquals( - "0", - exponentiateBySquaring(Expr("57"), 0u).expr, - "tried exponentiationBySquaring(57, 0u)" - ) - assertEquals( - "57", - exponentiateBySquaring(Expr("57"), 1u).expr, - "tried exponentiationBySquaring(57, 1u)" - ) - assertEquals( - "(57 * 57)", - exponentiateBySquaring(Expr("57"), 2u).expr, - "tried exponentiationBySquaring(57, 2u)" - ) - assertEquals( - "(57 * (57 * 57))", - exponentiateBySquaring(Expr("57"), 3u).expr, - "tried exponentiationBySquaring(57, 3u)" - ) - assertEquals( - "((57 * 57) * (57 * 57))", - exponentiateBySquaring(Expr("57"), 4u).expr, - "tried exponentiationBySquaring(57, 4u)" - ) - assertEquals( - "(57 * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 5u).expr, - "tried exponentiationBySquaring(57, 5u)" - ) - assertEquals( - "((57 * 57) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 6u).expr, - "tried exponentiationBySquaring(57, 6u)" - ) - assertEquals( - "((57 * (57 * 57)) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 7u).expr, - "tried exponentiationBySquaring(57, 7u)" - ) - assertEquals( - "(((57 * 57) * (57 * 57)) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 8u).expr, - "tried exponentiationBySquaring(57, 8u)" - ) - } - } - @Test - fun test_multiplyExponentiationBySquaring_for_Int() { - ExprRing { - assertEquals( - "57", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 0).expr, - "tried multiplyExponentiationBySquaring(57, 179, 0)" - ) - assertEquals( - "(57 * 179)", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 1).expr, - "tried multiplyExponentiationBySquaring(57, 179, 1)" - ) - assertEquals( - "(57 * (1 / 179))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -1).expr, - "tried multiplyExponentiationBySquaring(57, 179, -1)" - ) - assertEquals( - "(57 * (179 * 179))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 2).expr, - "tried multiplyExponentiationBySquaring(57, 179, 2)" - ) - assertEquals( - "(57 * ((1 / 179) * (1 / 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -2).expr, - "tried multiplyExponentiationBySquaring(57, 179, -2)" - ) - assertEquals( - "((57 * 179) * (179 * 179))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 3).expr, - "tried multiplyExponentiationBySquaring(57, 179, 3)" - ) - assertEquals( - "((57 * (1 / 179)) * ((1 / 179) * (1 / 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -3).expr, - "tried multiplyExponentiationBySquaring(57, 179, -3)" - ) - assertEquals( - "(57 * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 4).expr, - "tried multiplyExponentiationBySquaring(57, 179, 4)" - ) - assertEquals( - "(57 * (((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -4).expr, - "tried multiplyExponentiationBySquaring(57, 179, -4)" - ) - assertEquals( - "((57 * 179) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 5).expr, - "tried multiplyExponentiationBySquaring(57, 179, 5)" - ) - assertEquals( - "((57 * (1 / 179)) * (((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -5).expr, - "tried multiplyExponentiationBySquaring(57, 179, -5)" - ) - assertEquals( - "((57 * (179 * 179)) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 6).expr, - "tried multiplyExponentiationBySquaring(57, 179, 6)" - ) - assertEquals( - "((57 * ((1 / 179) * (1 / 179))) * (((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -6).expr, - "tried multiplyExponentiationBySquaring(57, 179, -6)" - ) - assertEquals( - "(((57 * 179) * (179 * 179)) * ((179 * 179) * (179 * 179)))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 7).expr, - "tried multiplyExponentiationBySquaring(57, 179, 7)" - ) - assertEquals( - "(((57 * (1 / 179)) * ((1 / 179) * (1 / 179))) * (((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -7).expr, - "tried multiplyExponentiationBySquaring(57, 179, -7)" - ) - assertEquals( - "(57 * (((179 * 179) * (179 * 179)) * ((179 * 179) * (179 * 179))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), 8).expr, - "tried multiplyExponentiationBySquaring(57, 179, 8)" - ) - assertEquals( - "(57 * ((((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179))) * (((1 / 179) * (1 / 179)) * ((1 / 179) * (1 / 179)))))", - multiplyExponentiatedBySquaring(Expr("57"), Expr("179"), -8).expr, - "tried multiplyExponentiationBySquaring(57, 179, -8)" - ) - } - } - @Test - fun test_exponentiationBySquaring_for_Int() { - ExprRing { - assertEquals( - "0", - exponentiateBySquaring(Expr("57"), 0).expr, - "tried exponentiationBySquaring(57, 0)" - ) - assertEquals( - "57", - exponentiateBySquaring(Expr("57"), 1).expr, - "tried exponentiationBySquaring(57, 1)" - ) - assertEquals( - "(1 / 57)", - exponentiateBySquaring(Expr("57"), -1).expr, - "tried exponentiationBySquaring(57, -1)" - ) - assertEquals( - "(57 * 57)", - exponentiateBySquaring(Expr("57"), 2).expr, - "tried exponentiationBySquaring(57, 2)" - ) - assertEquals( - "((1 / 57) * (1 / 57))", - exponentiateBySquaring(Expr("57"), -2).expr, - "tried exponentiationBySquaring(57, -2)" - ) - assertEquals( - "(57 * (57 * 57))", - exponentiateBySquaring(Expr("57"), 3).expr, - "tried exponentiationBySquaring(57, 3)" - ) - assertEquals( - "((1 / 57) * ((1 / 57) * (1 / 57)))", - exponentiateBySquaring(Expr("57"), -3).expr, - "tried exponentiationBySquaring(57, -3)" - ) - assertEquals( - "((57 * 57) * (57 * 57))", - exponentiateBySquaring(Expr("57"), 4).expr, - "tried exponentiationBySquaring(57, 4)" - ) - assertEquals( - "(((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57)))", - exponentiateBySquaring(Expr("57"), -4).expr, - "tried exponentiationBySquaring(57, -4)" - ) - assertEquals( - "(57 * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 5).expr, - "tried exponentiationBySquaring(57, 5)" - ) - assertEquals( - "((1 / 57) * (((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57))))", - exponentiateBySquaring(Expr("57"), -5).expr, - "tried exponentiationBySquaring(57, -5)" - ) - assertEquals( - "((57 * 57) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 6).expr, - "tried exponentiationBySquaring(57, 6)" - ) - assertEquals( - "(((1 / 57) * (1 / 57)) * (((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57))))", - exponentiateBySquaring(Expr("57"), -6).expr, - "tried exponentiationBySquaring(57, -6)" - ) - assertEquals( - "((57 * (57 * 57)) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 7).expr, - "tried exponentiationBySquaring(57, 7)" - ) - assertEquals( - "(((1 / 57) * ((1 / 57) * (1 / 57))) * (((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57))))", - exponentiateBySquaring(Expr("57"), -7).expr, - "tried exponentiationBySquaring(57, -7)" - ) - assertEquals( - "(((57 * 57) * (57 * 57)) * ((57 * 57) * (57 * 57)))", - exponentiateBySquaring(Expr("57"), 8).expr, - "tried exponentiationBySquaring(57, 8)" - ) - assertEquals( - "((((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57))) * (((1 / 57) * (1 / 57)) * ((1 / 57) * (1 / 57))))", - exponentiateBySquaring(Expr("57"), -8).expr, - "tried exponentiationBySquaring(57, -8)" - ) - } - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledConstructorsTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledConstructorsTest.kt deleted file mode 100644 index 80476050b..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledConstructorsTest.kt +++ /dev/null @@ -1,127 +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.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.functions.testUtils.t -import space.kscience.kmath.functions.testUtils.x -import space.kscience.kmath.functions.testUtils.y -import space.kscience.kmath.functions.testUtils.z -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.algebra -import space.kscience.kmath.operations.invoke -import kotlin.test.Test -import kotlin.test.assertEquals - -class LabeledConstructorsTest { - @Test - @UnstableKMathAPI - fun testDSL1() { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u, z to 3u) to 5, - mapOf(y to 1u) to -6, - ), - Int.algebra.labeledPolynomialSpace { - LabeledPolynomialDSL1 { - 5 { x pow 2u; z pow 3u } - (-6) { y pow 1u } - } - }, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to -1, - ), - Int.algebra.labeledPolynomialSpace { - LabeledPolynomialDSL1 { - 5 { } - (-6) { } - } - }, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to -1, - ), - Int.algebra.labeledPolynomialSpace { - LabeledPolynomialDSL1 { - 5 { x pow 1u; x pow 1u } - (-6) { x pow 2u } - } - }, - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to -1, - ), - Int.algebra.labeledPolynomialSpace { - LabeledPolynomialDSL1 { - 5 { x pow 1u; x pow 1u } - (-6) { x pow 2u; z pow 0u } - } - }, - "test 3" - ) - } - @Test - @UnstableKMathAPI - fun testFabric() { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u, z to 3u) to 5, - mapOf(y to 1u) to -6, - ), - Int.algebra { - LabeledPolynomial( - mapOf(x to 2u, z to 3u) to 5, - mapOf(y to 1u) to -6, - ) - }, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u, z to 3u) to 5, - mapOf(y to 1u) to -6, - ), - Int.algebra { - LabeledPolynomial( - mapOf(x to 2u, y to 0u, z to 3u, t to 0u) to 5, - mapOf(x to 0u, y to 1u, z to 0u, t to 0u) to -6, - ) - }, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to -1, - ), - Int.algebra { - LabeledPolynomial( - mapOf(x to 0u) to 5, - mapOf(y to 0u, z to 0u) to -6, - ) - }, - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 0, - ), - Int.algebra { - LabeledPolynomial( - mapOf(x to 0u) to 5, - mapOf(z to 0u, t to 0u) to -5, - ) - }, - "test 4" - ) - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialTest.kt deleted file mode 100644 index bde1386da..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialTest.kt +++ /dev/null @@ -1,2555 +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:Suppress("LocalVariableName") - -package space.kscience.kmath.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.functions.testUtils.IntModuloRing -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.functions.testUtils.iota -import space.kscience.kmath.functions.testUtils.m -import space.kscience.kmath.functions.testUtils.o -import space.kscience.kmath.functions.testUtils.s -import space.kscience.kmath.functions.testUtils.t -import space.kscience.kmath.functions.testUtils.x -import space.kscience.kmath.functions.testUtils.y -import space.kscience.kmath.functions.testUtils.z -import kotlin.test.* - - -// TODO: Тесты на конвертацию. -class LabeledPolynomialTest { - @Test - fun test_Variable_Int_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(1), - ), - x + 5, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - ), - x + 0, - "test 2" - ) - } - } - @Test - fun test_Variable_Int_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-5), - mapOf(x to 1u) to Rational(1), - ), - x - 5, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - ), - x - 0, - "test 2" - ) - } - } - @Test - fun test_Variable_Int_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(5), - ), - x * 5, - "test 1" - ) - assertSame( - zero, - x * 0, - "test 2" - ) - } - } - @Test - fun test_Int_Variable_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(1), - ), - 5 + x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - ), - 0 + x, - "test 2" - ) - } - } - @Test - fun test_Int_Variable_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(-1), - ), - 5 - x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-1), - ), - 0 - x, - "test 2" - ) - } - } - @Test - fun test_Int_Variable_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(5), - ), - 5 * x, - "test 1" - ) - assertSame( - zero, - 0 * x, - "test 2" - ) - } - } - @Test - fun test_Polynomial_Int_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + -3, - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + -3, - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + -3, - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ) + -3, - "test 4" - ) - val polynomial_5 = LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - polynomial_5 + 0, - "test 5" - ) - val polynomial_6 = LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - polynomial_6 + 0, - "test 6" - ) - val polynomial_7 = LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - polynomial_7 + 0, - "test 7" - ) - } - } - @Test - fun test_Polynomial_Int_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - 3, - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - 3, - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - 3, - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ) - 3, - "test 4" - ) - val polynomial_5 = LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - polynomial_5 - 0, - "test 5" - ) - val polynomial_6 = LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - polynomial_6 - 0, - "test 6" - ) - val polynomial_7 = LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - polynomial_7 - 0, - "test 7" - ) - } - } - @Test - fun test_Polynomial_Int_times() { - IntModuloRing(35).labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to m(34), - mapOf(x to 3u) to m(2), - mapOf(x to 0u, y to 1u) to m(1), - mapOf(x to 1u) to m(20), - mapOf(x to 0u, y to 0u, z to 2u) to m(2), - ), - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) * 27, - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - LabeledPolynomial( - mapOf() to m(7), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(49), - mapOf(x to 1u) to m(21), - mapOf(x to 0u, y to 0u, z to 2u) to m(14), - ) * 15, - "test 2" - ) - val polynomial = LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) - assertSame( - zero, - polynomial * 0, - "test 3" - ) - assertSame( - polynomial, - polynomial * 1, - "test 4" - ) - } - } - @Test - fun test_Int_Polynomial_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - -3 + LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - -3 + LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - -3 + LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - -3 + LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - "test 4" - ) - val polynomial_5 = LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - 0 + polynomial_5, - "test 5" - ) - val polynomial_6 = LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - 0 + polynomial_6, - "test 6" - ) - val polynomial_7 = LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - 0 + polynomial_7, - "test 7" - ) - } - } - @Test - fun test_Int_Polynomial_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(22, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 3 - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(3, 1), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 3 - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 3 - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - 3 - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(22, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 0 - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 0 - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - LabeledPolynomial( - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - 0 - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Int_Polynomial_times() { - IntModuloRing(35).labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to m(34), - mapOf(x to 3u) to m(2), - mapOf(x to 0u, y to 1u) to m(1), - mapOf(x to 1u) to m(20), - mapOf(x to 0u, y to 0u, z to 2u) to m(2), - ), - 27 * LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - 15 * LabeledPolynomial( - mapOf() to m(7), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(49), - mapOf(x to 1u) to m(21), - mapOf(x to 0u, y to 0u, z to 2u) to m(14), - ), - "test 2" - ) - val polynomial = LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) - assertSame( - zero, - 0 * polynomial, - "test 3" - ) - assertSame( - polynomial, - 1 * polynomial, - "test 4" - ) - } - } - @Test - fun test_Variable_Constant_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(1), - ), - x + Rational(5), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(1), - ), - x + Rational(0), - "test 2" - ) - } - } - @Test - fun test_Variable_Constant_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-5), - mapOf(x to 1u) to Rational(1), - ), - x - Rational(5), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(1), - ), - x - Rational(0), - "test 2" - ) - } - } - @Test - fun test_Variable_Constant_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(5), - ), - x * Rational(5), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(0), - ), - x * Rational(0), - "test 2" - ) - } - } - @Test - fun test_Constant_Variable_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(1), - ), - Rational(5) + x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(1), - ), - Rational(0) + x, - "test 2" - ) - } - } - @Test - fun test_Constant_Variable_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(5), - mapOf(x to 1u) to Rational(-1), - ), - Rational(5) - x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(-1), - ), - Rational(0) - x, - "test 2" - ) - } - } - @Test - fun test_Constant_Variable_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(5), - ), - Rational(5) * x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(0), - ), - Rational(0) * x, - "test 2" - ) - } - } - @Test - fun test_Polynomial_Constant_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ) + Rational(-3), - "test 4" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(0), - "test 5" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(0), - "test 6" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) + Rational(0), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(3), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(3), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(3), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ) - Rational(3), - "test 4" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(0), - "test 5" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(0), - "test 6" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ) - Rational(0), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_times() { - IntModuloRing(35).labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to m(34), - mapOf(x to 3u) to m(2), - mapOf(x to 0u, y to 1u) to m(1), - mapOf(x to 1u) to m(20), - mapOf(x to 0u, y to 0u, z to 2u) to m(2), - ), - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) * m(27), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - LabeledPolynomial( - mapOf() to m(7), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(49), - mapOf(x to 1u) to m(21), - mapOf(x to 0u, y to 0u, z to 2u) to m(14), - ) * m(15), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) * m(0), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ) * m(1), - "test 4" - ) - } - } - @Test - fun test_Constant_Polynomial_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(-3) + LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-3, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(-3) + LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(-3) + LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - Rational(-3) + LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(0) + LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(0) + LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - Rational(0) + LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(22, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(3) - LabeledPolynomial( - mapOf() to Rational(5, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(3, 1), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(3) - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 1), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(3) - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - Rational(3) - LabeledPolynomial( - mapOf() to Rational(27, 9), - mapOf(x to 3u) to Rational(0), - mapOf(x to 0u, y to 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(22, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(0) - LabeledPolynomial( - mapOf() to Rational(-22, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(0) - LabeledPolynomial( - mapOf() to Rational(0, 9), - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 3u) to Rational(8, 9), - mapOf(x to 0u, y to 4u) to Rational(8, 7), - ), - Rational(0) - LabeledPolynomial( - mapOf(x to 3u) to Rational(-8, 9), - mapOf(x to 0u, y to 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_times() { - IntModuloRing(35).labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to m(34), - mapOf(x to 3u) to m(2), - mapOf(x to 0u, y to 1u) to m(1), - mapOf(x to 1u) to m(20), - mapOf(x to 0u, y to 0u, z to 2u) to m(2), - ), - m(27) * LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - m(15) * LabeledPolynomial( - mapOf() to m(7), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(49), - mapOf(x to 1u) to m(21), - mapOf(x to 0u, y to 0u, z to 2u) to m(14), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(0), - mapOf(x to 3u) to m(0), - mapOf(x to 0u, y to 1u) to m(0), - mapOf(x to 1u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - ), - m(0) * LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - m(1) * LabeledPolynomial( - mapOf() to m(22), - mapOf(x to 3u) to m(26), - mapOf(x to 0u, y to 1u) to m(13), - mapOf(x to 1u) to m(15), - mapOf(x to 0u, y to 0u, z to 2u) to m(26), - ), - "test 4" - ) - } - } - @Test - fun test_Variable_unaryPlus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - ), - +x - ) - } - } - @Test - fun test_Variable_unaryMinus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-1), - ), - -x - ) - } - } - @Test - fun test_Variable_Variable_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(y to 1u) to Rational(1), - ), - x + y, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(2), - ), - x + x, - "test 2" - ) - } - } - @Test - fun test_Variable_Variable_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(y to 1u) to Rational(-1), - ), - x - y, - "test 1" - ) - assertSame( - zero, - x - x, - "test 2" - ) - } - } - @Test - fun test_Variable_Variable_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u, y to 1u) to Rational(1), - ), - x * y, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(1), - ), - x * x, - "test 2" - ) - } - } - @Test - fun test_Variable_Polynomial_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(7, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - x + LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(6, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - y + LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - mapOf(iota to 1u) to Rational(1), - ), - iota + LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 3" - ) - } - } - @Test - fun test_Variable_Polynomial_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(16, 4), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-3, 8), - mapOf(y to 1u) to Rational(1, 7), - mapOf(x to 1u, y to 1u) to Rational(15, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 5), - mapOf(y to 2u) to Rational(13, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(-11, 8), - ), - x - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(16, 4), - mapOf(x to 1u) to Rational(-4, 3), - mapOf(x to 2u) to Rational(-3, 8), - mapOf(y to 1u) to Rational(8, 7), - mapOf(x to 1u, y to 1u) to Rational(15, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 5), - mapOf(y to 2u) to Rational(13, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(-11, 8), - ), - y - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(16, 4), - mapOf(x to 1u) to Rational(-4, 3), - mapOf(x to 2u) to Rational(-3, 8), - mapOf(y to 1u) to Rational(1, 7), - mapOf(x to 1u, y to 1u) to Rational(15, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 5), - mapOf(y to 2u) to Rational(13, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(-11, 8), - mapOf(iota to 1u) to Rational(1), - ), - iota - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 3" - ) - } - } - @Test - fun test_Variable_Polynomial_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-16, 4), - mapOf(x to 2u) to Rational(4, 3), - mapOf(x to 3u) to Rational(3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 7), - mapOf(x to 2u, y to 1u) to Rational(-15, 3), - mapOf(x to 3u, y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 2u) to Rational(-13, 3), - mapOf(x to 2u, y to 2u) to Rational(13, 4), - mapOf(x to 3u, y to 2u) to Rational(11, 8), - ), - x * LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(-16, 4), - mapOf(x to 1u, y to 1u) to Rational(4, 3), - mapOf(x to 2u, y to 1u) to Rational(3, 8), - mapOf(y to 2u) to Rational(-1, 7), - mapOf(x to 1u, y to 2u) to Rational(-15, 3), - mapOf(x to 2u, y to 2u) to Rational(6, 5), - mapOf(y to 3u) to Rational(-13, 3), - mapOf(x to 1u, y to 3u) to Rational(13, 4), - mapOf(x to 2u, y to 3u) to Rational(11, 8), - ), - y * LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(iota to 1u) to Rational(-16, 4), - mapOf(x to 1u, iota to 1u) to Rational(4, 3), - mapOf(x to 2u, iota to 1u) to Rational(3, 8), - mapOf(y to 1u, iota to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u, iota to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u, iota to 1u) to Rational(6, 5), - mapOf(y to 2u, iota to 1u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u, iota to 1u) to Rational(13, 4), - mapOf(x to 2u, y to 2u, iota to 1u) to Rational(11, 8), - ), - iota * LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - "test 3" - ) - } - } - @Test - fun test_Polynomial_Variable_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(7, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) + x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(6, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) + y, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - mapOf(iota to 1u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) + iota, - "test 3" - ) - } - } - @Test - fun test_Polynomial_Variable_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(1, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) - x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-8, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) - y, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - mapOf(iota to 1u) to Rational(-1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) - iota, - "test 3" - ) - } - } - @Test - fun test_Polynomial_Variable_times() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-16, 4), - mapOf(x to 2u) to Rational(4, 3), - mapOf(x to 3u) to Rational(3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 7), - mapOf(x to 2u, y to 1u) to Rational(-15, 3), - mapOf(x to 3u, y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 2u) to Rational(-13, 3), - mapOf(x to 2u, y to 2u) to Rational(13, 4), - mapOf(x to 3u, y to 2u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) * x, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(-16, 4), - mapOf(x to 1u, y to 1u) to Rational(4, 3), - mapOf(x to 2u, y to 1u) to Rational(3, 8), - mapOf(y to 2u) to Rational(-1, 7), - mapOf(x to 1u, y to 2u) to Rational(-15, 3), - mapOf(x to 2u, y to 2u) to Rational(6, 5), - mapOf(y to 3u) to Rational(-13, 3), - mapOf(x to 1u, y to 3u) to Rational(13, 4), - mapOf(x to 2u, y to 3u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) * y, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(iota to 1u) to Rational(-16, 4), - mapOf(x to 1u, iota to 1u) to Rational(4, 3), - mapOf(x to 2u, iota to 1u) to Rational(3, 8), - mapOf(y to 1u, iota to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u, iota to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u, iota to 1u) to Rational(6, 5), - mapOf(y to 2u, iota to 1u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u, iota to 1u) to Rational(13, 4), - mapOf(x to 2u, y to 2u, iota to 1u) to Rational(11, 8), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-16, 4), - mapOf(x to 1u) to Rational(4, 3), - mapOf(x to 2u) to Rational(3, 8), - mapOf(y to 1u) to Rational(-1, 7), - mapOf(x to 1u, y to 1u) to Rational(-15, 3), - mapOf(x to 2u, y to 1u) to Rational(6, 5), - mapOf(y to 2u) to Rational(-13, 3), - mapOf(x to 1u, y to 2u) to Rational(13, 4), - mapOf(x to 2u, y to 2u) to Rational(11, 8), - ) * iota, - "test 3" - ) - } - } - @Test - fun test_Polynomial_unaryMinus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf(x to 5u) to Rational(-5, 9), - mapOf() to Rational(8, 9), - mapOf(iota to 13u) to Rational(8, 7), - ), - -LabeledPolynomial( - mapOf(x to 5u) to Rational(5, 9), - mapOf() to Rational(-8, 9), - mapOf(iota to 13u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf(x to 5u) to Rational(-5, 9), - mapOf() to Rational(8, 9), - mapOf(iota to 13u) to Rational(8, 7), - mapOf(x to 0u, y to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - ), - -LabeledPolynomial( - mapOf(x to 5u) to Rational(5, 9), - mapOf() to Rational(-8, 9), - mapOf(iota to 13u) to Rational(-8, 7), - mapOf(x to 0u, y to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - ), - "test 2" - ) - } - } - @Test - fun test_Polynomial_Polynomial_plus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(146, 63), - mapOf(x to 1u, y to 1u) to Rational(-3, 5), - mapOf(x to 2u, y to 1u) to Rational(61, 15), - mapOf(x to 0u, y to 2u) to Rational(157, 63), - mapOf(x to 1u, y to 2u) to Rational(-55, 21), - mapOf(x to 2u, y to 2u) to Rational(11, 24), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(-7, 7), - mapOf(x to 2u, y to 1u) to Rational(12, 5), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) + LabeledPolynomial( - mapOf() to Rational(-20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(-20, 7), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(7, 9), - mapOf(x to 1u, y to 2u) to Rational(5, 7), - mapOf(x to 2u, y to 2u) to Rational(-2, 3), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(157, 63), - mapOf(x to 1u, y to 2u) to Rational(-55, 21), - mapOf(x to 2u, y to 2u) to Rational(11, 24), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) + LabeledPolynomial( - mapOf() to Rational(-20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(-20, 7), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(7, 9), - mapOf(x to 1u, y to 2u) to Rational(5, 7), - mapOf(x to 2u, y to 2u) to Rational(-2, 3), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) + LabeledPolynomial( - mapOf() to Rational(-20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(-20, 7), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 0u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 0u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(-7, 7), - mapOf(x to 2u, y to 1u) to Rational(12, 5), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) + LabeledPolynomial( - mapOf() to Rational(-6, 4), - mapOf(x to 1u) to Rational(2, 6), - mapOf(x to 2u) to Rational(-10, 6), - mapOf(x to 0u, y to 1u) to Rational(-17, 7), - mapOf(x to 1u, y to 1u) to Rational(7, 7), - mapOf(x to 2u, y to 1u) to Rational(-12, 5), - mapOf(x to 0u, y to 2u) to Rational(-12, 7), - mapOf(x to 1u, y to 2u) to Rational(10, 3), - mapOf(x to 2u, y to 2u) to Rational(-9, 8), - ), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_minus() { - RationalField.labeledPolynomialSpace { - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(146, 63), - mapOf(x to 1u, y to 1u) to Rational(-3, 5), - mapOf(x to 2u, y to 1u) to Rational(61, 15), - mapOf(x to 0u, y to 2u) to Rational(157, 63), - mapOf(x to 1u, y to 2u) to Rational(-55, 21), - mapOf(x to 2u, y to 2u) to Rational(11, 24), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(-7, 7), - mapOf(x to 2u, y to 1u) to Rational(12, 5), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) - LabeledPolynomial( - mapOf() to Rational(20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(20, 7), - mapOf(x to 0u, y to 1u) to Rational(1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 5), - mapOf(x to 2u, y to 1u) to Rational(-10, 6), - mapOf(x to 0u, y to 2u) to Rational(-7, 9), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(2, 3), - ), - "test 1" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(157, 63), - mapOf(x to 1u, y to 2u) to Rational(-55, 21), - mapOf(x to 2u, y to 2u) to Rational(11, 24), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) - LabeledPolynomial( - mapOf() to Rational(20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(20, 7), - mapOf(x to 0u, y to 1u) to Rational(1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 5), - mapOf(x to 2u, y to 1u) to Rational(-10, 6), - mapOf(x to 0u, y to 2u) to Rational(-7, 9), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(2, 3), - ), - "test 2" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(-17, 2), - mapOf(x to 1u) to Rational(-1, 3), - mapOf(x to 2u) to Rational(-25, 21), - mapOf(x to 0u, y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(2, 5), - mapOf(x to 2u, y to 1u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) - LabeledPolynomial( - mapOf() to Rational(20, 2), - mapOf(x to 1u) to Rational(0, 9), - mapOf(x to 2u) to Rational(20, 7), - mapOf(x to 0u, y to 1u) to Rational(1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 5), - mapOf(x to 2u, y to 1u) to Rational(-10, 6), - mapOf(x to 0u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - ), - "test 3" - ) - assertEquals( - LabeledPolynomial( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 0u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 0u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - ), - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(-7, 7), - mapOf(x to 2u, y to 1u) to Rational(12, 5), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ) - LabeledPolynomial( - mapOf() to Rational(6, 4), - mapOf(x to 1u) to Rational(-2, 6), - mapOf(x to 2u) to Rational(10, 6), - mapOf(x to 0u, y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(-7, 7), - mapOf(x to 2u, y to 1u) to Rational(12, 5), - mapOf(x to 0u, y to 2u) to Rational(12, 7), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(9, 8), - ), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_times() { - IntModuloRing(35).labeledPolynomialSpace { - // (p + q + r) * (p^2 + q^2 + r^2 - pq - pr - qr) = p^3 + q^3 + r^3 - 3pqr - assertEquals( - LabeledPolynomial( - mapOf(x to 3u) to m(1), - mapOf(x to 0u, y to 3u) to m(1), - mapOf(x to 0u, y to 0u, z to 3u) to m(1), - mapOf(x to 1u, y to 2u) to m(0), - mapOf(x to 0u, y to 1u, z to 2u) to m(0), - mapOf(x to 2u, y to 0u, z to 1u) to m(0), - mapOf(x to 1u, y to 0u, z to 2u) to m(0), - mapOf(x to 2u, y to 1u) to m(0), - mapOf(x to 0u, y to 2u, z to 1u) to m(0), - mapOf(x to 1u, y to 1u, z to 1u) to m(-3), - ), - LabeledPolynomial( - mapOf(x to 1u) to m(1), - mapOf(x to 0u, y to 1u) to m(1), - mapOf(x to 0u, y to 0u, z to 1u) to m(1), - ) * LabeledPolynomial( - mapOf(x to 2u) to m(1), - mapOf(x to 0u, y to 2u) to m(1), - mapOf(x to 0u, y to 0u, z to 2u) to m(1), - mapOf(x to 1u, y to 1u) to m(-1), - mapOf(x to 0u, y to 1u, z to 1u) to m(-1), - mapOf(x to 1u, y to 0u, z to 1u) to m(-1), - ), - "test 1" - ) - // Spoiler: 5 * 7 = 0 - assertEquals( - LabeledPolynomial( - mapOf(x to 2u) to m(0), - mapOf(x to 0u, y to 2u) to m(0), - mapOf(x to 0u, y to 0u, z to 2u) to m(0), - mapOf(x to 1u, y to 1u) to m(0), - mapOf(x to 0u, y to 1u, z to 1u) to m(0), - mapOf(x to 1u, y to 0u, z to 1u) to m(0), - ), - LabeledPolynomial( - mapOf(x to 1u) to m(5), - mapOf(x to 0u, y to 1u) to m(-25), - mapOf(x to 0u, y to 0u, z to 1u) to m(10), - ) * LabeledPolynomial( - mapOf(x to 1u) to m(21), - mapOf(x to 0u, y to 1u) to m(14), - mapOf(x to 0u, y to 0u, z to 1u) to m(-7), - ), - "test 2" - ) - } - } - @Test - fun test_degree() { - RationalField.labeledPolynomialSpace { - assertEquals( - -1, - LabeledPolynomial().degree, - "test 1" - ) - assertEquals( - 0, - LabeledPolynomial( - mapOf() to o - ).degree, - "test 2" - ) - assertEquals( - 6, - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).degree, - "test 3" - ) - assertEquals( - 4, - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).degree, - "test 4" - ) - assertEquals( - 3, - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).degree, - "test 5" - ) - assertEquals( - 4, - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).degree, - "test 6" - ) - } - } - @Test - fun test_degrees() { - RationalField.labeledPolynomialSpace { - assertEquals( - mapOf(), - LabeledPolynomial().degrees, - "test 1" - ) - assertEquals( - mapOf(), - LabeledPolynomial( - mapOf() to o - ).degrees, - "test 2" - ) - assertEquals( - mapOf(x to 1u, y to 2u, z to 3u), - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).degrees, - "test 3" - ) - assertEquals( - mapOf(y to 1u, z to 2u, t to 1u), - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).degrees, - "test 4" - ) - assertEquals( - mapOf(x to 2u, y to 1u, z to 1u), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).degrees, - "test 5" - ) - assertEquals( - mapOf(x to 2u, y to 2u, z to 2u, t to 4u), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).degrees, - "test 6" - ) - } - } - @Test - fun test_degreeBy() { - RationalField.labeledPolynomialSpace { - fun LabeledPolynomial.collectDegrees(variables: Set = this.variables + iota): Map = variables.associateWith { degreeBy(it) } - assertEquals( - mapOf(iota to 0u), - LabeledPolynomial().collectDegrees(), - "test 1" - ) - assertEquals( - mapOf(iota to 0u), - LabeledPolynomial( - mapOf() to o - ).collectDegrees(), - "test 2" - ) - assertEquals( - mapOf(x to 1u, y to 2u, z to 3u, iota to 0u), - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).collectDegrees(), - "test 3" - ) - assertEquals( - mapOf(y to 1u, z to 2u, t to 1u, iota to 0u), - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).collectDegrees(), - "test 4" - ) - assertEquals( - mapOf(x to 2u, y to 1u, z to 1u, iota to 0u), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).collectDegrees(), - "test 5" - ) - assertEquals( - mapOf(x to 2u, y to 2u, z to 2u, t to 4u, iota to 0u), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).collectDegrees(), - "test 6" - ) - } - } - @Test - fun test_degreeBy_Collection() { - RationalField.labeledPolynomialSpace { - fun LabeledPolynomial.checkDegreeBy(message: String? = null) { - val variables = variables.toList() + iota - val variablesCollectionSequence: Sequence> = sequence { - val appearances = MutableList(variables.size) { 0 } - while (true) { - yield( - buildList { - for ((variableIndex, count) in appearances.withIndex()) repeat(count) { add(variables[variableIndex]) } - } - ) - val indexChange = appearances.indexOfFirst { it < 4 } - if (indexChange == -1) break - appearances[indexChange] += 1 - for (index in 0 until indexChange) appearances[index] = 0 - } - } - for (variablesCollection in variablesCollectionSequence) { - val expected = coefficients.keys.maxOfOrNull { degs -> degs.filterKeys { it in variablesCollection }.values.sum() } ?: 0u - val actual = degreeBy(variablesCollection) - if (actual != expected) - fail("${message ?: ""} Incorrect answer for variable collection $variablesCollection: expected $expected, actual $actual") - } - } - LabeledPolynomial().checkDegreeBy("test 1") - LabeledPolynomial( - mapOf() to o - ).checkDegreeBy("test 2") - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).checkDegreeBy("test 3") - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).checkDegreeBy("test 4") - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).checkDegreeBy("test 5") - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).checkDegreeBy("test 6") - } - } - @Test - fun test_variables() { - RationalField.labeledPolynomialSpace { - assertEquals( - setOf(), - LabeledPolynomial().variables, - "test 1" - ) - assertEquals( - setOf(), - LabeledPolynomial( - mapOf() to o - ).variables, - "test 2" - ) - assertEquals( - setOf(x, y, z), - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).variables, - "test 3" - ) - assertEquals( - setOf(y, z, t), - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).variables, - "test 4" - ) - assertEquals( - setOf(x, y, z), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).variables, - "test 5" - ) - assertEquals( - setOf(x, y, z, t), - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).variables, - "test 6" - ) - } - } - @Test - fun test_countOfVariables() { - RationalField.labeledPolynomialSpace { - assertEquals( - 0, - LabeledPolynomial().countOfVariables, - "test 1" - ) - assertEquals( - 0, - LabeledPolynomial( - mapOf() to o - ).countOfVariables, - "test 2" - ) - assertEquals( - 3, - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ).countOfVariables, - "test 3" - ) - assertEquals( - 3, - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u, t to 1u, s to 0u) to o - ).countOfVariables, - "test 4" - ) - assertEquals( - 3, - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ).countOfVariables, - "test 5" - ) - assertEquals( - 4, - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ).countOfVariables, - "test 6" - ) - } - } - @Test - fun test_RF_countOfVariables() { - RationalField.labeledRationalFunctionSpace { - assertEquals( - 0, - LabeledRationalFunction( - LabeledPolynomial() - ).countOfVariables, - "test 1" - ) - assertEquals( - 0, - LabeledRationalFunction( - LabeledPolynomial(), - LabeledPolynomial() - ).countOfVariables, - "test 2" - ) - assertEquals( - 0, - LabeledRationalFunction( - LabeledPolynomial( - mapOf() to o - ) - ).countOfVariables, - "test 3" - ) - assertEquals( - 3, - LabeledRationalFunction( - LabeledPolynomial( - mapOf(x to 1u, y to 2u, z to 3u) to o - ) - ).countOfVariables, - "test 4" - ) - assertEquals( - 3, - LabeledRationalFunction( - LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 0u, t to 1u) to o - ), - LabeledPolynomial( - mapOf(x to 0u, y to 0u, z to 2u) to o - ) - ).countOfVariables, - "test 5" - ) - assertEquals( - 3, - LabeledRationalFunction( - LabeledPolynomial( - mapOf() to o, - mapOf(x to 0u, y to 1u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ) - ).countOfVariables, - "test 6" - ) - assertEquals( - 4, - LabeledRationalFunction( - LabeledPolynomial( - mapOf() to o, - mapOf(x to 1u, y to 2u) to o, - mapOf(x to 2u, y to 0u, z to 1u) to o, - ), LabeledPolynomial( - mapOf(x to 0u, y to 1u, z to 2u) to o, - mapOf(x to 0u, y to 0u, z to 0u, t to 4u) to o, - ) - ).countOfVariables, - "test 7" - ) - } - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialUtilTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialUtilTest.kt deleted file mode 100644 index 6243818b4..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/LabeledPolynomialUtilTest.kt +++ /dev/null @@ -1,8222 +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.functions - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.functions.testUtils.assertEquals -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.functions.testUtils.iota -import space.kscience.kmath.functions.testUtils.x -import space.kscience.kmath.functions.testUtils.y -import space.kscience.kmath.misc.UnstableKMathAPI -import kotlin.test.Ignore -import kotlin.test.Test -import kotlin.test.assertEquals - -class LabeledPolynomialUtilTest { - @Test - fun test_Polynomial_substitute_Double() { - assertEquals( - LabeledPolynomialAsIs(emptyMap() to 0.0), - LabeledPolynomialAsIs( - mapOf() to 1.0, - mapOf(x to 1u) to -2.0, - mapOf(x to 2u) to 1.0, - ).substitute(mapOf( - x to 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf()), - 0.001, - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - iota to 0.9211194782050933 - )), - 0.001, - "test 2'" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(y to 2u) to 0.2700930201481795, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - x to 0.0 - )), - 0.001, - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(y to 2u) to 0.2700930201481795, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - x to 0.0, - iota to 0.9211194782050933 - )), - 0.001, - "test 3'" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 1.433510890645169, - mapOf(x to 1u) to 0.6264844682514724, - mapOf(x to 2u) to 0.8405727903771333, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - y to 0.8400458576651112 - )), - 0.001, - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 1.433510890645169, - mapOf(x to 1u) to 0.6264844682514724, - mapOf(x to 2u) to 0.8405727903771333, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - y to 0.8400458576651112, - iota to 0.9211194782050933 - )), - 0.001, - "test 4'" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 1.934530767358133, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - x to 0.4846192734143442, - y to 0.8400458576651112, - )), - 0.001, - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to 1.934530767358133, - ), - LabeledPolynomialAsIs( - mapOf() to 0.8597048543814783, - mapOf(x to 1u) to 0.22997637465889875, - mapOf(x to 2u) to 0.32675302591924016, - mapOf(y to 1u) to 0.4561746111587508, - mapOf(x to 1u, y to 1u) to 0.5304946210170756, - mapOf(x to 2u, y to 1u) to 0.6244313712888998, - mapOf(y to 2u) to 0.2700930201481795, - mapOf(x to 1u, y to 2u) to -0.06962351375204712, - mapOf(x to 2u, y to 2u) to -0.015206988092131501, - ).substitute(mapOf( - x to 0.4846192734143442, - y to 0.8400458576651112, - iota to 0.9211194782050933 - )), - 0.001, - "test 5'" - ) - } - @Test - fun test_Polynomial_substitute_Constant_Map() { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ).substitute(RationalField, mapOf( - x to Rational(1) - )), - "test 1" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5%2C+y+%3D+12%2F9 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(143, 150) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to Rational(-2, 5), - y to Rational(12, 9), - )), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(143, 150) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to Rational(-2, 5), - y to Rational(12, 9), - iota to Rational(57, 179), - )), - "test 2'" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+y+%3D+12%2F9 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-67, 18), - mapOf(x to 1u) to Rational(-70, 9), - mapOf(x to 2u) to Rational(88, 9), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - y to Rational(12, 9), - )), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-67, 18), - mapOf(x to 1u) to Rational(-70, 9), - mapOf(x to 2u) to Rational(88, 9), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - y to Rational(12, 9), - iota to Rational(57, 179), - )), - "test 3'" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-83, 50), - mapOf(y to 1u) to Rational(29, 25), - mapOf(y to 2u) to Rational(3, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to Rational(-2, 5), - )), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-83, 50), - mapOf(y to 1u) to Rational(29, 25), - mapOf(y to 2u) to Rational(3, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to Rational(-2, 5), - iota to Rational(57, 179), - )), - "test 4'" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf()), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - iota to Rational(57, 179), - )), - "test 5'" - ) - // https://www.wolframalpha.com/input?i=%28%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2%29+p%5E8+where+x+%3D+q%2Fp%2C+y+%3D+x%5E3%2C+p+%3D+-2%2F5%2C+q+%3D+12%2F9 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(47639065216, 2562890625) - ), - LabeledPolynomialAsIs( - mapOf(x to 8u) to Rational(-3, 2), - mapOf(x to 7u, y to 1u) to Rational(8, 6), - mapOf(x to 6u, y to 2u) to Rational(14, 6), - mapOf(x to 5u, y to 3u) to Rational(-3, 1), - mapOf(x to 4u, y to 4u) to Rational(-19, 2), - mapOf(x to 3u, y to 5u) to Rational(9, 4), - mapOf(x to 2u, y to 6u) to Rational(5, 5), - mapOf(x to 1u, y to 7u) to Rational(18, 9), - mapOf(y to 8u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to Rational(-2, 5), - y to Rational(12, 9), - )), - "test 6" - ) - } - @Test - fun test_Polynomial_substitute_Polynomial_Map() { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - )), - "test 1" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-5%2F1+s+%2B+2%2F8+t%2C+y+%3D+11%2F7+t - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(y to 1u) to Rational(-92, 21), - mapOf(y to 2u) to Rational(-2627, 2352), - mapOf(y to 3u) to Rational(4565, 3136), - mapOf(y to 4u) to Rational(605, 1568), - mapOf(x to 1u) to Rational(-20, 3), - mapOf(x to 1u, y to 1u) to Rational(1445, 21), - mapOf(x to 1u, y to 2u) to Rational(-13145, 392), - mapOf(x to 1u, y to 3u) to Rational(-3025, 196), - mapOf(x to 2u) to Rational(175, 3), - mapOf(x to 2u, y to 1u) to Rational(2475, 28), - mapOf(x to 2u, y to 2u) to Rational(15125, 98), - mapOf(x to 3u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-5, 1), - mapOf(y to 1u) to Rational(2, 8), - ), - y to LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(0, 5), - mapOf(y to 1u) to Rational(11, 7), - ), - )), - "test 2" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = (-9/2 + 2/7 s + 9/1 s^2) + (13/1 + -1/8 s + 2/8 s^2) t + (19/4 + 15/7 s + -19/4 s^2) t^2 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(129, 4), - mapOf(x to 1u) to Rational(48583, 336), - mapOf(x to 2u) to Rational(-913477, 1568), - mapOf(x to 3u) to Rational(-967567, 672), - mapOf(x to 4u) to Rational(4722043, 1344), - mapOf(x to 5u) to Rational(8855, 2), - mapOf(x to 6u) to Rational(-311971, 32), - mapOf(x to 7u) to Rational(-17325, 4), - mapOf(x to 8u) to Rational(19845, 2), - mapOf(y to 1u) to Rational(-827, 4), - mapOf(x to 1u, y to 1u) to Rational(191927, 840), - mapOf(x to 2u, y to 1u) to Rational(9592627, 2352), - mapOf(x to 3u, y to 1u) to Rational(-105400711, 53760), - mapOf(x to 4u, y to 1u) to Rational(-10054101459, 439040), - mapOf(x to 5u, y to 1u) to Rational(2127351, 128), - mapOf(x to 6u, y to 1u) to Rational(116680973, 3136), - mapOf(x to 7u, y to 1u) to Rational(-220445, 7), - mapOf(x to 8u, y to 1u) to Rational(-2655, 4), - mapOf(y to 2u) to Rational(30567, 100), - mapOf(x to 1u, y to 2u) to Rational(-156284953, 39200), - mapOf(x to 2u, y to 2u) to Rational(-57661541711, 6585600), - mapOf(x to 3u, y to 2u) to Rational(131931579, 3136), - mapOf(x to 4u, y to 2u) to Rational(98818124791, 3512320), - mapOf(x to 5u, y to 2u) to Rational(-94458855053, 878080), - mapOf(x to 6u, y to 2u) to Rational(13937705305, 1229312), - mapOf(x to 7u, y to 2u) to Rational(335706887, 21952), - mapOf(x to 8u, y to 2u) to Rational(23549165, 1568), - mapOf(y to 3u) to Rational(111367, 1400), - mapOf(x to 1u, y to 3u) to Rational(4937369, 700), - mapOf(x to 2u, y to 3u) to Rational(-4449423711, 274400), - mapOf(x to 3u, y to 3u) to Rational(-351873325703, 4390400), - mapOf(x to 4u, y to 3u) to Rational(23495875029, 307328), - mapOf(x to 5u, y to 3u) to Rational(17576300919, 878080), - mapOf(x to 6u, y to 3u) to Rational(230316993, 12544), - mapOf(x to 7u, y to 3u) to Rational(-191130515, 21952), - mapOf(x to 8u, y to 3u) to Rational(332435, 392), - mapOf(y to 4u) to Rational(-275084, 1225), - mapOf(x to 1u, y to 4u) to Rational(-266774603, 137200), - mapOf(x to 2u, y to 4u) to Rational(2176279167121, 30732800), - mapOf(x to 3u, y to 4u) to Rational(10904913303, 2195200), - mapOf(x to 4u, y to 4u) to Rational(-10769286147, 2195200), - mapOf(x to 5u, y to 4u) to Rational(-26277119793, 439040), - mapOf(x to 6u, y to 4u) to Rational(25859735869, 6146560), - mapOf(x to 7u, y to 4u) to Rational(38906289, 2744), - mapOf(x to 8u, y to 4u) to Rational(-3072025, 392), - mapOf(y to 5u) to Rational(9573, 98), - mapOf(x to 1u, y to 5u) to Rational(-4154651399, 548800), - mapOf(x to 2u, y to 5u) to Rational(3446069019, 548800), - mapOf(x to 3u, y to 5u) to Rational(-7851500623, 137200), - mapOf(x to 4u, y to 5u) to Rational(-53205142903, 1920800), - mapOf(x to 5u, y to 5u) to Rational(-31953611, 3430), - mapOf(x to 6u, y to 5u) to Rational(1447380313, 109760), - mapOf(x to 7u, y to 5u) to Rational(764158625, 21952), - mapOf(x to 8u, y to 5u) to Rational(1153515, 784), - mapOf(y to 6u) to Rational(1722351, 7840), - mapOf(x to 1u, y to 6u) to Rational(-164554821, 109760), - mapOf(x to 2u, y to 6u) to Rational(-79096147243, 7683200), - mapOf(x to 3u, y to 6u) to Rational(-624721089, 15680), - mapOf(x to 4u, y to 6u) to Rational(11147305567, 548800), - mapOf(x to 5u, y to 6u) to Rational(8318333679, 109760), - mapOf(x to 6u, y to 6u) to Rational(32981871553, 1536640), - mapOf(x to 7u, y to 6u) to Rational(-225359619, 21952), - mapOf(x to 8u, y to 6u) to Rational(-3973995, 392), - mapOf(y to 7u) to Rational(67203, 784), - mapOf(x to 1u, y to 7u) to Rational(39281469, 54880), - mapOf(x to 2u, y to 7u) to Rational(70162551, 27440), - mapOf(x to 3u, y to 7u) to Rational(413630709, 54880), - mapOf(x to 4u, y to 7u) to Rational(4640410269, 192080), - mapOf(x to 5u, y to 7u) to Rational(802712247, 54880), - mapOf(x to 6u, y to 7u) to Rational(-473517603, 27440), - mapOf(x to 7u, y to 7u) to Rational(-17055459, 1568), - mapOf(x to 8u, y to 7u) to Rational(-12825, 14), - mapOf(y to 8u) to Rational(16245, 1568), - mapOf(x to 1u, y to 8u) to Rational(503253, 2744), - mapOf(x to 2u, y to 8u) to Rational(125292591, 96040), - mapOf(x to 3u, y to 8u) to Rational(12033171, 2744), - mapOf(x to 4u, y to 8u) to Rational(154352673, 27440), - mapOf(x to 5u, y to 8u) to Rational(-1302291, 392), - mapOf(x to 6u, y to 8u) to Rational(-20265741, 1960), - mapOf(x to 7u, y to 8u) to Rational(-26163, 56), - mapOf(x to 8u, y to 8u) to Rational(146205, 32), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(0, 6), - mapOf(x to 1u) to Rational(14, 8), - mapOf(x to 2u) to Rational(-14, 2), - mapOf(y to 1u) to Rational(-3, 5), - mapOf(x to 1u, y to 1u) to Rational(11, 1), - mapOf(x to 2u, y to 1u) to Rational(3, 7), - mapOf(y to 2u) to Rational(-3, 7), - mapOf(x to 1u, y to 2u) to Rational(-18, 5), - mapOf(x to 2u, y to 2u) to Rational(-9, 1), - ), - y to LabeledPolynomialAsIs( - mapOf() to Rational(-9, 2), - mapOf(x to 1u) to Rational(2, 7), - mapOf(x to 2u) to Rational(9, 1), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-1, 8), - mapOf(x to 2u, y to 1u) to Rational(2, 8), - mapOf(y to 2u) to Rational(19, 4), - mapOf(x to 1u, y to 2u) to Rational(15, 7), - mapOf(x to 2u, y to 2u) to Rational(-19, 4), - ), - )), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(129, 4), - mapOf(x to 1u) to Rational(48583, 336), - mapOf(x to 2u) to Rational(-913477, 1568), - mapOf(x to 3u) to Rational(-967567, 672), - mapOf(x to 4u) to Rational(4722043, 1344), - mapOf(x to 5u) to Rational(8855, 2), - mapOf(x to 6u) to Rational(-311971, 32), - mapOf(x to 7u) to Rational(-17325, 4), - mapOf(x to 8u) to Rational(19845, 2), - mapOf(y to 1u) to Rational(-827, 4), - mapOf(x to 1u, y to 1u) to Rational(191927, 840), - mapOf(x to 2u, y to 1u) to Rational(9592627, 2352), - mapOf(x to 3u, y to 1u) to Rational(-105400711, 53760), - mapOf(x to 4u, y to 1u) to Rational(-10054101459, 439040), - mapOf(x to 5u, y to 1u) to Rational(2127351, 128), - mapOf(x to 6u, y to 1u) to Rational(116680973, 3136), - mapOf(x to 7u, y to 1u) to Rational(-220445, 7), - mapOf(x to 8u, y to 1u) to Rational(-2655, 4), - mapOf(y to 2u) to Rational(30567, 100), - mapOf(x to 1u, y to 2u) to Rational(-156284953, 39200), - mapOf(x to 2u, y to 2u) to Rational(-57661541711, 6585600), - mapOf(x to 3u, y to 2u) to Rational(131931579, 3136), - mapOf(x to 4u, y to 2u) to Rational(98818124791, 3512320), - mapOf(x to 5u, y to 2u) to Rational(-94458855053, 878080), - mapOf(x to 6u, y to 2u) to Rational(13937705305, 1229312), - mapOf(x to 7u, y to 2u) to Rational(335706887, 21952), - mapOf(x to 8u, y to 2u) to Rational(23549165, 1568), - mapOf(y to 3u) to Rational(111367, 1400), - mapOf(x to 1u, y to 3u) to Rational(4937369, 700), - mapOf(x to 2u, y to 3u) to Rational(-4449423711, 274400), - mapOf(x to 3u, y to 3u) to Rational(-351873325703, 4390400), - mapOf(x to 4u, y to 3u) to Rational(23495875029, 307328), - mapOf(x to 5u, y to 3u) to Rational(17576300919, 878080), - mapOf(x to 6u, y to 3u) to Rational(230316993, 12544), - mapOf(x to 7u, y to 3u) to Rational(-191130515, 21952), - mapOf(x to 8u, y to 3u) to Rational(332435, 392), - mapOf(y to 4u) to Rational(-275084, 1225), - mapOf(x to 1u, y to 4u) to Rational(-266774603, 137200), - mapOf(x to 2u, y to 4u) to Rational(2176279167121, 30732800), - mapOf(x to 3u, y to 4u) to Rational(10904913303, 2195200), - mapOf(x to 4u, y to 4u) to Rational(-10769286147, 2195200), - mapOf(x to 5u, y to 4u) to Rational(-26277119793, 439040), - mapOf(x to 6u, y to 4u) to Rational(25859735869, 6146560), - mapOf(x to 7u, y to 4u) to Rational(38906289, 2744), - mapOf(x to 8u, y to 4u) to Rational(-3072025, 392), - mapOf(y to 5u) to Rational(9573, 98), - mapOf(x to 1u, y to 5u) to Rational(-4154651399, 548800), - mapOf(x to 2u, y to 5u) to Rational(3446069019, 548800), - mapOf(x to 3u, y to 5u) to Rational(-7851500623, 137200), - mapOf(x to 4u, y to 5u) to Rational(-53205142903, 1920800), - mapOf(x to 5u, y to 5u) to Rational(-31953611, 3430), - mapOf(x to 6u, y to 5u) to Rational(1447380313, 109760), - mapOf(x to 7u, y to 5u) to Rational(764158625, 21952), - mapOf(x to 8u, y to 5u) to Rational(1153515, 784), - mapOf(y to 6u) to Rational(1722351, 7840), - mapOf(x to 1u, y to 6u) to Rational(-164554821, 109760), - mapOf(x to 2u, y to 6u) to Rational(-79096147243, 7683200), - mapOf(x to 3u, y to 6u) to Rational(-624721089, 15680), - mapOf(x to 4u, y to 6u) to Rational(11147305567, 548800), - mapOf(x to 5u, y to 6u) to Rational(8318333679, 109760), - mapOf(x to 6u, y to 6u) to Rational(32981871553, 1536640), - mapOf(x to 7u, y to 6u) to Rational(-225359619, 21952), - mapOf(x to 8u, y to 6u) to Rational(-3973995, 392), - mapOf(y to 7u) to Rational(67203, 784), - mapOf(x to 1u, y to 7u) to Rational(39281469, 54880), - mapOf(x to 2u, y to 7u) to Rational(70162551, 27440), - mapOf(x to 3u, y to 7u) to Rational(413630709, 54880), - mapOf(x to 4u, y to 7u) to Rational(4640410269, 192080), - mapOf(x to 5u, y to 7u) to Rational(802712247, 54880), - mapOf(x to 6u, y to 7u) to Rational(-473517603, 27440), - mapOf(x to 7u, y to 7u) to Rational(-17055459, 1568), - mapOf(x to 8u, y to 7u) to Rational(-12825, 14), - mapOf(y to 8u) to Rational(16245, 1568), - mapOf(x to 1u, y to 8u) to Rational(503253, 2744), - mapOf(x to 2u, y to 8u) to Rational(125292591, 96040), - mapOf(x to 3u, y to 8u) to Rational(12033171, 2744), - mapOf(x to 4u, y to 8u) to Rational(154352673, 27440), - mapOf(x to 5u, y to 8u) to Rational(-1302291, 392), - mapOf(x to 6u, y to 8u) to Rational(-20265741, 1960), - mapOf(x to 7u, y to 8u) to Rational(-26163, 56), - mapOf(x to 8u, y to 8u) to Rational(146205, 32), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(0, 6), - mapOf(x to 1u) to Rational(14, 8), - mapOf(x to 2u) to Rational(-14, 2), - mapOf(y to 1u) to Rational(-3, 5), - mapOf(x to 1u, y to 1u) to Rational(11, 1), - mapOf(x to 2u, y to 1u) to Rational(3, 7), - mapOf(y to 2u) to Rational(-3, 7), - mapOf(x to 1u, y to 2u) to Rational(-18, 5), - mapOf(x to 2u, y to 2u) to Rational(-9, 1), - ), - y to LabeledPolynomialAsIs( - mapOf() to Rational(-9, 2), - mapOf(x to 1u) to Rational(2, 7), - mapOf(x to 2u) to Rational(9, 1), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-1, 8), - mapOf(x to 2u, y to 1u) to Rational(2, 8), - mapOf(y to 2u) to Rational(19, 4), - mapOf(x to 1u, y to 2u) to Rational(15, 7), - mapOf(x to 2u, y to 2u) to Rational(-19, 4), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-11, 3), - mapOf(x to 1u) to Rational(5, 2), - mapOf(x to 2u) to Rational(13, 7), - mapOf(y to 1u) to Rational(16, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(6, 1), - mapOf(y to 2u) to Rational(-14, 3), - mapOf(x to 1u, y to 2u) to Rational(-2, 7), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - )), - "test 3'" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = s, y = (-9/2 + 2/7 s + 9/1 s^2) + (13/1 + -1/8 s + 2/8 s^2) t + (19/4 + 15/7 s + -19/4 s^2) t^2 - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(129, 4), - mapOf(x to 1u) to Rational(6817, 84), - mapOf(x to 2u) to Rational(-21445, 294), - mapOf(x to 3u) to Rational(-12151, 49), - mapOf(x to 4u) to Rational(-17789, 196), - mapOf(x to 5u) to Rational(1224, 7), - mapOf(x to 6u) to Rational(405, 2), - mapOf(y to 1u) to Rational(-156), - mapOf(x to 1u, y to 1u) to Rational(-2440, 7), - mapOf(x to 2u, y to 1u) to Rational(-1571, 112), - mapOf(x to 3u, y to 1u) to Rational(107515, 224), - mapOf(x to 4u, y to 1u) to Rational(64965, 112), - mapOf(x to 5u, y to 1u) to Rational(209, 56), - mapOf(x to 6u, y to 1u) to Rational(45, 4), - mapOf(y to 2u) to Rational(112), - mapOf(x to 1u, y to 2u) to Rational(1449, 8), - mapOf(x to 2u, y to 2u) to Rational(1306309, 3136), - mapOf(x to 3u, y to 2u) to Rational(483207, 1568), - mapOf(x to 4u, y to 2u) to Rational(1978437, 6272), - mapOf(x to 5u, y to 2u) to Rational(-18231, 224), - mapOf(x to 6u, y to 2u) to Rational(-6835, 32), - mapOf(y to 3u) to Rational(247, 2), - mapOf(x to 1u, y to 3u) to Rational(33771, 112), - mapOf(x to 2u, y to 3u) to Rational(2073, 7), - mapOf(x to 3u, y to 3u) to Rational(-23463, 224), - mapOf(x to 4u, y to 3u) to Rational(-33825, 112), - mapOf(x to 5u, y to 3u) to Rational(201, 224), - mapOf(x to 6u, y to 3u) to Rational(-95, 16), - mapOf(y to 4u) to Rational(361, 16), - mapOf(x to 1u, y to 4u) to Rational(3667, 56), - mapOf(x to 2u, y to 4u) to Rational(88729, 1568), - mapOf(x to 3u, y to 4u) to Rational(-2476, 49), - mapOf(x to 4u, y to 4u) to Rational(-23419, 196), - mapOf(x to 5u, y to 4u) to Rational(-323, 56), - mapOf(x to 6u, y to 4u) to Rational(1805, 32), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - y to LabeledPolynomialAsIs( - mapOf() to Rational(-9, 2), - mapOf(x to 1u) to Rational(2, 7), - mapOf(x to 2u) to Rational(9, 1), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-1, 8), - mapOf(x to 2u, y to 1u) to Rational(2, 8), - mapOf(y to 2u) to Rational(19, 4), - mapOf(x to 1u, y to 2u) to Rational(15, 7), - mapOf(x to 2u, y to 2u) to Rational(-19, 4), - ), - )), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(129, 4), - mapOf(x to 1u) to Rational(6817, 84), - mapOf(x to 2u) to Rational(-21445, 294), - mapOf(x to 3u) to Rational(-12151, 49), - mapOf(x to 4u) to Rational(-17789, 196), - mapOf(x to 5u) to Rational(1224, 7), - mapOf(x to 6u) to Rational(405, 2), - mapOf(y to 1u) to Rational(-156), - mapOf(x to 1u, y to 1u) to Rational(-2440, 7), - mapOf(x to 2u, y to 1u) to Rational(-1571, 112), - mapOf(x to 3u, y to 1u) to Rational(107515, 224), - mapOf(x to 4u, y to 1u) to Rational(64965, 112), - mapOf(x to 5u, y to 1u) to Rational(209, 56), - mapOf(x to 6u, y to 1u) to Rational(45, 4), - mapOf(y to 2u) to Rational(112), - mapOf(x to 1u, y to 2u) to Rational(1449, 8), - mapOf(x to 2u, y to 2u) to Rational(1306309, 3136), - mapOf(x to 3u, y to 2u) to Rational(483207, 1568), - mapOf(x to 4u, y to 2u) to Rational(1978437, 6272), - mapOf(x to 5u, y to 2u) to Rational(-18231, 224), - mapOf(x to 6u, y to 2u) to Rational(-6835, 32), - mapOf(y to 3u) to Rational(247, 2), - mapOf(x to 1u, y to 3u) to Rational(33771, 112), - mapOf(x to 2u, y to 3u) to Rational(2073, 7), - mapOf(x to 3u, y to 3u) to Rational(-23463, 224), - mapOf(x to 4u, y to 3u) to Rational(-33825, 112), - mapOf(x to 5u, y to 3u) to Rational(201, 224), - mapOf(x to 6u, y to 3u) to Rational(-95, 16), - mapOf(y to 4u) to Rational(361, 16), - mapOf(x to 1u, y to 4u) to Rational(3667, 56), - mapOf(x to 2u, y to 4u) to Rational(88729, 1568), - mapOf(x to 3u, y to 4u) to Rational(-2476, 49), - mapOf(x to 4u, y to 4u) to Rational(-23419, 196), - mapOf(x to 5u, y to 4u) to Rational(-323, 56), - mapOf(x to 6u, y to 4u) to Rational(1805, 32), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - y to LabeledPolynomialAsIs( - mapOf() to Rational(-9, 2), - mapOf(x to 1u) to Rational(2, 7), - mapOf(x to 2u) to Rational(9, 1), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-1, 8), - mapOf(x to 2u, y to 1u) to Rational(2, 8), - mapOf(y to 2u) to Rational(19, 4), - mapOf(x to 1u, y to 2u) to Rational(15, 7), - mapOf(x to 2u, y to 2u) to Rational(-19, 4), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-11, 3), - mapOf(x to 1u) to Rational(5, 2), - mapOf(x to 2u) to Rational(13, 7), - mapOf(y to 1u) to Rational(16, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(6, 1), - mapOf(y to 2u) to Rational(-14, 3), - mapOf(x to 1u, y to 2u) to Rational(-2, 7), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - )), - "test 4'" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = t - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(7, 3), - mapOf(x to 2u) to Rational(-35, 16), - mapOf(x to 3u) to Rational(-343, 6), - mapOf(x to 4u) to Rational(343, 3), - mapOf(y to 1u) to Rational(-19, 5), - mapOf(x to 1u, y to 1u) to Rational(-823, 120), - mapOf(x to 2u, y to 1u) to Rational(1232417, 6720), - mapOf(x to 3u, y to 1u) to Rational(-9863, 24), - mapOf(x to 4u, y to 1u) to Rational(385, 4), - mapOf(y to 2u) to Rational(2439, 350), - mapOf(x to 1u, y to 2u) to Rational(-5793, 40), - mapOf(x to 2u, y to 2u) to Rational(1172113, 3360), - mapOf(x to 3u, y to 2u) to Rational(-13531, 40), - mapOf(x to 4u, y to 2u) to Rational(2824, 7), - mapOf(y to 3u) to Rational(3417, 700), - mapOf(x to 1u, y to 3u) to Rational(1191, 200), - mapOf(x to 2u, y to 3u) to Rational(8383, 28), - mapOf(x to 3u, y to 3u) to Rational(-220279, 280), - mapOf(x to 4u, y to 3u) to Rational(49179, 196), - mapOf(y to 4u) to Rational(57, 35), - mapOf(x to 1u, y to 4u) to Rational(-33771, 700), - mapOf(x to 2u, y to 4u) to Rational(196279, 1225), - mapOf(x to 3u, y to 4u) to Rational(-32259, 140), - mapOf(x to 4u, y to 4u) to Rational(23868, 49), - mapOf(y to 5u) to Rational(333, 196), - mapOf(x to 1u, y to 5u) to Rational(-204, 35), - mapOf(x to 2u, y to 5u) to Rational(-307233, 2450), - mapOf(x to 3u, y to 5u) to Rational(-12492, 35), - mapOf(x to 4u, y to 5u) to Rational(4563, 28), - mapOf(y to 6u) to Rational(45, 98), - mapOf(x to 1u, y to 6u) to Rational(54, 7), - mapOf(x to 2u, y to 6u) to Rational(1809, 35), - mapOf(x to 3u, y to 6u) to Rational(162), - mapOf(x to 4u, y to 6u) to Rational(405, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(0, 6), - mapOf(x to 1u) to Rational(14, 8), - mapOf(x to 2u) to Rational(-14, 2), - mapOf(y to 1u) to Rational(-3, 5), - mapOf(x to 1u, y to 1u) to Rational(11, 1), - mapOf(x to 2u, y to 1u) to Rational(3, 7), - mapOf(y to 2u) to Rational(-3, 7), - mapOf(x to 1u, y to 2u) to Rational(-18, 5), - mapOf(x to 2u, y to 2u) to Rational(-9, 1), - ), - )), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(7, 3), - mapOf(x to 2u) to Rational(-35, 16), - mapOf(x to 3u) to Rational(-343, 6), - mapOf(x to 4u) to Rational(343, 3), - mapOf(y to 1u) to Rational(-19, 5), - mapOf(x to 1u, y to 1u) to Rational(-823, 120), - mapOf(x to 2u, y to 1u) to Rational(1232417, 6720), - mapOf(x to 3u, y to 1u) to Rational(-9863, 24), - mapOf(x to 4u, y to 1u) to Rational(385, 4), - mapOf(y to 2u) to Rational(2439, 350), - mapOf(x to 1u, y to 2u) to Rational(-5793, 40), - mapOf(x to 2u, y to 2u) to Rational(1172113, 3360), - mapOf(x to 3u, y to 2u) to Rational(-13531, 40), - mapOf(x to 4u, y to 2u) to Rational(2824, 7), - mapOf(y to 3u) to Rational(3417, 700), - mapOf(x to 1u, y to 3u) to Rational(1191, 200), - mapOf(x to 2u, y to 3u) to Rational(8383, 28), - mapOf(x to 3u, y to 3u) to Rational(-220279, 280), - mapOf(x to 4u, y to 3u) to Rational(49179, 196), - mapOf(y to 4u) to Rational(57, 35), - mapOf(x to 1u, y to 4u) to Rational(-33771, 700), - mapOf(x to 2u, y to 4u) to Rational(196279, 1225), - mapOf(x to 3u, y to 4u) to Rational(-32259, 140), - mapOf(x to 4u, y to 4u) to Rational(23868, 49), - mapOf(y to 5u) to Rational(333, 196), - mapOf(x to 1u, y to 5u) to Rational(-204, 35), - mapOf(x to 2u, y to 5u) to Rational(-307233, 2450), - mapOf(x to 3u, y to 5u) to Rational(-12492, 35), - mapOf(x to 4u, y to 5u) to Rational(4563, 28), - mapOf(y to 6u) to Rational(45, 98), - mapOf(x to 1u, y to 6u) to Rational(54, 7), - mapOf(x to 2u, y to 6u) to Rational(1809, 35), - mapOf(x to 3u, y to 6u) to Rational(162), - mapOf(x to 4u, y to 6u) to Rational(405, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(0, 6), - mapOf(x to 1u) to Rational(14, 8), - mapOf(x to 2u) to Rational(-14, 2), - mapOf(y to 1u) to Rational(-3, 5), - mapOf(x to 1u, y to 1u) to Rational(11, 1), - mapOf(x to 2u, y to 1u) to Rational(3, 7), - mapOf(y to 2u) to Rational(-3, 7), - mapOf(x to 1u, y to 2u) to Rational(-18, 5), - mapOf(x to 2u, y to 2u) to Rational(-9, 1), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-11, 3), - mapOf(x to 1u) to Rational(5, 2), - mapOf(x to 2u) to Rational(13, 7), - mapOf(y to 1u) to Rational(16, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(6, 1), - mapOf(y to 2u) to Rational(-14, 3), - mapOf(x to 1u, y to 2u) to Rational(-2, 7), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - )), - "test 5'" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 2), - mapOf(x to 1u) to Rational(8, 6), - mapOf(x to 2u) to Rational(14, 6), - mapOf(y to 1u) to Rational(-3, 1), - mapOf(x to 1u, y to 1u) to Rational(-19, 2), - mapOf(x to 2u, y to 1u) to Rational(9, 4), - mapOf(y to 2u) to Rational(5, 5), - mapOf(x to 1u, y to 2u) to Rational(18, 9), - mapOf(x to 2u, y to 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-11, 3), - mapOf(x to 1u) to Rational(5, 2), - mapOf(x to 2u) to Rational(13, 7), - mapOf(y to 1u) to Rational(16, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(6, 1), - mapOf(y to 2u) to Rational(-14, 3), - mapOf(x to 1u, y to 2u) to Rational(-2, 7), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - )), - "test 6'" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_Polynomial_substitute_RationalFunction_Map() { - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(-194071, 4900), - mapOf(x to 3u, y to 1u) to Rational(394811, 225), - mapOf(x to 2u, y to 2u) to Rational(-444183161, 66150), - mapOf(x to 1u, y to 3u) to Rational(70537618, 59535), - mapOf(y to 4u) to Rational(9655504, 2835), - ), - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(9, 1), - mapOf(x to 3u, y to 1u) to Rational(61, 1), - mapOf(x to 2u, y to 2u) to Rational(2137, 36), - mapOf(x to 1u, y to 3u) to Rational(-1342, 9), - mapOf(y to 4u) to Rational(484, 9), - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(17, 7), - mapOf(y to 1u) to Rational(-13, 1), - ), - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-18, 6), - mapOf(y to 1u) to Rational(11, 6), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(18, 5), - mapOf(y to 1u) to Rational(-16, 3), - ), - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-1, 1), - mapOf(y to 1u) to Rational(-4, 1), - ) - ), - )), - "test 2" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-6443599, 10000), - mapOf(x to 1u) to Rational(166251223, 210000), - mapOf(x to 2u) to Rational(-4606805099, 3528000), - mapOf(x to 3u) to Rational(51204379, 19600), - mapOf(x to 4u) to Rational(-529045460659, 277830000), - mapOf(x to 5u) to Rational(2630836709, 1488375), - mapOf(x to 6u) to Rational(-42675691369, 25004700), - mapOf(x to 7u) to Rational(495825223, 1250235), - mapOf(x to 8u) to Rational(-22531756, 1750329), - mapOf(y to 1u) to Rational(-2526552797, 420000), - mapOf(x to 1u, y to 1u) to Rational(31108840471, 2520000), - mapOf(x to 2u, y to 1u) to Rational(-4789740847, 1102500), - mapOf(x to 3u, y to 1u) to Rational(186594307807, 11340000), - mapOf(x to 4u, y to 1u) to Rational(-11677815943, 1488375), - mapOf(x to 5u, y to 1u) to Rational(-181118486447, 27783000), - mapOf(x to 6u, y to 1u) to Rational(-16123292162, 14586075), - mapOf(x to 7u, y to 1u) to Rational(-140339343808, 26254935), - mapOf(x to 8u, y to 1u) to Rational(4570171616, 5250987), - mapOf(y to 2u) to Rational(-181436530573, 10080000), - mapOf(x to 1u, y to 2u) to Rational(6700437957491, 105840000), - mapOf(x to 2u, y to 2u) to Rational(-3527267461, 1417500), - mapOf(x to 3u, y to 2u) to Rational(-38084563451, 5556600), - mapOf(x to 4u, y to 2u) to Rational(-565662040631, 13891500), - mapOf(x to 5u, y to 2u) to Rational(-35479071126397, 583443000), - mapOf(x to 6u, y to 2u) to Rational(-11717559078469, 525098700), - mapOf(x to 7u, y to 2u) to Rational(-2043385293517, 225042300), - mapOf(x to 8u, y to 2u) to Rational(-3644439630451, 551353635), - mapOf(y to 3u) to Rational(-1760423269, 126000), - mapOf(x to 1u, y to 3u) to Rational(310176758299, 2352000), - mapOf(x to 2u, y to 3u) to Rational(-907229584837, 21168000), - mapOf(x to 3u, y to 3u) to Rational(-16717135885963, 95256000), - mapOf(x to 4u, y to 3u) to Rational(-43762928025353, 333396000), - mapOf(x to 5u, y to 3u) to Rational(-328427480571607, 3000564000), - mapOf(x to 6u, y to 3u) to Rational(-7722675917197, 210039480), - mapOf(x to 7u, y to 3u) to Rational(1713350137019, 1225230300), - mapOf(x to 8u, y to 3u) to Rational(156695935643, 31505922), - mapOf(y to 4u) to Rational(18362364269, 1008000), - mapOf(x to 1u, y to 4u) to Rational(955674858553, 10584000), - mapOf(x to 2u, y to 4u) to Rational(-71937470607371, 444528000), - mapOf(x to 3u, y to 4u) to Rational(-34097985615163, 95256000), - mapOf(x to 4u, y to 4u) to Rational(-340736178775883, 2000376000), - mapOf(x to 5u, y to 4u) to Rational(-511324523441897, 10501974000), - mapOf(x to 6u, y to 4u) to Rational(-125375649409151, 8821658160), - mapOf(x to 7u, y to 4u) to Rational(-2813518533421, 1575296100), - mapOf(x to 8u, y to 4u) to Rational(-17044089109, 5250987), - mapOf(y to 5u) to Rational(600086461, 20160), - mapOf(x to 1u, y to 5u) to Rational(-18959931367, 423360), - mapOf(x to 2u, y to 5u) to Rational(-9178804929607, 44452800), - mapOf(x to 3u, y to 5u) to Rational(-1460114275979, 5334336), - mapOf(x to 4u, y to 5u) to Rational(-342533479090169, 4200789600), - mapOf(x to 5u, y to 5u) to Rational(20335453022963, 4200789600), - mapOf(x to 6u, y to 5u) to Rational(-21649775090197, 6301184400), - mapOf(x to 7u, y to 5u) to Rational(-197301716069, 131274675), - mapOf(x to 8u, y to 5u) to Rational(18711357470, 15752961), - mapOf(y to 6u) to Rational(621417991, 100800), - mapOf(x to 1u, y to 6u) to Rational(-159236792977, 2116800), - mapOf(x to 2u, y to 6u) to Rational(-6602528890883, 66679200), - mapOf(x to 3u, y to 6u) to Rational(-1086091664047, 19051200), - mapOf(x to 4u, y to 6u) to Rational(3769375009003, 1680315840), - mapOf(x to 5u, y to 6u) to Rational(-12920385574769, 1050197400), - mapOf(x to 6u, y to 6u) to Rational(-90219591809287, 6301184400), - mapOf(x to 7u, y to 6u) to Rational(656361553391, 1575296100), - mapOf(x to 8u, y to 6u) to Rational(757900793, 2250423), - mapOf(y to 7u) to Rational(-100770017, 15120), - mapOf(x to 1u, y to 7u) to Rational(-316364851, 17640), - mapOf(x to 2u, y to 7u) to Rational(-85118560057, 6667920), - mapOf(x to 3u, y to 7u) to Rational(6286563719, 416745), - mapOf(x to 4u, y to 7u) to Rational(26803885301, 1714608), - mapOf(x to 5u, y to 7u) to Rational(-13767154393, 4286520), - mapOf(x to 6u, y to 7u) to Rational(-3875138933, 1224720), - mapOf(x to 7u, y to 7u) to Rational(65193755, 333396), - mapOf(x to 8u, y to 7u) to Rational(90974351, 2500470), - mapOf(y to 8u) to Rational(-3182197, 1260), - mapOf(x to 1u, y to 8u) to Rational(24899923, 8820), - mapOf(x to 2u, y to 8u) to Rational(-19999556, 19845), - mapOf(x to 3u, y to 8u) to Rational(3276587, 3969), - mapOf(x to 4u, y to 8u) to Rational(13719549239, 5000940), - mapOf(x to 5u, y to 8u) to Rational(-961839938, 1250235), - mapOf(x to 6u, y to 8u) to Rational(-198184871, 833490), - mapOf(x to 7u, y to 8u) to Rational(230659711, 5000940), - mapOf(x to 8u, y to 8u) to Rational(292447, 35721) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(9, 100), - mapOf(x to 1u) to Rational(-21, 50), - mapOf(x to 2u) to Rational(293, 700), - mapOf(x to 3u) to Rational(29, 210), - mapOf(x to 4u) to Rational(3233, 8820), - mapOf(x to 5u) to Rational(-289, 441), - mapOf(x to 6u) to Rational(-1, 9), - mapOf(x to 7u) to Rational(-20, 441), - mapOf(x to 8u) to Rational(100, 441), - mapOf(y to 1u) to Rational(-57, 80), - mapOf(x to 1u, y to 1u) to Rational(-121, 400), - mapOf(x to 2u, y to 1u) to Rational(37117, 8400), - mapOf(x to 3u, y to 1u) to Rational(-4853, 3150), - mapOf(x to 4u, y to 1u) to Rational(1166203, 132300), - mapOf(x to 5u, y to 1u) to Rational(-2708, 567), - mapOf(x to 6u, y to 1u) to Rational(-287159, 416745), - mapOf(x to 7u, y to 1u) to Rational(-478204, 83349), - mapOf(x to 8u, y to 1u) to Rational(176320, 83349), - mapOf(y to 2u) to Rational(-6239, 6400), - mapOf(x to 1u, y to 2u) to Rational(264211, 11200), - mapOf(x to 2u, y to 2u) to Rational(-1591999, 100800), - mapOf(x to 3u, y to 2u) to Rational(12450091, 529200), - mapOf(x to 4u, y to 2u) to Rational(9230759, 226800), - mapOf(x to 5u, y to 2u) to Rational(18995554, 2083725), - mapOf(x to 6u, y to 2u) to Rational(136706258, 6251175), - mapOf(x to 7u, y to 2u) to Rational(-120907496, 3750705), - mapOf(x to 8u, y to 2u) to Rational(117200176, 15752961), - mapOf(y to 3u) to Rational(5653, 320), - mapOf(x to 1u, y to 3u) to Rational(-130853, 8400), - mapOf(x to 2u, y to 3u) to Rational(-20939327, 151200), - mapOf(x to 3u, y to 3u) to Rational(2566691, 25200), - mapOf(x to 4u, y to 3u) to Rational(-68441519, 476280), - mapOf(x to 5u, y to 3u) to Rational(2462904247, 12502350), - mapOf(x to 6u, y to 3u) to Rational(353667161, 18753525), - mapOf(x to 7u, y to 3u) to Rational(-1689134372, 26254935), - mapOf(x to 8u, y to 3u) to Rational(35084104, 2250423), - mapOf(y to 4u) to Rational(-3587, 300), - mapOf(x to 1u, y to 4u) to Rational(-10513243, 33600), - mapOf(x to 2u, y to 4u) to Rational(30766733, 176400), - mapOf(x to 3u, y to 4u) to Rational(-65680021, 198450), - mapOf(x to 4u, y to 4u) to Rational(-8108910547, 20003760), - mapOf(x to 5u, y to 4u) to Rational(2922125159, 6251175), - mapOf(x to 6u, y to 4u) to Rational(-4245279943, 131274675), - mapOf(x to 7u, y to 4u) to Rational(-371946872, 3750705), - mapOf(x to 8u, y to 4u) to Rational(61286752, 2250423), - mapOf(y to 5u) to Rational(-20477, 160), - mapOf(x to 1u, y to 5u) to Rational(215741, 1120), - mapOf(x to 2u, y to 5u) to Rational(30785843, 31752), - mapOf(x to 3u, y to 5u) to Rational(-357495959, 317520), - mapOf(x to 4u, y to 5u) to Rational(-1611242993, 10001880), - mapOf(x to 5u, y to 5u) to Rational(345925495, 500094), - mapOf(x to 6u, y to 5u) to Rational(-755948411, 3750705), - mapOf(x to 7u, y to 5u) to Rational(-108643496, 1250235), - mapOf(x to 8u, y to 5u) to Rational(1122512, 35721), - mapOf(y to 6u) to Rational(358037, 2880), - mapOf(x to 1u, y to 6u) to Rational(3895837, 3360), - mapOf(x to 2u, y to 6u) to Rational(359419201, 1270080), - mapOf(x to 3u, y to 6u) to Rational(-158522587, 105840), - mapOf(x to 4u, y to 6u) to Rational(10909002599, 20003760), - mapOf(x to 5u, y to 6u) to Rational(76846972, 138915), - mapOf(x to 6u, y to 6u) to Rational(-327696553, 1250235), - mapOf(x to 7u, y to 6u) to Rational(-1687328, 35721), - mapOf(x to 8u, y to 6u) to Rational(1016836, 35721), - mapOf(y to 7u) to Rational(658, 3), - mapOf(x to 1u, y to 7u) to Rational(48035, 168), - mapOf(x to 2u, y to 7u) to Rational(-5777875, 5292), - mapOf(x to 3u, y to 7u) to Rational(-7893899, 10584), - mapOf(x to 4u, y to 7u) to Rational(10191652, 11907), - mapOf(x to 5u, y to 7u) to Rational(2920121, 23814), - mapOf(x to 6u, y to 7u) to Rational(-2699780, 11907), - mapOf(x to 7u, y to 7u) to Rational(4556, 441), - mapOf(x to 8u, y to 7u) to Rational(3440, 189), - mapOf(y to 8u) to Rational(64, 1), - mapOf(x to 1u, y to 8u) to Rational(-808, 7), - mapOf(x to 2u, y to 8u) to Rational(-360895, 1764), - mapOf(x to 3u, y to 8u) to Rational(257657, 882), - mapOf(x to 4u, y to 8u) to Rational(3779917, 15876), - mapOf(x to 5u, y to 8u) to Rational(-610279, 3969), - mapOf(x to 6u, y to 8u) to Rational(-25091, 441), - mapOf(x to 7u, y to 8u) to Rational(9560, 567), - mapOf(x to 8u, y to 8u) to Rational(400, 81) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(17, 5), - mapOf(x to 1u) to Rational(11, 6), - mapOf(x to 2u) to Rational(14, 3), - mapOf(y to 1u) to Rational(17, 1), - mapOf(x to 1u, y to 1u) to Rational(12, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 2), - mapOf(y to 2u) to Rational(17, 1), - mapOf(x to 1u, y to 2u) to Rational(-4, 3), - mapOf(x to 2u, y to 2u) to Rational(2, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(3, 5), - mapOf(x to 1u) to Rational(3, 5), - mapOf(x to 2u) to Rational(3, 7), - mapOf(y to 1u) to Rational(-3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 1), - mapOf(x to 2u, y to 1u) to Rational(17, 9), - mapOf(y to 2u) to Rational(-8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 4), - mapOf(x to 2u, y to 2u) to Rational(10, 9), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(18, 5), - mapOf(x to 1u) to Rational(-17, 5), - mapOf(x to 2u) to Rational(-2, 7), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(-5, 1), - mapOf(x to 2u, y to 1u) to Rational(-9, 1), - mapOf(y to 2u) to Rational(-8, 8), - mapOf(x to 1u, y to 2u) to Rational(2, 7), - mapOf(x to 2u, y to 2u) to Rational(-13, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-4, 8), - mapOf(x to 1u) to Rational(15, 9), - mapOf(x to 2u) to Rational(-10, 9), - mapOf(y to 1u) to Rational(5, 3), - mapOf(x to 1u, y to 1u) to Rational(4, 1), - mapOf(x to 2u, y to 1u) to Rational(-2, 7), - mapOf(y to 2u) to Rational(2, 2), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(-18, 9), - ) - ), - )), - "test 3" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-6443599, 10000), - mapOf(x to 1u) to Rational(166251223, 210000), - mapOf(x to 2u) to Rational(-4606805099, 3528000), - mapOf(x to 3u) to Rational(51204379, 19600), - mapOf(x to 4u) to Rational(-529045460659, 277830000), - mapOf(x to 5u) to Rational(2630836709, 1488375), - mapOf(x to 6u) to Rational(-42675691369, 25004700), - mapOf(x to 7u) to Rational(495825223, 1250235), - mapOf(x to 8u) to Rational(-22531756, 1750329), - mapOf(y to 1u) to Rational(-2526552797, 420000), - mapOf(x to 1u, y to 1u) to Rational(31108840471, 2520000), - mapOf(x to 2u, y to 1u) to Rational(-4789740847, 1102500), - mapOf(x to 3u, y to 1u) to Rational(186594307807, 11340000), - mapOf(x to 4u, y to 1u) to Rational(-11677815943, 1488375), - mapOf(x to 5u, y to 1u) to Rational(-181118486447, 27783000), - mapOf(x to 6u, y to 1u) to Rational(-16123292162, 14586075), - mapOf(x to 7u, y to 1u) to Rational(-140339343808, 26254935), - mapOf(x to 8u, y to 1u) to Rational(4570171616, 5250987), - mapOf(y to 2u) to Rational(-181436530573, 10080000), - mapOf(x to 1u, y to 2u) to Rational(6700437957491, 105840000), - mapOf(x to 2u, y to 2u) to Rational(-3527267461, 1417500), - mapOf(x to 3u, y to 2u) to Rational(-38084563451, 5556600), - mapOf(x to 4u, y to 2u) to Rational(-565662040631, 13891500), - mapOf(x to 5u, y to 2u) to Rational(-35479071126397, 583443000), - mapOf(x to 6u, y to 2u) to Rational(-11717559078469, 525098700), - mapOf(x to 7u, y to 2u) to Rational(-2043385293517, 225042300), - mapOf(x to 8u, y to 2u) to Rational(-3644439630451, 551353635), - mapOf(y to 3u) to Rational(-1760423269, 126000), - mapOf(x to 1u, y to 3u) to Rational(310176758299, 2352000), - mapOf(x to 2u, y to 3u) to Rational(-907229584837, 21168000), - mapOf(x to 3u, y to 3u) to Rational(-16717135885963, 95256000), - mapOf(x to 4u, y to 3u) to Rational(-43762928025353, 333396000), - mapOf(x to 5u, y to 3u) to Rational(-328427480571607, 3000564000), - mapOf(x to 6u, y to 3u) to Rational(-7722675917197, 210039480), - mapOf(x to 7u, y to 3u) to Rational(1713350137019, 1225230300), - mapOf(x to 8u, y to 3u) to Rational(156695935643, 31505922), - mapOf(y to 4u) to Rational(18362364269, 1008000), - mapOf(x to 1u, y to 4u) to Rational(955674858553, 10584000), - mapOf(x to 2u, y to 4u) to Rational(-71937470607371, 444528000), - mapOf(x to 3u, y to 4u) to Rational(-34097985615163, 95256000), - mapOf(x to 4u, y to 4u) to Rational(-340736178775883, 2000376000), - mapOf(x to 5u, y to 4u) to Rational(-511324523441897, 10501974000), - mapOf(x to 6u, y to 4u) to Rational(-125375649409151, 8821658160), - mapOf(x to 7u, y to 4u) to Rational(-2813518533421, 1575296100), - mapOf(x to 8u, y to 4u) to Rational(-17044089109, 5250987), - mapOf(y to 5u) to Rational(600086461, 20160), - mapOf(x to 1u, y to 5u) to Rational(-18959931367, 423360), - mapOf(x to 2u, y to 5u) to Rational(-9178804929607, 44452800), - mapOf(x to 3u, y to 5u) to Rational(-1460114275979, 5334336), - mapOf(x to 4u, y to 5u) to Rational(-342533479090169, 4200789600), - mapOf(x to 5u, y to 5u) to Rational(20335453022963, 4200789600), - mapOf(x to 6u, y to 5u) to Rational(-21649775090197, 6301184400), - mapOf(x to 7u, y to 5u) to Rational(-197301716069, 131274675), - mapOf(x to 8u, y to 5u) to Rational(18711357470, 15752961), - mapOf(y to 6u) to Rational(621417991, 100800), - mapOf(x to 1u, y to 6u) to Rational(-159236792977, 2116800), - mapOf(x to 2u, y to 6u) to Rational(-6602528890883, 66679200), - mapOf(x to 3u, y to 6u) to Rational(-1086091664047, 19051200), - mapOf(x to 4u, y to 6u) to Rational(3769375009003, 1680315840), - mapOf(x to 5u, y to 6u) to Rational(-12920385574769, 1050197400), - mapOf(x to 6u, y to 6u) to Rational(-90219591809287, 6301184400), - mapOf(x to 7u, y to 6u) to Rational(656361553391, 1575296100), - mapOf(x to 8u, y to 6u) to Rational(757900793, 2250423), - mapOf(y to 7u) to Rational(-100770017, 15120), - mapOf(x to 1u, y to 7u) to Rational(-316364851, 17640), - mapOf(x to 2u, y to 7u) to Rational(-85118560057, 6667920), - mapOf(x to 3u, y to 7u) to Rational(6286563719, 416745), - mapOf(x to 4u, y to 7u) to Rational(26803885301, 1714608), - mapOf(x to 5u, y to 7u) to Rational(-13767154393, 4286520), - mapOf(x to 6u, y to 7u) to Rational(-3875138933, 1224720), - mapOf(x to 7u, y to 7u) to Rational(65193755, 333396), - mapOf(x to 8u, y to 7u) to Rational(90974351, 2500470), - mapOf(y to 8u) to Rational(-3182197, 1260), - mapOf(x to 1u, y to 8u) to Rational(24899923, 8820), - mapOf(x to 2u, y to 8u) to Rational(-19999556, 19845), - mapOf(x to 3u, y to 8u) to Rational(3276587, 3969), - mapOf(x to 4u, y to 8u) to Rational(13719549239, 5000940), - mapOf(x to 5u, y to 8u) to Rational(-961839938, 1250235), - mapOf(x to 6u, y to 8u) to Rational(-198184871, 833490), - mapOf(x to 7u, y to 8u) to Rational(230659711, 5000940), - mapOf(x to 8u, y to 8u) to Rational(292447, 35721) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(9, 100), - mapOf(x to 1u) to Rational(-21, 50), - mapOf(x to 2u) to Rational(293, 700), - mapOf(x to 3u) to Rational(29, 210), - mapOf(x to 4u) to Rational(3233, 8820), - mapOf(x to 5u) to Rational(-289, 441), - mapOf(x to 6u) to Rational(-1, 9), - mapOf(x to 7u) to Rational(-20, 441), - mapOf(x to 8u) to Rational(100, 441), - mapOf(y to 1u) to Rational(-57, 80), - mapOf(x to 1u, y to 1u) to Rational(-121, 400), - mapOf(x to 2u, y to 1u) to Rational(37117, 8400), - mapOf(x to 3u, y to 1u) to Rational(-4853, 3150), - mapOf(x to 4u, y to 1u) to Rational(1166203, 132300), - mapOf(x to 5u, y to 1u) to Rational(-2708, 567), - mapOf(x to 6u, y to 1u) to Rational(-287159, 416745), - mapOf(x to 7u, y to 1u) to Rational(-478204, 83349), - mapOf(x to 8u, y to 1u) to Rational(176320, 83349), - mapOf(y to 2u) to Rational(-6239, 6400), - mapOf(x to 1u, y to 2u) to Rational(264211, 11200), - mapOf(x to 2u, y to 2u) to Rational(-1591999, 100800), - mapOf(x to 3u, y to 2u) to Rational(12450091, 529200), - mapOf(x to 4u, y to 2u) to Rational(9230759, 226800), - mapOf(x to 5u, y to 2u) to Rational(18995554, 2083725), - mapOf(x to 6u, y to 2u) to Rational(136706258, 6251175), - mapOf(x to 7u, y to 2u) to Rational(-120907496, 3750705), - mapOf(x to 8u, y to 2u) to Rational(117200176, 15752961), - mapOf(y to 3u) to Rational(5653, 320), - mapOf(x to 1u, y to 3u) to Rational(-130853, 8400), - mapOf(x to 2u, y to 3u) to Rational(-20939327, 151200), - mapOf(x to 3u, y to 3u) to Rational(2566691, 25200), - mapOf(x to 4u, y to 3u) to Rational(-68441519, 476280), - mapOf(x to 5u, y to 3u) to Rational(2462904247, 12502350), - mapOf(x to 6u, y to 3u) to Rational(353667161, 18753525), - mapOf(x to 7u, y to 3u) to Rational(-1689134372, 26254935), - mapOf(x to 8u, y to 3u) to Rational(35084104, 2250423), - mapOf(y to 4u) to Rational(-3587, 300), - mapOf(x to 1u, y to 4u) to Rational(-10513243, 33600), - mapOf(x to 2u, y to 4u) to Rational(30766733, 176400), - mapOf(x to 3u, y to 4u) to Rational(-65680021, 198450), - mapOf(x to 4u, y to 4u) to Rational(-8108910547, 20003760), - mapOf(x to 5u, y to 4u) to Rational(2922125159, 6251175), - mapOf(x to 6u, y to 4u) to Rational(-4245279943, 131274675), - mapOf(x to 7u, y to 4u) to Rational(-371946872, 3750705), - mapOf(x to 8u, y to 4u) to Rational(61286752, 2250423), - mapOf(y to 5u) to Rational(-20477, 160), - mapOf(x to 1u, y to 5u) to Rational(215741, 1120), - mapOf(x to 2u, y to 5u) to Rational(30785843, 31752), - mapOf(x to 3u, y to 5u) to Rational(-357495959, 317520), - mapOf(x to 4u, y to 5u) to Rational(-1611242993, 10001880), - mapOf(x to 5u, y to 5u) to Rational(345925495, 500094), - mapOf(x to 6u, y to 5u) to Rational(-755948411, 3750705), - mapOf(x to 7u, y to 5u) to Rational(-108643496, 1250235), - mapOf(x to 8u, y to 5u) to Rational(1122512, 35721), - mapOf(y to 6u) to Rational(358037, 2880), - mapOf(x to 1u, y to 6u) to Rational(3895837, 3360), - mapOf(x to 2u, y to 6u) to Rational(359419201, 1270080), - mapOf(x to 3u, y to 6u) to Rational(-158522587, 105840), - mapOf(x to 4u, y to 6u) to Rational(10909002599, 20003760), - mapOf(x to 5u, y to 6u) to Rational(76846972, 138915), - mapOf(x to 6u, y to 6u) to Rational(-327696553, 1250235), - mapOf(x to 7u, y to 6u) to Rational(-1687328, 35721), - mapOf(x to 8u, y to 6u) to Rational(1016836, 35721), - mapOf(y to 7u) to Rational(658, 3), - mapOf(x to 1u, y to 7u) to Rational(48035, 168), - mapOf(x to 2u, y to 7u) to Rational(-5777875, 5292), - mapOf(x to 3u, y to 7u) to Rational(-7893899, 10584), - mapOf(x to 4u, y to 7u) to Rational(10191652, 11907), - mapOf(x to 5u, y to 7u) to Rational(2920121, 23814), - mapOf(x to 6u, y to 7u) to Rational(-2699780, 11907), - mapOf(x to 7u, y to 7u) to Rational(4556, 441), - mapOf(x to 8u, y to 7u) to Rational(3440, 189), - mapOf(y to 8u) to Rational(64, 1), - mapOf(x to 1u, y to 8u) to Rational(-808, 7), - mapOf(x to 2u, y to 8u) to Rational(-360895, 1764), - mapOf(x to 3u, y to 8u) to Rational(257657, 882), - mapOf(x to 4u, y to 8u) to Rational(3779917, 15876), - mapOf(x to 5u, y to 8u) to Rational(-610279, 3969), - mapOf(x to 6u, y to 8u) to Rational(-25091, 441), - mapOf(x to 7u, y to 8u) to Rational(9560, 567), - mapOf(x to 8u, y to 8u) to Rational(400, 81) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(17, 5), - mapOf(x to 1u) to Rational(11, 6), - mapOf(x to 2u) to Rational(14, 3), - mapOf(y to 1u) to Rational(17, 1), - mapOf(x to 1u, y to 1u) to Rational(12, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 2), - mapOf(y to 2u) to Rational(17, 1), - mapOf(x to 1u, y to 2u) to Rational(-4, 3), - mapOf(x to 2u, y to 2u) to Rational(2, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(3, 5), - mapOf(x to 1u) to Rational(3, 5), - mapOf(x to 2u) to Rational(3, 7), - mapOf(y to 1u) to Rational(-3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 1), - mapOf(x to 2u, y to 1u) to Rational(17, 9), - mapOf(y to 2u) to Rational(-8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 4), - mapOf(x to 2u, y to 2u) to Rational(10, 9), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(18, 5), - mapOf(x to 1u) to Rational(-17, 5), - mapOf(x to 2u) to Rational(-2, 7), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(-5, 1), - mapOf(x to 2u, y to 1u) to Rational(-9, 1), - mapOf(y to 2u) to Rational(-8, 8), - mapOf(x to 1u, y to 2u) to Rational(2, 7), - mapOf(x to 2u, y to 2u) to Rational(-13, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-4, 8), - mapOf(x to 1u) to Rational(15, 9), - mapOf(x to 2u) to Rational(-10, 9), - mapOf(y to 1u) to Rational(5, 3), - mapOf(x to 1u, y to 1u) to Rational(4, 1), - mapOf(x to 2u, y to 1u) to Rational(-2, 7), - mapOf(y to 2u) to Rational(2, 2), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(-18, 9), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 9), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(10, 9), - mapOf(y to 1u) to Rational(13, 3), - mapOf(x to 1u, y to 1u) to Rational(-12, 4), - mapOf(x to 2u, y to 1u) to Rational(3, 6), - mapOf(y to 2u) to Rational(2, 9), - mapOf(x to 1u, y to 2u) to Rational(7, 3), - mapOf(x to 2u, y to 2u) to Rational(16, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 2), - mapOf(x to 1u) to Rational(6, 2), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 5), - mapOf(y to 2u) to Rational(8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(17, 4), - ) - ) - )), - "test 3'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-66677, 3500), - mapOf(x to 1u) to Rational(-206281, 10500), - mapOf(x to 2u) to Rational(-412567, 7056), - mapOf(x to 3u) to Rational(-310081, 11025), - mapOf(x to 4u) to Rational(-575996, 15435), - mapOf(y to 1u) to Rational(-573701, 4200), - mapOf(x to 1u, y to 1u) to Rational(-2239001, 25200), - mapOf(x to 2u, y to 1u) to Rational(-8817889, 132300), - mapOf(x to 3u, y to 1u) to Rational(2317919, 44100), - mapOf(x to 4u, y to 1u) to Rational(1169471, 6615), - mapOf(y to 2u) to Rational(-4057819, 33600), - mapOf(x to 1u, y to 2u) to Rational(1373311, 12600), - mapOf(x to 2u, y to 2u) to Rational(32433493, 52920), - mapOf(x to 3u, y to 2u) to Rational(4998053, 33075), - mapOf(x to 4u, y to 2u) to Rational(-2147779, 8820), - mapOf(y to 3u) to Rational(2018481, 2240), - mapOf(x to 1u, y to 3u) to Rational(941713, 1440), - mapOf(x to 2u, y to 3u) to Rational(183749, 6615), - mapOf(x to 3u, y to 3u) to Rational(-4631023, 15876), - mapOf(x to 4u, y to 3u) to Rational(25609336, 178605), - mapOf(y to 4u) to Rational(11886431, 6720), - mapOf(x to 1u, y to 4u) to Rational(18433, 504), - mapOf(x to 2u, y to 4u) to Rational(-39613331, 45360), - mapOf(x to 3u, y to 4u) to Rational(681619, 5670), - mapOf(x to 4u, y to 4u) to Rational(-864841, 20412), - mapOf(y to 5u) to Rational(343535, 1008), - mapOf(x to 1u, y to 5u) to Rational(-33583, 72), - mapOf(x to 2u, y to 5u) to Rational(1194625, 9072), - mapOf(x to 3u, y to 5u) to Rational(-62917, 2268), - mapOf(x to 4u, y to 5u) to Rational(157645, 10206), - mapOf(y to 6u) to Rational(-1381, 3), - mapOf(x to 1u, y to 6u) to Rational(919, 36), - mapOf(x to 2u, y to 6u) to Rational(-3053, 36), - mapOf(x to 3u, y to 6u) to Rational(2125, 324), - mapOf(x to 4u, y to 6u) to Rational(-236, 243) - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-5, 3), - mapOf(x to 2u) to Rational(35, 9), - mapOf(x to 3u) to Rational(-100, 27), - mapOf(x to 4u) to Rational(100, 81), - mapOf(y to 1u) to Rational(-5, 3), - mapOf(x to 1u, y to 1u) to Rational(14, 9), - mapOf(x to 2u, y to 1u) to Rational(1874, 189), - mapOf(x to 3u, y to 1u) to Rational(-620, 63), - mapOf(x to 4u, y to 1u) to Rational(40, 63), - mapOf(y to 2u) to Rational(16, 9), - mapOf(x to 1u, y to 2u) to Rational(365, 21), - mapOf(x to 2u, y to 2u) to Rational(112, 9), - mapOf(x to 3u, y to 2u) to Rational(-464, 63), - mapOf(x to 4u, y to 2u) to Rational(1996, 441), - mapOf(y to 3u) to Rational(10, 3), - mapOf(x to 1u, y to 3u) to Rational(118, 21), - mapOf(x to 2u, y to 3u) to Rational(-272, 21), - mapOf(x to 3u, y to 3u) to Rational(-764, 49), - mapOf(x to 4u, y to 3u) to Rational(8, 7), - mapOf(y to 4u) to Rational(1, 1), - mapOf(x to 1u, y to 4u) to Rational(-10, 7), - mapOf(x to 2u, y to 4u) to Rational(-171, 49), - mapOf(x to 3u, y to 4u) to Rational(20, 7), - mapOf(x to 4u, y to 4u) to Rational(4, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(17, 5), - mapOf(x to 1u) to Rational(11, 6), - mapOf(x to 2u) to Rational(14, 3), - mapOf(y to 1u) to Rational(17, 1), - mapOf(x to 1u, y to 1u) to Rational(12, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 2), - mapOf(y to 2u) to Rational(17, 1), - mapOf(x to 1u, y to 2u) to Rational(-4, 3), - mapOf(x to 2u, y to 2u) to Rational(2, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(3, 5), - mapOf(x to 1u) to Rational(3, 5), - mapOf(x to 2u) to Rational(3, 7), - mapOf(y to 1u) to Rational(-3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 1), - mapOf(x to 2u, y to 1u) to Rational(17, 9), - mapOf(y to 2u) to Rational(-8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 4), - mapOf(x to 2u, y to 2u) to Rational(10, 9), - ) - ), - )), - "test 4" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-66677, 3500), - mapOf(x to 1u) to Rational(-206281, 10500), - mapOf(x to 2u) to Rational(-412567, 7056), - mapOf(x to 3u) to Rational(-310081, 11025), - mapOf(x to 4u) to Rational(-575996, 15435), - mapOf(y to 1u) to Rational(-573701, 4200), - mapOf(x to 1u, y to 1u) to Rational(-2239001, 25200), - mapOf(x to 2u, y to 1u) to Rational(-8817889, 132300), - mapOf(x to 3u, y to 1u) to Rational(2317919, 44100), - mapOf(x to 4u, y to 1u) to Rational(1169471, 6615), - mapOf(y to 2u) to Rational(-4057819, 33600), - mapOf(x to 1u, y to 2u) to Rational(1373311, 12600), - mapOf(x to 2u, y to 2u) to Rational(32433493, 52920), - mapOf(x to 3u, y to 2u) to Rational(4998053, 33075), - mapOf(x to 4u, y to 2u) to Rational(-2147779, 8820), - mapOf(y to 3u) to Rational(2018481, 2240), - mapOf(x to 1u, y to 3u) to Rational(941713, 1440), - mapOf(x to 2u, y to 3u) to Rational(183749, 6615), - mapOf(x to 3u, y to 3u) to Rational(-4631023, 15876), - mapOf(x to 4u, y to 3u) to Rational(25609336, 178605), - mapOf(y to 4u) to Rational(11886431, 6720), - mapOf(x to 1u, y to 4u) to Rational(18433, 504), - mapOf(x to 2u, y to 4u) to Rational(-39613331, 45360), - mapOf(x to 3u, y to 4u) to Rational(681619, 5670), - mapOf(x to 4u, y to 4u) to Rational(-864841, 20412), - mapOf(y to 5u) to Rational(343535, 1008), - mapOf(x to 1u, y to 5u) to Rational(-33583, 72), - mapOf(x to 2u, y to 5u) to Rational(1194625, 9072), - mapOf(x to 3u, y to 5u) to Rational(-62917, 2268), - mapOf(x to 4u, y to 5u) to Rational(157645, 10206), - mapOf(y to 6u) to Rational(-1381, 3), - mapOf(x to 1u, y to 6u) to Rational(919, 36), - mapOf(x to 2u, y to 6u) to Rational(-3053, 36), - mapOf(x to 3u, y to 6u) to Rational(2125, 324), - mapOf(x to 4u, y to 6u) to Rational(-236, 243) - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-5, 3), - mapOf(x to 2u) to Rational(35, 9), - mapOf(x to 3u) to Rational(-100, 27), - mapOf(x to 4u) to Rational(100, 81), - mapOf(y to 1u) to Rational(-5, 3), - mapOf(x to 1u, y to 1u) to Rational(14, 9), - mapOf(x to 2u, y to 1u) to Rational(1874, 189), - mapOf(x to 3u, y to 1u) to Rational(-620, 63), - mapOf(x to 4u, y to 1u) to Rational(40, 63), - mapOf(y to 2u) to Rational(16, 9), - mapOf(x to 1u, y to 2u) to Rational(365, 21), - mapOf(x to 2u, y to 2u) to Rational(112, 9), - mapOf(x to 3u, y to 2u) to Rational(-464, 63), - mapOf(x to 4u, y to 2u) to Rational(1996, 441), - mapOf(y to 3u) to Rational(10, 3), - mapOf(x to 1u, y to 3u) to Rational(118, 21), - mapOf(x to 2u, y to 3u) to Rational(-272, 21), - mapOf(x to 3u, y to 3u) to Rational(-764, 49), - mapOf(x to 4u, y to 3u) to Rational(8, 7), - mapOf(y to 4u) to Rational(1, 1), - mapOf(x to 1u, y to 4u) to Rational(-10, 7), - mapOf(x to 2u, y to 4u) to Rational(-171, 49), - mapOf(x to 3u, y to 4u) to Rational(20, 7), - mapOf(x to 4u, y to 4u) to Rational(4, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(17, 5), - mapOf(x to 1u) to Rational(11, 6), - mapOf(x to 2u) to Rational(14, 3), - mapOf(y to 1u) to Rational(17, 1), - mapOf(x to 1u, y to 1u) to Rational(12, 3), - mapOf(x to 2u, y to 1u) to Rational(-6, 2), - mapOf(y to 2u) to Rational(17, 1), - mapOf(x to 1u, y to 2u) to Rational(-4, 3), - mapOf(x to 2u, y to 2u) to Rational(2, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(3, 5), - mapOf(x to 1u) to Rational(3, 5), - mapOf(x to 2u) to Rational(3, 7), - mapOf(y to 1u) to Rational(-3, 8), - mapOf(x to 1u, y to 1u) to Rational(-1, 1), - mapOf(x to 2u, y to 1u) to Rational(17, 9), - mapOf(y to 2u) to Rational(-8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 4), - mapOf(x to 2u, y to 2u) to Rational(10, 9), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 9), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(10, 9), - mapOf(y to 1u) to Rational(13, 3), - mapOf(x to 1u, y to 1u) to Rational(-12, 4), - mapOf(x to 2u, y to 1u) to Rational(3, 6), - mapOf(y to 2u) to Rational(2, 9), - mapOf(x to 1u, y to 2u) to Rational(7, 3), - mapOf(x to 2u, y to 2u) to Rational(16, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 2), - mapOf(x to 1u) to Rational(6, 2), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 5), - mapOf(y to 2u) to Rational(8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(17, 4), - ) - ) - )), - "test 4'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(3539, 700), - mapOf(x to 1u) to Rational(-307079, 6300), - mapOf(x to 2u) to Rational(451609, 15120), - mapOf(x to 3u) to Rational(35287733, 396900), - mapOf(x to 4u) to Rational(-37242617, 396900), - mapOf(x to 5u) to Rational(382747, 19845), - mapOf(x to 6u) to Rational(-2407, 3969), - mapOf(y to 1u) to Rational(-226, 175), - mapOf(x to 1u, y to 1u) to Rational(-74113, 1890), - mapOf(x to 2u, y to 1u) to Rational(250931, 1764), - mapOf(x to 3u, y to 1u) to Rational(30071473, 99225), - mapOf(x to 4u, y to 1u) to Rational(-286466, 1323), - mapOf(x to 5u, y to 1u) to Rational(-2285282, 9261), - mapOf(x to 6u, y to 1u) to Rational(17900, 441), - mapOf(y to 2u) to Rational(3817, 3150), - mapOf(x to 1u, y to 2u) to Rational(577568, 11025), - mapOf(x to 2u, y to 2u) to Rational(9073553, 99225), - mapOf(x to 3u, y to 2u) to Rational(-1415849, 79380), - mapOf(x to 4u, y to 2u) to Rational(-124715629, 277830), - mapOf(x to 5u, y to 2u) to Rational(-1328953, 1890), - mapOf(x to 6u, y to 2u) to Rational(-297148, 1323), - mapOf(y to 3u) to Rational(6043, 945), - mapOf(x to 1u, y to 3u) to Rational(160381, 6615), - mapOf(x to 2u, y to 3u) to Rational(-673249, 13230), - mapOf(x to 3u, y to 3u) to Rational(-319255, 2058), - mapOf(x to 4u, y to 3u) to Rational(-98144, 1029), - mapOf(x to 5u, y to 3u) to Rational(-320239, 5145), - mapOf(x to 6u, y to 3u) to Rational(400, 147), - mapOf(y to 4u) to Rational(163, 63), - mapOf(x to 1u, y to 4u) to Rational(-25183, 4410), - mapOf(x to 2u, y to 4u) to Rational(-21369, 1372), - mapOf(x to 3u, y to 4u) to Rational(127499, 30870), - mapOf(x to 4u, y to 4u) to Rational(86971, 12348), - mapOf(x to 5u, y to 4u) to Rational(-11129, 1470), - mapOf(x to 6u, y to 4u) to Rational(544, 147) - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-5, 3), - mapOf(x to 2u) to Rational(35, 9), - mapOf(x to 3u) to Rational(-100, 27), - mapOf(x to 4u) to Rational(100, 81), - mapOf(y to 1u) to Rational(-5, 3), - mapOf(x to 1u, y to 1u) to Rational(14, 9), - mapOf(x to 2u, y to 1u) to Rational(1874, 189), - mapOf(x to 3u, y to 1u) to Rational(-620, 63), - mapOf(x to 4u, y to 1u) to Rational(40, 63), - mapOf(y to 2u) to Rational(16, 9), - mapOf(x to 1u, y to 2u) to Rational(365, 21), - mapOf(x to 2u, y to 2u) to Rational(112, 9), - mapOf(x to 3u, y to 2u) to Rational(-464, 63), - mapOf(x to 4u, y to 2u) to Rational(1996, 441), - mapOf(y to 3u) to Rational(10, 3), - mapOf(x to 1u, y to 3u) to Rational(118, 21), - mapOf(x to 2u, y to 3u) to Rational(-272, 21), - mapOf(x to 3u, y to 3u) to Rational(-764, 49), - mapOf(x to 4u, y to 3u) to Rational(8, 7), - mapOf(y to 4u) to Rational(1, 1), - mapOf(x to 1u, y to 4u) to Rational(-10, 7), - mapOf(x to 2u, y to 4u) to Rational(-171, 49), - mapOf(x to 3u, y to 4u) to Rational(20, 7), - mapOf(x to 4u, y to 4u) to Rational(4, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(18, 5), - mapOf(x to 1u) to Rational(-17, 5), - mapOf(x to 2u) to Rational(-2, 7), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(-5, 1), - mapOf(x to 2u, y to 1u) to Rational(-9, 1), - mapOf(y to 2u) to Rational(-8, 8), - mapOf(x to 1u, y to 2u) to Rational(2, 7), - mapOf(x to 2u, y to 2u) to Rational(-13, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-4, 8), - mapOf(x to 1u) to Rational(15, 9), - mapOf(x to 2u) to Rational(-10, 9), - mapOf(y to 1u) to Rational(5, 3), - mapOf(x to 1u, y to 1u) to Rational(4, 1), - mapOf(x to 2u, y to 1u) to Rational(-2, 7), - mapOf(y to 2u) to Rational(2, 2), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(-18, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(3539, 700), - mapOf(x to 1u) to Rational(-307079, 6300), - mapOf(x to 2u) to Rational(451609, 15120), - mapOf(x to 3u) to Rational(35287733, 396900), - mapOf(x to 4u) to Rational(-37242617, 396900), - mapOf(x to 5u) to Rational(382747, 19845), - mapOf(x to 6u) to Rational(-2407, 3969), - mapOf(y to 1u) to Rational(-226, 175), - mapOf(x to 1u, y to 1u) to Rational(-74113, 1890), - mapOf(x to 2u, y to 1u) to Rational(250931, 1764), - mapOf(x to 3u, y to 1u) to Rational(30071473, 99225), - mapOf(x to 4u, y to 1u) to Rational(-286466, 1323), - mapOf(x to 5u, y to 1u) to Rational(-2285282, 9261), - mapOf(x to 6u, y to 1u) to Rational(17900, 441), - mapOf(y to 2u) to Rational(3817, 3150), - mapOf(x to 1u, y to 2u) to Rational(577568, 11025), - mapOf(x to 2u, y to 2u) to Rational(9073553, 99225), - mapOf(x to 3u, y to 2u) to Rational(-1415849, 79380), - mapOf(x to 4u, y to 2u) to Rational(-124715629, 277830), - mapOf(x to 5u, y to 2u) to Rational(-1328953, 1890), - mapOf(x to 6u, y to 2u) to Rational(-297148, 1323), - mapOf(y to 3u) to Rational(6043, 945), - mapOf(x to 1u, y to 3u) to Rational(160381, 6615), - mapOf(x to 2u, y to 3u) to Rational(-673249, 13230), - mapOf(x to 3u, y to 3u) to Rational(-319255, 2058), - mapOf(x to 4u, y to 3u) to Rational(-98144, 1029), - mapOf(x to 5u, y to 3u) to Rational(-320239, 5145), - mapOf(x to 6u, y to 3u) to Rational(400, 147), - mapOf(y to 4u) to Rational(163, 63), - mapOf(x to 1u, y to 4u) to Rational(-25183, 4410), - mapOf(x to 2u, y to 4u) to Rational(-21369, 1372), - mapOf(x to 3u, y to 4u) to Rational(127499, 30870), - mapOf(x to 4u, y to 4u) to Rational(86971, 12348), - mapOf(x to 5u, y to 4u) to Rational(-11129, 1470), - mapOf(x to 6u, y to 4u) to Rational(544, 147) - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-5, 3), - mapOf(x to 2u) to Rational(35, 9), - mapOf(x to 3u) to Rational(-100, 27), - mapOf(x to 4u) to Rational(100, 81), - mapOf(y to 1u) to Rational(-5, 3), - mapOf(x to 1u, y to 1u) to Rational(14, 9), - mapOf(x to 2u, y to 1u) to Rational(1874, 189), - mapOf(x to 3u, y to 1u) to Rational(-620, 63), - mapOf(x to 4u, y to 1u) to Rational(40, 63), - mapOf(y to 2u) to Rational(16, 9), - mapOf(x to 1u, y to 2u) to Rational(365, 21), - mapOf(x to 2u, y to 2u) to Rational(112, 9), - mapOf(x to 3u, y to 2u) to Rational(-464, 63), - mapOf(x to 4u, y to 2u) to Rational(1996, 441), - mapOf(y to 3u) to Rational(10, 3), - mapOf(x to 1u, y to 3u) to Rational(118, 21), - mapOf(x to 2u, y to 3u) to Rational(-272, 21), - mapOf(x to 3u, y to 3u) to Rational(-764, 49), - mapOf(x to 4u, y to 3u) to Rational(8, 7), - mapOf(y to 4u) to Rational(1, 1), - mapOf(x to 1u, y to 4u) to Rational(-10, 7), - mapOf(x to 2u, y to 4u) to Rational(-171, 49), - mapOf(x to 3u, y to 4u) to Rational(20, 7), - mapOf(x to 4u, y to 4u) to Rational(4, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(18, 5), - mapOf(x to 1u) to Rational(-17, 5), - mapOf(x to 2u) to Rational(-2, 7), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(-5, 1), - mapOf(x to 2u, y to 1u) to Rational(-9, 1), - mapOf(y to 2u) to Rational(-8, 8), - mapOf(x to 1u, y to 2u) to Rational(2, 7), - mapOf(x to 2u, y to 2u) to Rational(-13, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-4, 8), - mapOf(x to 1u) to Rational(15, 9), - mapOf(x to 2u) to Rational(-10, 9), - mapOf(y to 1u) to Rational(5, 3), - mapOf(x to 1u, y to 1u) to Rational(4, 1), - mapOf(x to 2u, y to 1u) to Rational(-2, 7), - mapOf(y to 2u) to Rational(2, 2), - mapOf(x to 1u, y to 2u) to Rational(-5, 7), - mapOf(x to 2u, y to 2u) to Rational(-18, 9), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 9), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(10, 9), - mapOf(y to 1u) to Rational(13, 3), - mapOf(x to 1u, y to 1u) to Rational(-12, 4), - mapOf(x to 2u, y to 1u) to Rational(3, 6), - mapOf(y to 2u) to Rational(2, 9), - mapOf(x to 1u, y to 2u) to Rational(7, 3), - mapOf(x to 2u, y to 2u) to Rational(16, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 2), - mapOf(x to 1u) to Rational(6, 2), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 5), - mapOf(y to 2u) to Rational(8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(17, 4), - ) - ) - )), - "test 5'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(0, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ), - LabeledPolynomialAsIs(mapOf() to Rational(0, 1), - mapOf() to Rational(0, 1) - ) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(15, 7), - mapOf(x to 1u) to Rational(1, 5), - mapOf(x to 2u) to Rational(-7, 4), - mapOf(y to 1u) to Rational(-1, 9), - mapOf(x to 1u, y to 1u) to Rational(-2, 7), - mapOf(x to 2u, y to 1u) to Rational(17, 3), - mapOf(y to 2u) to Rational(2, 6), - mapOf(x to 1u, y to 2u) to Rational(-17, 6), - mapOf(x to 2u, y to 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 9), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(10, 9), - mapOf(y to 1u) to Rational(13, 3), - mapOf(x to 1u, y to 1u) to Rational(-12, 4), - mapOf(x to 2u, y to 1u) to Rational(3, 6), - mapOf(y to 2u) to Rational(2, 9), - mapOf(x to 1u, y to 2u) to Rational(7, 3), - mapOf(x to 2u, y to 2u) to Rational(16, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 2), - mapOf(x to 1u) to Rational(6, 2), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 5), - mapOf(y to 2u) to Rational(8, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(17, 4), - ) - ) - )), - "test 6'" - ) - } - @Test - fun test_RationalFunction_substitute_Double_Map() { - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs(emptyMap() to 0.0), - LabeledPolynomialAsIs(emptyMap() to 1.0), - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 1.0, - mapOf(x to 1u) to -2.0, - mapOf(x to 2u) to 1.0, - ), - LabeledPolynomialAsIs( - mapOf() to 1.0, - ) - ).substitute(mapOf( - x to 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf()), - 0.001, - "test 2" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - iota to 0.9211194782050933 - )), - 0.001, - "test 2'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 151.1502229133916, - mapOf(y to 1u) to -262.3790170577034, - mapOf(y to 2u) to 102.5097937392923, - ), - LabeledPolynomialAsIs( - mapOf() to -367.9969733169944, - mapOf(y to 1u) to 112.4911133334554, - mapOf(y to 2u) to -469.755906895345, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - x to -8.11707689492641, - )), - 0.001, - "test 3" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 151.1502229133916, - mapOf(y to 1u) to -262.3790170577034, - mapOf(y to 2u) to 102.5097937392923, - ), - LabeledPolynomialAsIs( - mapOf() to -367.9969733169944, - mapOf(y to 1u) to 112.4911133334554, - mapOf(y to 2u) to -469.755906895345, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - x to -8.11707689492641, - iota to 0.9211194782050933 - )), - 0.001, - "test 3'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 14.24074356896978, - mapOf(x to 1u) to -17.71987055153461, - mapOf(x to 2u) to -2.288056483312383, - ), - LabeledPolynomialAsIs( - mapOf() to 7.480604285873397, - mapOf(x to 1u) to -8.43478016688617, - mapOf(x to 2u) to -9.88934943900592, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - y to 0.795265651276015, - )), - 0.001, - "test 4" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 14.24074356896978, - mapOf(x to 1u) to -17.71987055153461, - mapOf(x to 2u) to -2.288056483312383, - ), - LabeledPolynomialAsIs( - mapOf() to 7.480604285873397, - mapOf(x to 1u) to -8.43478016688617, - mapOf(x to 2u) to -9.88934943900592, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - y to 0.795265651276015, - iota to 0.9211194782050933 - )), - 0.001, - "test 4'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 7.321261307532708, - ), - LabeledPolynomialAsIs( - mapOf() to -575.6325831127576, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - x to -8.11707689492641, - y to 0.795265651276015, - )), - 0.001, - "test 5" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 7.321261307532708, - ), - LabeledPolynomialAsIs( - mapOf() to -575.6325831127576, - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to 6.593754860231304, - mapOf(x to 1u) to -7.853302571550634, - mapOf(x to 2u) to 1.2265042281530025, - mapOf(y to 1u) to 3.762648877294904, - mapOf(x to 1u, y to 1u) to -8.945144619305292, - mapOf(x to 2u, y to 1u) to -5.141384718042281, - mapOf(y to 2u) to 7.359794483988782, - mapOf(x to 1u, y to 2u) to -4.3526172680518815, - mapOf(x to 2u, y to 2u) to 0.907910924854372, - ), - LabeledPolynomialAsIs( - mapOf() to 9.533292132172562, - mapOf(x to 1u) to -1.982814534018857, - mapOf(x to 2u) to -5.974248303415283, - mapOf(y to 1u) to 1.5876716499288879, - mapOf(x to 1u, y to 1u) to -7.535152566659664, - mapOf(x to 2u, y to 1u) to 0.7549300500153517, - mapOf(y to 2u) to -5.242030058021028, - mapOf(x to 1u, y to 2u) to -0.7265704289690582, - mapOf(x to 2u, y to 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - x to -8.11707689492641, - y to 0.795265651276015, - iota to 0.9211194782050933 - )), - 0.001, - "test 5'" - ) - } - @Test - fun test_RationalFunction_substitute_Constant_Map() { - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ).substitute(RationalField, mapOf( - x to Rational(1) - )), - "test 1" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(22047, 2450), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-2204953, 147000), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - x to Rational(7, 5), - y to Rational(-13, 7), - )), - "test 2" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(22047, 2450), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-2204953, 147000), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - x to Rational(7, 5), - y to Rational(-13, 7), - iota to Rational(-16, 4), - )), - "test 2'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(4191, 490), - mapOf(x to 1u) to Rational(14975, 1176), - mapOf(x to 2u) to Rational(-10429, 1176) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-775, 147), - mapOf(x to 1u) to Rational(-155, 49), - mapOf(x to 2u) to Rational(-757, 280) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - y to Rational(-13, 7), - )), - "test 3" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(4191, 490), - mapOf(x to 1u) to Rational(14975, 1176), - mapOf(x to 2u) to Rational(-10429, 1176) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-775, 147), - mapOf(x to 1u) to Rational(-155, 49), - mapOf(x to 2u) to Rational(-757, 280) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - y to Rational(-13, 7), - iota to Rational(-16, 4), - )), - "test 3'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-939, 200), - mapOf(y to 1u) to Rational(123, 50), - mapOf(y to 2u) to Rational(1059, 200) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(121, 25), - mapOf(y to 1u) to Rational(-949, 375), - mapOf(y to 2u) to Rational(-1423, 200) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - x to Rational(7, 5), - )), - "test 4" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-939, 200), - mapOf(y to 1u) to Rational(123, 50), - mapOf(y to 2u) to Rational(1059, 200) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(121, 25), - mapOf(y to 1u) to Rational(-949, 375), - mapOf(y to 2u) to Rational(-1423, 200) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - x to Rational(7, 5), - iota to Rational(-16, 4), - )), - "test 4'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf()), - "test 5" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-3, 5), - mapOf(x to 1u) to Rational(-18, 4), - mapOf(x to 2u) to Rational(9, 8), - mapOf(y to 1u) to Rational(-11, 6), - mapOf(x to 1u, y to 1u) to Rational(-16, 3), - mapOf(x to 2u, y to 1u) to Rational(12, 2), - mapOf(y to 2u) to Rational(5, 3), - mapOf(x to 1u, y to 2u) to Rational(17, 8), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(11, 1), - mapOf(x to 1u) to Rational(4, 1), - mapOf(x to 2u) to Rational(-18, 3), - mapOf(y to 1u) to Rational(12, 9), - mapOf(x to 1u, y to 1u) to Rational(14, 7), - mapOf(x to 2u, y to 1u) to Rational(-17, 5), - mapOf(y to 2u) to Rational(-4, 1), - mapOf(x to 1u, y to 2u) to Rational(-5, 5), - mapOf(x to 2u, y to 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - iota to Rational(-16, 4), - )), - "test 5'" - ) - } - @Test - fun test_RationalFunction_substitute_Polynomial_Map() { - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - )), - "test 1" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(211, 4), - mapOf(x to 2u) to Rational(88, 3), - mapOf(x to 3u) to Rational(-63, 8), - mapOf(x to 4u) to Rational(441, 16), - mapOf(y to 1u) to Rational(-671, 15), - mapOf(x to 1u, y to 1u) to Rational(-551, 21), - mapOf(x to 2u, y to 1u) to Rational(279, 25), - mapOf(x to 3u, y to 1u) to Rational(231, 20), - mapOf(y to 2u) to Rational(-1436, 1575), - mapOf(x to 1u, y to 2u) to Rational(2471, 250), - mapOf(x to 2u, y to 2u) to Rational(-4919, 100), - mapOf(y to 3u) to Rational(-1464, 125), - mapOf(x to 1u, y to 3u) to Rational(-264, 25), - mapOf(y to 4u) to Rational(576, 25), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(-9, 4), - mapOf(x to 2u) to Rational(943, 8), - mapOf(x to 3u) to Rational(117, 8), - mapOf(x to 4u) to Rational(147, 16), - mapOf(y to 1u) to Rational(289, 90), - mapOf(x to 1u, y to 1u) to Rational(-2692, 15), - mapOf(x to 2u, y to 1u) to Rational(-1629, 140), - mapOf(x to 3u, y to 1u) to Rational(77, 20), - mapOf(y to 2u) to Rational(6187, 75), - mapOf(x to 1u, y to 2u) to Rational(-2879, 175), - mapOf(x to 2u, y to 2u) to Rational(-4919, 300), - mapOf(y to 3u) to Rational(336, 25), - mapOf(x to 1u, y to 3u) to Rational(-88, 25), - mapOf(y to 4u) to Rational(192, 25), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(3, 2), - mapOf(y to 1u) to Rational(8, 5), - ), - y to LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(7, 2), - mapOf(y to 1u) to Rational(-3, 1), - ) - )), - "test 2" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1202861, 210), - mapOf(x to 1u) to Rational(-215117, 45), - mapOf(x to 2u) to Rational(10889651, 19845), - mapOf(x to 3u) to Rational(-3503956, 6615), - mapOf(x to 4u) to Rational(809066, 2205), - mapOf(x to 5u) to Rational(-9056, 735), - mapOf(x to 6u) to Rational(5396, 315), - mapOf(x to 7u) to Rational(-752, 147), - mapOf(x to 8u) to Rational(16, 49), - mapOf(y to 1u) to Rational(1738469, 1470), - mapOf(x to 1u, y to 1u) to Rational(-926238703, 52920), - mapOf(x to 2u, y to 1u) to Rational(-44113982, 6615), - mapOf(x to 3u, y to 1u) to Rational(10423519, 5292), - mapOf(x to 4u, y to 1u) to Rational(3769712, 2205), - mapOf(x to 5u, y to 1u) to Rational(8905046, 6615), - mapOf(x to 6u, y to 1u) to Rational(1186972, 6615), - mapOf(x to 7u, y to 1u) to Rational(22124, 441), - mapOf(x to 8u, y to 1u) to Rational(-1504, 147), - mapOf(y to 2u) to Rational(-54723628, 2205), - mapOf(x to 1u, y to 2u) to Rational(70109407, 1323), - mapOf(x to 2u, y to 2u) to Rational(151072591, 17640), - mapOf(x to 3u, y to 2u) to Rational(1216428107, 52920), - mapOf(x to 4u, y to 2u) to Rational(2587873193, 317520), - mapOf(x to 5u, y to 2u) to Rational(393536369, 79380), - mapOf(x to 6u, y to 2u) to Rational(137614937, 79380), - mapOf(x to 7u, y to 2u) to Rational(566866, 1323), - mapOf(x to 8u, y to 2u) to Rational(41848, 441), - mapOf(y to 3u) to Rational(-19470406, 2205), - mapOf(x to 1u, y to 3u) to Rational(72514195, 882), - mapOf(x to 2u, y to 3u) to Rational(-78090707, 1764), - mapOf(x to 3u, y to 3u) to Rational(-1988237707, 26460), - mapOf(x to 4u, y to 3u) to Rational(-802137919, 17640), - mapOf(x to 5u, y to 3u) to Rational(-139989463, 5880), - mapOf(x to 6u, y to 3u) to Rational(-26066641, 3780), - mapOf(x to 7u, y to 3u) to Rational(-2363369, 1323), - mapOf(x to 8u, y to 3u) to Rational(-108280, 441), - mapOf(y to 4u) to Rational(14878516, 441), - mapOf(x to 1u, y to 4u) to Rational(-253416724, 2205), - mapOf(x to 2u, y to 4u) to Rational(16699157, 840), - mapOf(x to 3u, y to 4u) to Rational(-105220979, 13230), - mapOf(x to 4u, y to 4u) to Rational(208266383, 5880), - mapOf(x to 5u, y to 4u) to Rational(650135309, 26460), - mapOf(x to 6u, y to 4u) to Rational(123808663, 11760), - mapOf(x to 7u, y to 4u) to Rational(8563385, 2646), - mapOf(x to 8u, y to 4u) to Rational(19721, 49), - mapOf(y to 5u) to Rational(675645, 49), - mapOf(x to 1u, y to 5u) to Rational(-70554077, 588), - mapOf(x to 2u, y to 5u) to Rational(157884029, 980), - mapOf(x to 3u, y to 5u) to Rational(489548623, 4410), - mapOf(x to 4u, y to 5u) to Rational(148540519, 17640), - mapOf(x to 5u, y to 5u) to Rational(-5559551, 392), - mapOf(x to 6u, y to 5u) to Rational(-18335711, 1470), - mapOf(x to 7u, y to 5u) to Rational(-38437, 9), - mapOf(x to 8u, y to 5u) to Rational(-29620, 63), - mapOf(y to 6u) to Rational(-727625, 49), - mapOf(x to 1u, y to 6u) to Rational(7046685, 98), - mapOf(x to 2u, y to 6u) to Rational(-334814231, 7056), - mapOf(x to 3u, y to 6u) to Rational(-243971737, 17640), - mapOf(x to 4u, y to 6u) to Rational(-571116659, 35280), - mapOf(x to 5u, y to 6u) to Rational(567538, 315), - mapOf(x to 6u, y to 6u) to Rational(3199768, 315), - mapOf(x to 7u, y to 6u) to Rational(227744, 63), - mapOf(x to 8u, y to 6u) to Rational(23116, 63), - mapOf(y to 7u) to Rational(-27500, 7), - mapOf(x to 1u, y to 7u) to Rational(120125, 3), - mapOf(x to 2u, y to 7u) to Rational(-279200, 3), - mapOf(x to 3u, y to 7u) to Rational(-100160, 7), - mapOf(x to 4u, y to 7u) to Rational(920452, 21), - mapOf(x to 5u, y to 7u) to Rational(226481, 21), - mapOf(x to 6u, y to 7u) to Rational(-34428, 7), - mapOf(x to 7u, y to 7u) to Rational(-6232, 3), - mapOf(x to 8u, y to 7u) to Rational(-608, 3), - mapOf(y to 8u) to Rational(2500, 1), - mapOf(x to 1u, y to 8u) to Rational(-19000, 1), - mapOf(x to 2u, y to 8u) to Rational(37900, 1), - mapOf(x to 3u, y to 8u) to Rational(-1840, 1), - mapOf(x to 4u, y to 8u) to Rational(-17876, 1), - mapOf(x to 5u, y to 8u) to Rational(-1240, 1), - mapOf(x to 6u, y to 8u) to Rational(2788, 1), - mapOf(x to 7u, y to 8u) to Rational(800, 1), - mapOf(x to 8u, y to 8u) to Rational(64, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(162487, 63), - mapOf(x to 1u) to Rational(-92713, 54), - mapOf(x to 2u) to Rational(802436, 1323), - mapOf(x to 3u) to Rational(-55088, 441), - mapOf(x to 4u) to Rational(1404034, 9261), - mapOf(x to 5u) to Rational(-5804, 1029), - mapOf(x to 6u) to Rational(51556, 9261), - mapOf(x to 7u) to Rational(-752, 441), - mapOf(x to 8u) to Rational(16, 147), - mapOf(y to 1u) to Rational(296071, 441), - mapOf(x to 1u, y to 1u) to Rational(-4991281, 882), - mapOf(x to 2u, y to 1u) to Rational(-18702811, 9261), - mapOf(x to 3u, y to 1u) to Rational(40759043, 27783), - mapOf(x to 4u, y to 1u) to Rational(19768501, 27783), - mapOf(x to 5u, y to 1u) to Rational(14307337, 27783), - mapOf(x to 6u, y to 1u) to Rational(1655684, 27783), - mapOf(x to 7u, y to 1u) to Rational(22124, 1323), - mapOf(x to 8u, y to 1u) to Rational(-1504, 441), - mapOf(y to 2u) to Rational(-27667474, 3087), - mapOf(x to 1u, y to 2u) to Rational(265605901, 12348), - mapOf(x to 2u, y to 2u) to Rational(160360775, 98784), - mapOf(x to 3u, y to 2u) to Rational(1169992093, 148176), - mapOf(x to 4u, y to 2u) to Rational(3978014077, 1333584), - mapOf(x to 5u, y to 2u) to Rational(567058123, 333396), - mapOf(x to 6u, y to 2u) to Rational(205132579, 333396), - mapOf(x to 7u, y to 2u) to Rational(566866, 3969), - mapOf(x to 8u, y to 2u) to Rational(41848, 1323), - mapOf(y to 3u) to Rational(-2228822, 1029), - mapOf(x to 1u, y to 3u) to Rational(80179390, 3087), - mapOf(x to 2u, y to 3u) to Rational(-1378630487, 74088), - mapOf(x to 3u, y to 3u) to Rational(-3385811693, 111132), - mapOf(x to 4u, y to 3u) to Rational(-820686977, 49392), - mapOf(x to 5u, y to 3u) to Rational(-89101027, 10584), - mapOf(x to 6u, y to 3u) to Rational(-37847387, 15876), - mapOf(x to 7u, y to 3u) to Rational(-2363369, 3969), - mapOf(x to 8u, y to 3u) to Rational(-108280, 1323), - mapOf(y to 4u) to Rational(12619982, 1029), - mapOf(x to 1u, y to 4u) to Rational(-277723177, 6174), - mapOf(x to 2u, y to 4u) to Rational(649414169, 49392), - mapOf(x to 3u, y to 4u) to Rational(14457595, 63504), - mapOf(x to 4u, y to 4u) to Rational(139270339, 10584), - mapOf(x to 5u, y to 4u) to Rational(140367961, 15876), - mapOf(x to 6u, y to 4u) to Rational(25467083, 7056), - mapOf(x to 7u, y to 4u) to Rational(8563385, 7938), - mapOf(x to 8u, y to 4u) to Rational(19721, 147), - mapOf(y to 5u) to Rational(643850, 147), - mapOf(x to 1u, y to 5u) to Rational(-11818025, 294), - mapOf(x to 2u, y to 5u) to Rational(33963203, 588), - mapOf(x to 3u, y to 5u) to Rational(207216235, 5292), - mapOf(x to 4u, y to 5u) to Rational(2861021, 1512), - mapOf(x to 5u, y to 5u) to Rational(-6302335, 1176), - mapOf(x to 6u, y to 5u) to Rational(-3738587, 882), - mapOf(x to 7u, y to 5u) to Rational(-38437, 27), - mapOf(x to 8u, y to 5u) to Rational(-29620, 189), - mapOf(y to 6u) to Rational(-248725, 49), - mapOf(x to 1u, y to 6u) to Rational(2478535, 98), - mapOf(x to 2u, y to 6u) to Rational(-399721367, 21168), - mapOf(x to 3u, y to 6u) to Rational(-54309317, 10584), - mapOf(x to 4u, y to 6u) to Rational(-95398327, 21168), - mapOf(x to 5u, y to 6u) to Rational(173750, 189), - mapOf(x to 6u, y to 6u) to Rational(92216, 27), - mapOf(x to 7u, y to 6u) to Rational(227744, 189), - mapOf(x to 8u, y to 6u) to Rational(23116, 189), - mapOf(y to 7u) to Rational(-27500, 21), - mapOf(x to 1u, y to 7u) to Rational(120125, 9), - mapOf(x to 2u, y to 7u) to Rational(-279200, 9), - mapOf(x to 3u, y to 7u) to Rational(-100160, 21), - mapOf(x to 4u, y to 7u) to Rational(920452, 63), - mapOf(x to 5u, y to 7u) to Rational(226481, 63), - mapOf(x to 6u, y to 7u) to Rational(-11476, 7), - mapOf(x to 7u, y to 7u) to Rational(-6232, 9), - mapOf(x to 8u, y to 7u) to Rational(-608, 9), - mapOf(y to 8u) to Rational(2500, 3), - mapOf(x to 1u, y to 8u) to Rational(-19000, 3), - mapOf(x to 2u, y to 8u) to Rational(37900, 3), - mapOf(x to 3u, y to 8u) to Rational(-1840, 3), - mapOf(x to 4u, y to 8u) to Rational(-17876, 3), - mapOf(x to 5u, y to 8u) to Rational(-1240, 3), - mapOf(x to 6u, y to 8u) to Rational(2788, 3), - mapOf(x to 7u, y to 8u) to Rational(800, 3), - mapOf(x to 8u, y to 8u) to Rational(64, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(18, 1), - mapOf(x to 1u) to Rational(16, 3), - mapOf(x to 2u) to Rational(12, 6), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 4), - mapOf(x to 2u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(-10, 1), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - y to LabeledPolynomialAsIs( - mapOf() to Rational(8, 2), - mapOf(x to 1u) to Rational(-15, 5), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 7), - mapOf(x to 1u, y to 1u) to Rational(-16, 6), - mapOf(x to 2u, y to 1u) to Rational(-13, 3), - mapOf(y to 2u) to Rational(-5, 1), - mapOf(x to 1u, y to 2u) to Rational(17, 1), - mapOf(x to 2u, y to 2u) to Rational(8, 2), - ), - )), - "test 3" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1202861, 210), - mapOf(x to 1u) to Rational(-215117, 45), - mapOf(x to 2u) to Rational(10889651, 19845), - mapOf(x to 3u) to Rational(-3503956, 6615), - mapOf(x to 4u) to Rational(809066, 2205), - mapOf(x to 5u) to Rational(-9056, 735), - mapOf(x to 6u) to Rational(5396, 315), - mapOf(x to 7u) to Rational(-752, 147), - mapOf(x to 8u) to Rational(16, 49), - mapOf(y to 1u) to Rational(1738469, 1470), - mapOf(x to 1u, y to 1u) to Rational(-926238703, 52920), - mapOf(x to 2u, y to 1u) to Rational(-44113982, 6615), - mapOf(x to 3u, y to 1u) to Rational(10423519, 5292), - mapOf(x to 4u, y to 1u) to Rational(3769712, 2205), - mapOf(x to 5u, y to 1u) to Rational(8905046, 6615), - mapOf(x to 6u, y to 1u) to Rational(1186972, 6615), - mapOf(x to 7u, y to 1u) to Rational(22124, 441), - mapOf(x to 8u, y to 1u) to Rational(-1504, 147), - mapOf(y to 2u) to Rational(-54723628, 2205), - mapOf(x to 1u, y to 2u) to Rational(70109407, 1323), - mapOf(x to 2u, y to 2u) to Rational(151072591, 17640), - mapOf(x to 3u, y to 2u) to Rational(1216428107, 52920), - mapOf(x to 4u, y to 2u) to Rational(2587873193, 317520), - mapOf(x to 5u, y to 2u) to Rational(393536369, 79380), - mapOf(x to 6u, y to 2u) to Rational(137614937, 79380), - mapOf(x to 7u, y to 2u) to Rational(566866, 1323), - mapOf(x to 8u, y to 2u) to Rational(41848, 441), - mapOf(y to 3u) to Rational(-19470406, 2205), - mapOf(x to 1u, y to 3u) to Rational(72514195, 882), - mapOf(x to 2u, y to 3u) to Rational(-78090707, 1764), - mapOf(x to 3u, y to 3u) to Rational(-1988237707, 26460), - mapOf(x to 4u, y to 3u) to Rational(-802137919, 17640), - mapOf(x to 5u, y to 3u) to Rational(-139989463, 5880), - mapOf(x to 6u, y to 3u) to Rational(-26066641, 3780), - mapOf(x to 7u, y to 3u) to Rational(-2363369, 1323), - mapOf(x to 8u, y to 3u) to Rational(-108280, 441), - mapOf(y to 4u) to Rational(14878516, 441), - mapOf(x to 1u, y to 4u) to Rational(-253416724, 2205), - mapOf(x to 2u, y to 4u) to Rational(16699157, 840), - mapOf(x to 3u, y to 4u) to Rational(-105220979, 13230), - mapOf(x to 4u, y to 4u) to Rational(208266383, 5880), - mapOf(x to 5u, y to 4u) to Rational(650135309, 26460), - mapOf(x to 6u, y to 4u) to Rational(123808663, 11760), - mapOf(x to 7u, y to 4u) to Rational(8563385, 2646), - mapOf(x to 8u, y to 4u) to Rational(19721, 49), - mapOf(y to 5u) to Rational(675645, 49), - mapOf(x to 1u, y to 5u) to Rational(-70554077, 588), - mapOf(x to 2u, y to 5u) to Rational(157884029, 980), - mapOf(x to 3u, y to 5u) to Rational(489548623, 4410), - mapOf(x to 4u, y to 5u) to Rational(148540519, 17640), - mapOf(x to 5u, y to 5u) to Rational(-5559551, 392), - mapOf(x to 6u, y to 5u) to Rational(-18335711, 1470), - mapOf(x to 7u, y to 5u) to Rational(-38437, 9), - mapOf(x to 8u, y to 5u) to Rational(-29620, 63), - mapOf(y to 6u) to Rational(-727625, 49), - mapOf(x to 1u, y to 6u) to Rational(7046685, 98), - mapOf(x to 2u, y to 6u) to Rational(-334814231, 7056), - mapOf(x to 3u, y to 6u) to Rational(-243971737, 17640), - mapOf(x to 4u, y to 6u) to Rational(-571116659, 35280), - mapOf(x to 5u, y to 6u) to Rational(567538, 315), - mapOf(x to 6u, y to 6u) to Rational(3199768, 315), - mapOf(x to 7u, y to 6u) to Rational(227744, 63), - mapOf(x to 8u, y to 6u) to Rational(23116, 63), - mapOf(y to 7u) to Rational(-27500, 7), - mapOf(x to 1u, y to 7u) to Rational(120125, 3), - mapOf(x to 2u, y to 7u) to Rational(-279200, 3), - mapOf(x to 3u, y to 7u) to Rational(-100160, 7), - mapOf(x to 4u, y to 7u) to Rational(920452, 21), - mapOf(x to 5u, y to 7u) to Rational(226481, 21), - mapOf(x to 6u, y to 7u) to Rational(-34428, 7), - mapOf(x to 7u, y to 7u) to Rational(-6232, 3), - mapOf(x to 8u, y to 7u) to Rational(-608, 3), - mapOf(y to 8u) to Rational(2500, 1), - mapOf(x to 1u, y to 8u) to Rational(-19000, 1), - mapOf(x to 2u, y to 8u) to Rational(37900, 1), - mapOf(x to 3u, y to 8u) to Rational(-1840, 1), - mapOf(x to 4u, y to 8u) to Rational(-17876, 1), - mapOf(x to 5u, y to 8u) to Rational(-1240, 1), - mapOf(x to 6u, y to 8u) to Rational(2788, 1), - mapOf(x to 7u, y to 8u) to Rational(800, 1), - mapOf(x to 8u, y to 8u) to Rational(64, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(162487, 63), - mapOf(x to 1u) to Rational(-92713, 54), - mapOf(x to 2u) to Rational(802436, 1323), - mapOf(x to 3u) to Rational(-55088, 441), - mapOf(x to 4u) to Rational(1404034, 9261), - mapOf(x to 5u) to Rational(-5804, 1029), - mapOf(x to 6u) to Rational(51556, 9261), - mapOf(x to 7u) to Rational(-752, 441), - mapOf(x to 8u) to Rational(16, 147), - mapOf(y to 1u) to Rational(296071, 441), - mapOf(x to 1u, y to 1u) to Rational(-4991281, 882), - mapOf(x to 2u, y to 1u) to Rational(-18702811, 9261), - mapOf(x to 3u, y to 1u) to Rational(40759043, 27783), - mapOf(x to 4u, y to 1u) to Rational(19768501, 27783), - mapOf(x to 5u, y to 1u) to Rational(14307337, 27783), - mapOf(x to 6u, y to 1u) to Rational(1655684, 27783), - mapOf(x to 7u, y to 1u) to Rational(22124, 1323), - mapOf(x to 8u, y to 1u) to Rational(-1504, 441), - mapOf(y to 2u) to Rational(-27667474, 3087), - mapOf(x to 1u, y to 2u) to Rational(265605901, 12348), - mapOf(x to 2u, y to 2u) to Rational(160360775, 98784), - mapOf(x to 3u, y to 2u) to Rational(1169992093, 148176), - mapOf(x to 4u, y to 2u) to Rational(3978014077, 1333584), - mapOf(x to 5u, y to 2u) to Rational(567058123, 333396), - mapOf(x to 6u, y to 2u) to Rational(205132579, 333396), - mapOf(x to 7u, y to 2u) to Rational(566866, 3969), - mapOf(x to 8u, y to 2u) to Rational(41848, 1323), - mapOf(y to 3u) to Rational(-2228822, 1029), - mapOf(x to 1u, y to 3u) to Rational(80179390, 3087), - mapOf(x to 2u, y to 3u) to Rational(-1378630487, 74088), - mapOf(x to 3u, y to 3u) to Rational(-3385811693, 111132), - mapOf(x to 4u, y to 3u) to Rational(-820686977, 49392), - mapOf(x to 5u, y to 3u) to Rational(-89101027, 10584), - mapOf(x to 6u, y to 3u) to Rational(-37847387, 15876), - mapOf(x to 7u, y to 3u) to Rational(-2363369, 3969), - mapOf(x to 8u, y to 3u) to Rational(-108280, 1323), - mapOf(y to 4u) to Rational(12619982, 1029), - mapOf(x to 1u, y to 4u) to Rational(-277723177, 6174), - mapOf(x to 2u, y to 4u) to Rational(649414169, 49392), - mapOf(x to 3u, y to 4u) to Rational(14457595, 63504), - mapOf(x to 4u, y to 4u) to Rational(139270339, 10584), - mapOf(x to 5u, y to 4u) to Rational(140367961, 15876), - mapOf(x to 6u, y to 4u) to Rational(25467083, 7056), - mapOf(x to 7u, y to 4u) to Rational(8563385, 7938), - mapOf(x to 8u, y to 4u) to Rational(19721, 147), - mapOf(y to 5u) to Rational(643850, 147), - mapOf(x to 1u, y to 5u) to Rational(-11818025, 294), - mapOf(x to 2u, y to 5u) to Rational(33963203, 588), - mapOf(x to 3u, y to 5u) to Rational(207216235, 5292), - mapOf(x to 4u, y to 5u) to Rational(2861021, 1512), - mapOf(x to 5u, y to 5u) to Rational(-6302335, 1176), - mapOf(x to 6u, y to 5u) to Rational(-3738587, 882), - mapOf(x to 7u, y to 5u) to Rational(-38437, 27), - mapOf(x to 8u, y to 5u) to Rational(-29620, 189), - mapOf(y to 6u) to Rational(-248725, 49), - mapOf(x to 1u, y to 6u) to Rational(2478535, 98), - mapOf(x to 2u, y to 6u) to Rational(-399721367, 21168), - mapOf(x to 3u, y to 6u) to Rational(-54309317, 10584), - mapOf(x to 4u, y to 6u) to Rational(-95398327, 21168), - mapOf(x to 5u, y to 6u) to Rational(173750, 189), - mapOf(x to 6u, y to 6u) to Rational(92216, 27), - mapOf(x to 7u, y to 6u) to Rational(227744, 189), - mapOf(x to 8u, y to 6u) to Rational(23116, 189), - mapOf(y to 7u) to Rational(-27500, 21), - mapOf(x to 1u, y to 7u) to Rational(120125, 9), - mapOf(x to 2u, y to 7u) to Rational(-279200, 9), - mapOf(x to 3u, y to 7u) to Rational(-100160, 21), - mapOf(x to 4u, y to 7u) to Rational(920452, 63), - mapOf(x to 5u, y to 7u) to Rational(226481, 63), - mapOf(x to 6u, y to 7u) to Rational(-11476, 7), - mapOf(x to 7u, y to 7u) to Rational(-6232, 9), - mapOf(x to 8u, y to 7u) to Rational(-608, 9), - mapOf(y to 8u) to Rational(2500, 3), - mapOf(x to 1u, y to 8u) to Rational(-19000, 3), - mapOf(x to 2u, y to 8u) to Rational(37900, 3), - mapOf(x to 3u, y to 8u) to Rational(-1840, 3), - mapOf(x to 4u, y to 8u) to Rational(-17876, 3), - mapOf(x to 5u, y to 8u) to Rational(-1240, 3), - mapOf(x to 6u, y to 8u) to Rational(2788, 3), - mapOf(x to 7u, y to 8u) to Rational(800, 3), - mapOf(x to 8u, y to 8u) to Rational(64, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(18, 1), - mapOf(x to 1u) to Rational(16, 3), - mapOf(x to 2u) to Rational(12, 6), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 4), - mapOf(x to 2u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(-10, 1), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - y to LabeledPolynomialAsIs( - mapOf() to Rational(8, 2), - mapOf(x to 1u) to Rational(-15, 5), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 7), - mapOf(x to 1u, y to 1u) to Rational(-16, 6), - mapOf(x to 2u, y to 1u) to Rational(-13, 3), - mapOf(y to 2u) to Rational(-5, 1), - mapOf(x to 1u, y to 2u) to Rational(17, 1), - mapOf(x to 2u, y to 2u) to Rational(8, 2), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-6, 1), - mapOf(x to 1u) to Rational(-9, 8), - mapOf(x to 2u) to Rational(17, 5), - mapOf(y to 1u) to Rational(-2, 3), - mapOf(x to 1u, y to 1u) to Rational(1, 5), - mapOf(x to 2u, y to 1u) to Rational(-11, 7), - mapOf(y to 2u) to Rational(13, 6), - mapOf(x to 1u, y to 2u) to Rational(-15, 2), - mapOf(x to 2u, y to 2u) to Rational(-14, 4), - ) - )), - "test 3'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(493, 6), - mapOf(x to 1u) to Rational(-15991, 210), - mapOf(x to 2u) to Rational(2734, 63), - mapOf(x to 3u) to Rational(-8213, 245), - mapOf(x to 4u) to Rational(1843, 147), - mapOf(x to 5u) to Rational(-432, 245), - mapOf(x to 6u) to Rational(4, 49), - mapOf(y to 1u) to Rational(-66, 1), - mapOf(x to 1u, y to 1u) to Rational(-92924, 2205), - mapOf(x to 2u, y to 1u) to Rational(-257461, 2205), - mapOf(x to 3u, y to 1u) to Rational(58658, 2205), - mapOf(x to 4u, y to 1u) to Rational(-87884, 2205), - mapOf(x to 5u, y to 1u) to Rational(2726, 105), - mapOf(x to 6u, y to 1u) to Rational(-52, 21), - mapOf(y to 2u) to Rational(-17569, 147), - mapOf(x to 1u, y to 2u) to Rational(368819, 735), - mapOf(x to 2u, y to 2u) to Rational(-644626, 6615), - mapOf(x to 3u, y to 2u) to Rational(221738, 945), - mapOf(x to 4u, y to 2u) to Rational(-18022, 945), - mapOf(x to 5u, y to 2u) to Rational(-1201, 315), - mapOf(x to 6u, y to 2u) to Rational(1327, 63), - mapOf(y to 3u) to Rational(240, 7), - mapOf(x to 1u, y to 3u) to Rational(-868, 9), - mapOf(x to 2u, y to 3u) to Rational(-8936, 315), - mapOf(x to 3u, y to 3u) to Rational(-77146, 315), - mapOf(x to 4u, y to 3u) to Rational(-4072, 315), - mapOf(x to 5u, y to 3u) to Rational(-2218, 15), - mapOf(x to 6u, y to 3u) to Rational(-104, 3), - mapOf(y to 4u) to Rational(100, 3), - mapOf(x to 1u, y to 4u) to Rational(-725, 3), - mapOf(x to 2u, y to 4u) to Rational(459, 1), - mapOf(x to 3u, y to 4u) to Rational(-2071, 15), - mapOf(x to 4u, y to 4u) to Rational(2831, 15), - mapOf(x to 5u, y to 4u) to Rational(632, 5), - mapOf(x to 6u, y to 4u) to Rational(16, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1255, 9), - mapOf(x to 1u) to Rational(-24781, 126), - mapOf(x to 2u) to Rational(1195, 14), - mapOf(x to 3u) to Rational(-1931, 147), - mapOf(x to 4u) to Rational(439, 147), - mapOf(x to 5u) to Rational(-172, 343), - mapOf(x to 6u) to Rational(4, 147), - mapOf(y to 1u) to Rational(-183, 1), - mapOf(x to 1u, y to 1u) to Rational(-30988, 441), - mapOf(x to 2u, y to 1u) to Rational(-56137, 294), - mapOf(x to 3u, y to 1u) to Rational(204308, 1029), - mapOf(x to 4u, y to 1u) to Rational(-3263, 441), - mapOf(x to 5u, y to 1u) to Rational(2662, 441), - mapOf(x to 6u, y to 1u) to Rational(-52, 63), - mapOf(y to 2u) to Rational(-87119, 294), - mapOf(x to 1u, y to 2u) to Rational(1077919, 686), - mapOf(x to 2u, y to 2u) to Rational(-35209, 147), - mapOf(x to 3u, y to 2u) to Rational(15041, 147), - mapOf(x to 4u, y to 2u) to Rational(240889, 1323), - mapOf(x to 5u, y to 2u) to Rational(27778, 1323), - mapOf(x to 6u, y to 2u) to Rational(1327, 189), - mapOf(y to 3u) to Rational(1620, 7), - mapOf(x to 1u, y to 3u) to Rational(-25716, 49), - mapOf(x to 2u, y to 3u) to Rational(-32078, 49), - mapOf(x to 3u, y to 3u) to Rational(-704038, 441), - mapOf(x to 4u, y to 3u) to Rational(-30190, 63), - mapOf(x to 5u, y to 3u) to Rational(-5414, 63), - mapOf(x to 6u, y to 3u) to Rational(-104, 9), - mapOf(y to 4u) to Rational(225, 1), - mapOf(x to 1u, y to 4u) to Rational(-10560, 7), - mapOf(x to 2u, y to 4u) to Rational(44176, 21), - mapOf(x to 3u, y to 4u) to Rational(28996, 21), - mapOf(x to 4u, y to 4u) to Rational(2405, 7), - mapOf(x to 5u, y to 4u) to Rational(1240, 21), - mapOf(x to 6u, y to 4u) to Rational(16, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - y to LabeledPolynomialAsIs( - mapOf() to Rational(8, 2), - mapOf(x to 1u) to Rational(-15, 5), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 7), - mapOf(x to 1u, y to 1u) to Rational(-16, 6), - mapOf(x to 2u, y to 1u) to Rational(-13, 3), - mapOf(y to 2u) to Rational(-5, 1), - mapOf(x to 1u, y to 2u) to Rational(17, 1), - mapOf(x to 2u, y to 2u) to Rational(8, 2), - ), - )), - "test 4" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(493, 6), - mapOf(x to 1u) to Rational(-15991, 210), - mapOf(x to 2u) to Rational(2734, 63), - mapOf(x to 3u) to Rational(-8213, 245), - mapOf(x to 4u) to Rational(1843, 147), - mapOf(x to 5u) to Rational(-432, 245), - mapOf(x to 6u) to Rational(4, 49), - mapOf(y to 1u) to Rational(-66, 1), - mapOf(x to 1u, y to 1u) to Rational(-92924, 2205), - mapOf(x to 2u, y to 1u) to Rational(-257461, 2205), - mapOf(x to 3u, y to 1u) to Rational(58658, 2205), - mapOf(x to 4u, y to 1u) to Rational(-87884, 2205), - mapOf(x to 5u, y to 1u) to Rational(2726, 105), - mapOf(x to 6u, y to 1u) to Rational(-52, 21), - mapOf(y to 2u) to Rational(-17569, 147), - mapOf(x to 1u, y to 2u) to Rational(368819, 735), - mapOf(x to 2u, y to 2u) to Rational(-644626, 6615), - mapOf(x to 3u, y to 2u) to Rational(221738, 945), - mapOf(x to 4u, y to 2u) to Rational(-18022, 945), - mapOf(x to 5u, y to 2u) to Rational(-1201, 315), - mapOf(x to 6u, y to 2u) to Rational(1327, 63), - mapOf(y to 3u) to Rational(240, 7), - mapOf(x to 1u, y to 3u) to Rational(-868, 9), - mapOf(x to 2u, y to 3u) to Rational(-8936, 315), - mapOf(x to 3u, y to 3u) to Rational(-77146, 315), - mapOf(x to 4u, y to 3u) to Rational(-4072, 315), - mapOf(x to 5u, y to 3u) to Rational(-2218, 15), - mapOf(x to 6u, y to 3u) to Rational(-104, 3), - mapOf(y to 4u) to Rational(100, 3), - mapOf(x to 1u, y to 4u) to Rational(-725, 3), - mapOf(x to 2u, y to 4u) to Rational(459, 1), - mapOf(x to 3u, y to 4u) to Rational(-2071, 15), - mapOf(x to 4u, y to 4u) to Rational(2831, 15), - mapOf(x to 5u, y to 4u) to Rational(632, 5), - mapOf(x to 6u, y to 4u) to Rational(16, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1255, 9), - mapOf(x to 1u) to Rational(-24781, 126), - mapOf(x to 2u) to Rational(1195, 14), - mapOf(x to 3u) to Rational(-1931, 147), - mapOf(x to 4u) to Rational(439, 147), - mapOf(x to 5u) to Rational(-172, 343), - mapOf(x to 6u) to Rational(4, 147), - mapOf(y to 1u) to Rational(-183, 1), - mapOf(x to 1u, y to 1u) to Rational(-30988, 441), - mapOf(x to 2u, y to 1u) to Rational(-56137, 294), - mapOf(x to 3u, y to 1u) to Rational(204308, 1029), - mapOf(x to 4u, y to 1u) to Rational(-3263, 441), - mapOf(x to 5u, y to 1u) to Rational(2662, 441), - mapOf(x to 6u, y to 1u) to Rational(-52, 63), - mapOf(y to 2u) to Rational(-87119, 294), - mapOf(x to 1u, y to 2u) to Rational(1077919, 686), - mapOf(x to 2u, y to 2u) to Rational(-35209, 147), - mapOf(x to 3u, y to 2u) to Rational(15041, 147), - mapOf(x to 4u, y to 2u) to Rational(240889, 1323), - mapOf(x to 5u, y to 2u) to Rational(27778, 1323), - mapOf(x to 6u, y to 2u) to Rational(1327, 189), - mapOf(y to 3u) to Rational(1620, 7), - mapOf(x to 1u, y to 3u) to Rational(-25716, 49), - mapOf(x to 2u, y to 3u) to Rational(-32078, 49), - mapOf(x to 3u, y to 3u) to Rational(-704038, 441), - mapOf(x to 4u, y to 3u) to Rational(-30190, 63), - mapOf(x to 5u, y to 3u) to Rational(-5414, 63), - mapOf(x to 6u, y to 3u) to Rational(-104, 9), - mapOf(y to 4u) to Rational(225, 1), - mapOf(x to 1u, y to 4u) to Rational(-10560, 7), - mapOf(x to 2u, y to 4u) to Rational(44176, 21), - mapOf(x to 3u, y to 4u) to Rational(28996, 21), - mapOf(x to 4u, y to 4u) to Rational(2405, 7), - mapOf(x to 5u, y to 4u) to Rational(1240, 21), - mapOf(x to 6u, y to 4u) to Rational(16, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - y to LabeledPolynomialAsIs( - mapOf() to Rational(8, 2), - mapOf(x to 1u) to Rational(-15, 5), - mapOf(x to 2u) to Rational(2, 7), - mapOf(y to 1u) to Rational(-18, 7), - mapOf(x to 1u, y to 1u) to Rational(-16, 6), - mapOf(x to 2u, y to 1u) to Rational(-13, 3), - mapOf(y to 2u) to Rational(-5, 1), - mapOf(x to 1u, y to 2u) to Rational(17, 1), - mapOf(x to 2u, y to 2u) to Rational(8, 2), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-6, 1), - mapOf(x to 1u) to Rational(-9, 8), - mapOf(x to 2u) to Rational(17, 5), - mapOf(y to 1u) to Rational(-2, 3), - mapOf(x to 1u, y to 1u) to Rational(1, 5), - mapOf(x to 2u, y to 1u) to Rational(-11, 7), - mapOf(y to 2u) to Rational(13, 6), - mapOf(x to 1u, y to 2u) to Rational(-15, 2), - mapOf(x to 2u, y to 2u) to Rational(-14, 4), - ) - )), - "test 4'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-409, 6), - mapOf(x to 1u) to Rational(-376, 9), - mapOf(x to 2u) to Rational(-1781, 81), - mapOf(x to 3u) to Rational(-128, 27), - mapOf(x to 4u) to Rational(-8, 9), - mapOf(y to 1u) to Rational(18701, 210), - mapOf(x to 1u, y to 1u) to Rational(614183, 7560), - mapOf(x to 2u, y to 1u) to Rational(90941, 1890), - mapOf(x to 3u, y to 1u) to Rational(1802, 135), - mapOf(x to 4u, y to 1u) to Rational(112, 45), - mapOf(y to 2u) to Rational(181421, 315), - mapOf(x to 1u, y to 2u) to Rational(77813, 378), - mapOf(x to 2u, y to 2u) to Rational(598583, 7560), - mapOf(x to 3u, y to 2u) to Rational(85, 27), - mapOf(x to 4u, y to 2u) to Rational(2, 5), - mapOf(y to 3u) to Rational(130997, 315), - mapOf(x to 1u, y to 3u) to Rational(1093, 420), - mapOf(x to 2u, y to 3u) to Rational(9551, 2520), - mapOf(x to 3u, y to 3u) to Rational(-14, 45), - mapOf(x to 4u, y to 3u) to Rational(22, 45), - mapOf(y to 4u) to Rational(-2801, 9), - mapOf(x to 1u, y to 4u) to Rational(4033, 90), - mapOf(x to 2u, y to 4u) to Rational(6429, 80), - mapOf(x to 3u, y to 4u) to Rational(2851, 90), - mapOf(x to 4u, y to 4u) to Rational(293, 45), - mapOf(y to 5u) to Rational(-220, 1), - mapOf(x to 1u, y to 5u) to Rational(127, 1), - mapOf(x to 2u, y to 5u) to Rational(202, 5), - mapOf(x to 3u, y to 5u) to Rational(-63, 5), - mapOf(x to 4u, y to 5u) to Rational(-12, 5), - mapOf(y to 6u) to Rational(100, 1), - mapOf(x to 1u, y to 6u) to Rational(-80, 1), - mapOf(x to 2u, y to 6u) to Rational(-24, 1), - mapOf(x to 3u, y to 6u) to Rational(16, 1), - mapOf(x to 4u, y to 6u) to Rational(4, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5407, 9), - mapOf(x to 1u) to Rational(9568, 27), - mapOf(x to 2u) to Rational(4996, 27), - mapOf(x to 3u) to Rational(352, 9), - mapOf(x to 4u) to Rational(22, 3), - mapOf(y to 1u) to Rational(104411, 126), - mapOf(x to 1u, y to 1u) to Rational(6001, 126), - mapOf(x to 2u, y to 1u) to Rational(-796, 21), - mapOf(x to 3u, y to 1u) to Rational(-5389, 126), - mapOf(x to 4u, y to 1u) to Rational(-166, 21), - mapOf(y to 2u) to Rational(-35327, 126), - mapOf(x to 1u, y to 2u) to Rational(53, 252), - mapOf(x to 2u, y to 2u) to Rational(849197, 6048), - mapOf(x to 3u, y to 2u) to Rational(22361, 252), - mapOf(x to 4u, y to 2u) to Rational(773, 42), - mapOf(y to 3u) to Rational(-6067, 21), - mapOf(x to 1u, y to 3u) to Rational(39049, 126), - mapOf(x to 2u, y to 3u) to Rational(80303, 1008), - mapOf(x to 3u, y to 3u) to Rational(-3035, 63), - mapOf(x to 4u, y to 3u) to Rational(-209, 21), - mapOf(y to 4u) to Rational(3113, 21), - mapOf(x to 1u, y to 4u) to Rational(-22345, 126), - mapOf(x to 2u, y to 4u) to Rational(-30931, 1008), - mapOf(x to 3u, y to 4u) to Rational(5837, 126), - mapOf(x to 4u, y to 4u) to Rational(229, 21), - mapOf(y to 5u) to Rational(-2120, 21), - mapOf(x to 1u, y to 5u) to Rational(451, 7), - mapOf(x to 2u, y to 5u) to Rational(422, 21), - mapOf(x to 3u, y to 5u) to Rational(-181, 21), - mapOf(x to 4u, y to 5u) to Rational(-40, 21), - mapOf(y to 6u) to Rational(100, 3), - mapOf(x to 1u, y to 6u) to Rational(-80, 3), - mapOf(x to 2u, y to 6u) to Rational(-8, 1), - mapOf(x to 3u, y to 6u) to Rational(16, 3), - mapOf(x to 4u, y to 6u) to Rational(4, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(18, 1), - mapOf(x to 1u) to Rational(16, 3), - mapOf(x to 2u) to Rational(12, 6), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 4), - mapOf(x to 2u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(-10, 1), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - )), - "test 5" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-409, 6), - mapOf(x to 1u) to Rational(-376, 9), - mapOf(x to 2u) to Rational(-1781, 81), - mapOf(x to 3u) to Rational(-128, 27), - mapOf(x to 4u) to Rational(-8, 9), - mapOf(y to 1u) to Rational(18701, 210), - mapOf(x to 1u, y to 1u) to Rational(614183, 7560), - mapOf(x to 2u, y to 1u) to Rational(90941, 1890), - mapOf(x to 3u, y to 1u) to Rational(1802, 135), - mapOf(x to 4u, y to 1u) to Rational(112, 45), - mapOf(y to 2u) to Rational(181421, 315), - mapOf(x to 1u, y to 2u) to Rational(77813, 378), - mapOf(x to 2u, y to 2u) to Rational(598583, 7560), - mapOf(x to 3u, y to 2u) to Rational(85, 27), - mapOf(x to 4u, y to 2u) to Rational(2, 5), - mapOf(y to 3u) to Rational(130997, 315), - mapOf(x to 1u, y to 3u) to Rational(1093, 420), - mapOf(x to 2u, y to 3u) to Rational(9551, 2520), - mapOf(x to 3u, y to 3u) to Rational(-14, 45), - mapOf(x to 4u, y to 3u) to Rational(22, 45), - mapOf(y to 4u) to Rational(-2801, 9), - mapOf(x to 1u, y to 4u) to Rational(4033, 90), - mapOf(x to 2u, y to 4u) to Rational(6429, 80), - mapOf(x to 3u, y to 4u) to Rational(2851, 90), - mapOf(x to 4u, y to 4u) to Rational(293, 45), - mapOf(y to 5u) to Rational(-220, 1), - mapOf(x to 1u, y to 5u) to Rational(127, 1), - mapOf(x to 2u, y to 5u) to Rational(202, 5), - mapOf(x to 3u, y to 5u) to Rational(-63, 5), - mapOf(x to 4u, y to 5u) to Rational(-12, 5), - mapOf(y to 6u) to Rational(100, 1), - mapOf(x to 1u, y to 6u) to Rational(-80, 1), - mapOf(x to 2u, y to 6u) to Rational(-24, 1), - mapOf(x to 3u, y to 6u) to Rational(16, 1), - mapOf(x to 4u, y to 6u) to Rational(4, 1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5407, 9), - mapOf(x to 1u) to Rational(9568, 27), - mapOf(x to 2u) to Rational(4996, 27), - mapOf(x to 3u) to Rational(352, 9), - mapOf(x to 4u) to Rational(22, 3), - mapOf(y to 1u) to Rational(104411, 126), - mapOf(x to 1u, y to 1u) to Rational(6001, 126), - mapOf(x to 2u, y to 1u) to Rational(-796, 21), - mapOf(x to 3u, y to 1u) to Rational(-5389, 126), - mapOf(x to 4u, y to 1u) to Rational(-166, 21), - mapOf(y to 2u) to Rational(-35327, 126), - mapOf(x to 1u, y to 2u) to Rational(53, 252), - mapOf(x to 2u, y to 2u) to Rational(849197, 6048), - mapOf(x to 3u, y to 2u) to Rational(22361, 252), - mapOf(x to 4u, y to 2u) to Rational(773, 42), - mapOf(y to 3u) to Rational(-6067, 21), - mapOf(x to 1u, y to 3u) to Rational(39049, 126), - mapOf(x to 2u, y to 3u) to Rational(80303, 1008), - mapOf(x to 3u, y to 3u) to Rational(-3035, 63), - mapOf(x to 4u, y to 3u) to Rational(-209, 21), - mapOf(y to 4u) to Rational(3113, 21), - mapOf(x to 1u, y to 4u) to Rational(-22345, 126), - mapOf(x to 2u, y to 4u) to Rational(-30931, 1008), - mapOf(x to 3u, y to 4u) to Rational(5837, 126), - mapOf(x to 4u, y to 4u) to Rational(229, 21), - mapOf(y to 5u) to Rational(-2120, 21), - mapOf(x to 1u, y to 5u) to Rational(451, 7), - mapOf(x to 2u, y to 5u) to Rational(422, 21), - mapOf(x to 3u, y to 5u) to Rational(-181, 21), - mapOf(x to 4u, y to 5u) to Rational(-40, 21), - mapOf(y to 6u) to Rational(100, 3), - mapOf(x to 1u, y to 6u) to Rational(-80, 3), - mapOf(x to 2u, y to 6u) to Rational(-8, 1), - mapOf(x to 3u, y to 6u) to Rational(16, 3), - mapOf(x to 4u, y to 6u) to Rational(4, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - x to LabeledPolynomialAsIs( - mapOf() to Rational(18, 1), - mapOf(x to 1u) to Rational(16, 3), - mapOf(x to 2u) to Rational(12, 6), - mapOf(y to 1u) to Rational(13, 1), - mapOf(x to 1u, y to 1u) to Rational(-11, 4), - mapOf(x to 2u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(-10, 1), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-6, 1), - mapOf(x to 1u) to Rational(-9, 8), - mapOf(x to 2u) to Rational(17, 5), - mapOf(y to 1u) to Rational(-2, 3), - mapOf(x to 1u, y to 1u) to Rational(1, 5), - mapOf(x to 2u, y to 1u) to Rational(-11, 7), - mapOf(y to 2u) to Rational(13, 6), - mapOf(x to 1u, y to 2u) to Rational(-15, 2), - mapOf(x to 2u, y to 2u) to Rational(-14, 4), - ) - )), - "test 5'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 6), - mapOf(x to 1u) to Rational(1, 6), - mapOf(x to 2u) to Rational(-2, 9), - mapOf(y to 1u) to Rational(15, 1), - mapOf(x to 1u, y to 1u) to Rational(18, 7), - mapOf(x to 2u, y to 1u) to Rational(2, 5), - mapOf(y to 2u) to Rational(12, 9), - mapOf(x to 1u, y to 2u) to Rational(-3, 5), - mapOf(x to 2u, y to 2u) to Rational(4, 4), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-11, 9), - mapOf(x to 1u) to Rational(4, 9), - mapOf(x to 2u) to Rational(11, 6), - mapOf(y to 1u) to Rational(-5, 6), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(-1, 7), - mapOf(y to 2u) to Rational(9, 1), - mapOf(x to 1u, y to 2u) to Rational(6, 7), - mapOf(x to 2u, y to 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - iota to LabeledPolynomialAsIs( - mapOf() to Rational(-6, 1), - mapOf(x to 1u) to Rational(-9, 8), - mapOf(x to 2u) to Rational(17, 5), - mapOf(y to 1u) to Rational(-2, 3), - mapOf(x to 1u, y to 1u) to Rational(1, 5), - mapOf(x to 2u, y to 1u) to Rational(-11, 7), - mapOf(y to 2u) to Rational(13, 6), - mapOf(x to 1u, y to 2u) to Rational(-15, 2), - mapOf(x to 2u, y to 2u) to Rational(-14, 4), - ) - )), - "test 6'" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_RationalFunction_substitute_RationalFunction_Map() { - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(0) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ), - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(-17166109, 793800), - mapOf(x to 3u, y to 1u) to Rational(-930960143, 5556600), - mapOf(x to 2u, y to 2u) to Rational(-144665109691, 350065800), - mapOf(x to 1u, y to 3u) to Rational(-17232577, 52920), - mapOf(y to 4u) to Rational(-68141, 1323), - ), - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(-57522533, 14288400), - mapOf(x to 3u, y to 1u) to Rational(-13085162953, 300056400), - mapOf(x to 2u, y to 2u) to Rational(-92093367341, 525098700), - mapOf(x to 1u, y to 3u) to Rational(-1979342797, 6667920), - mapOf(y to 4u) to Rational(-3082727, 21168), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(11, 5), - mapOf(y to 1u) to Rational(8, 4), - ), - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1, 9), - mapOf(y to 1u) to Rational(11, 7), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-2, 7), - mapOf(y to 1u) to Rational(-4, 3), - ), - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(3, 6), - mapOf(y to 1u) to Rational(12, 8), - ) - ), - )), - "test 2" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-130778291, 76800), - mapOf(x to 1u) to Rational(-445270919, 230400), - mapOf(x to 2u) to Rational(44578444937, 14515200), - mapOf(x to 3u) to Rational(17329402153, 1555200), - mapOf(x to 4u) to Rational(89239926809, 2332800), - mapOf(x to 5u) to Rational(2808812267, 145152), - mapOf(x to 6u) to Rational(-21362661007, 725760), - mapOf(x to 7u) to Rational(-258455443, 2016), - mapOf(x to 8u) to Rational(-21454693, 96), - mapOf(y to 1u) to Rational(-1002137, 15360), - mapOf(x to 1u, y to 1u) to Rational(-1704849697, 430080), - mapOf(x to 2u, y to 1u) to Rational(-57657676789, 4838400), - mapOf(x to 3u, y to 1u) to Rational(-101331731, 89600), - mapOf(x to 4u, y to 1u) to Rational(5362280079329, 130636800), - mapOf(x to 5u, y to 1u) to Rational(4069896167053, 130636800), - mapOf(x to 6u, y to 1u) to Rational(12011514569, 544320), - mapOf(x to 7u, y to 1u) to Rational(138293195623, 725760), - mapOf(x to 8u, y to 1u) to Rational(6228779419, 48384), - mapOf(y to 2u) to Rational(-32395872823, 8064000), - mapOf(x to 1u, y to 2u) to Rational(-7398505523, 2304000), - mapOf(x to 2u, y to 2u) to Rational(95217051699521, 3048192000), - mapOf(x to 3u, y to 2u) to Rational(198026968812079, 3657830400), - mapOf(x to 4u, y to 2u) to Rational(4291645618499, 228614400), - mapOf(x to 5u, y to 2u) to Rational(-33211690942439, 914457600), - mapOf(x to 6u, y to 2u) to Rational(-637385538163153, 1371686400), - mapOf(x to 7u, y to 2u) to Rational(-138671528276273, 182891520), - mapOf(x to 8u, y to 2u) to Rational(-14566368751, 217728), - mapOf(y to 3u) to Rational(-10538718719, 2016000), - mapOf(x to 1u, y to 3u) to Rational(-1844485375199, 84672000), - mapOf(x to 2u, y to 3u) to Rational(103968665891, 12096000), - mapOf(x to 3u, y to 3u) to Rational(175402107278351, 1828915200), - mapOf(x to 4u, y to 3u) to Rational(8020699588879, 114307200), - mapOf(x to 5u, y to 3u) to Rational(3414841894991, 38102400), - mapOf(x to 6u, y to 3u) to Rational(1848405591611, 4665600), - mapOf(x to 7u, y to 3u) to Rational(39486708738989, 137168640), - mapOf(x to 8u, y to 3u) to Rational(255926289517, 9144576), - mapOf(y to 4u) to Rational(-655379564629, 105840000), - mapOf(x to 1u, y to 4u) to Rational(-208336039441, 127008000), - mapOf(x to 2u, y to 4u) to Rational(40173146771411, 1143072000), - mapOf(x to 3u, y to 4u) to Rational(150473493581239, 2667168000), - mapOf(x to 4u, y to 4u) to Rational(38833783990483, 1143072000), - mapOf(x to 5u, y to 4u) to Rational(-1963676248203053, 4800902400), - mapOf(x to 6u, y to 4u) to Rational(-2598759412825747, 3200601600), - mapOf(x to 7u, y to 4u) to Rational(-192895352019667, 1280240640), - mapOf(x to 8u, y to 4u) to Rational(3737382679, 6858432), - mapOf(y to 5u) to Rational(-16959378721, 1890000), - mapOf(x to 1u, y to 5u) to Rational(-1864802244743, 79380000), - mapOf(x to 2u, y to 5u) to Rational(13449261536489, 666792000), - mapOf(x to 3u, y to 5u) to Rational(215272234137329, 2667168000), - mapOf(x to 4u, y to 5u) to Rational(6040691379277, 83349000), - mapOf(x to 5u, y to 5u) to Rational(153687143525887, 800150400), - mapOf(x to 6u, y to 5u) to Rational(475602854903563, 2400451200), - mapOf(x to 7u, y to 5u) to Rational(27315599358749, 640120320), - mapOf(x to 8u, y to 5u) to Rational(-2630413357, 10668672), - mapOf(y to 6u) to Rational(-6654999511, 2646000), - mapOf(x to 1u, y to 6u) to Rational(-67885252327, 15876000), - mapOf(x to 2u, y to 6u) to Rational(5786776220983, 2667168000), - mapOf(x to 3u, y to 6u) to Rational(60615922629083, 1143072000), - mapOf(x to 4u, y to 6u) to Rational(-34703539637627407, 672126336000), - mapOf(x to 5u, y to 6u) to Rational(-744694192134101, 2240421120), - mapOf(x to 6u, y to 6u) to Rational(-1782470617231, 14817600), - mapOf(x to 7u, y to 6u) to Rational(59123208433, 8890560), - mapOf(x to 8u, y to 6u) to Rational(-141653, 5292), - mapOf(y to 7u) to Rational(-338051969, 441000), - mapOf(x to 1u, y to 7u) to Rational(468850013, 1764000), - mapOf(x to 2u, y to 7u) to Rational(2102343426101, 222264000), - mapOf(x to 3u, y to 7u) to Rational(7836130602007, 1333584000), - mapOf(x to 4u, y to 7u) to Rational(16239111865997, 746807040), - mapOf(x to 5u, y to 7u) to Rational(3824649185383, 88905600), - mapOf(x to 6u, y to 7u) to Rational(56058614459, 3457440), - mapOf(x to 7u, y to 7u) to Rational(-396766339, 493920), - mapOf(x to 8u, y to 7u) to Rational(-165147, 2744), - mapOf(y to 8u) to Rational(-3088619, 58800), - mapOf(x to 1u, y to 8u) to Rational(155343347, 88200), - mapOf(x to 2u, y to 8u) to Rational(100098736469, 7408800), - mapOf(x to 3u, y to 8u) to Rational(109725511381, 7408800), - mapOf(x to 4u, y to 8u) to Rational(-2431199641013, 59270400), - mapOf(x to 5u, y to 8u) to Rational(-102872383249, 3457440), - mapOf(x to 6u, y to 8u) to Rational(1449461309, 576240), - mapOf(x to 7u, y to 8u) to Rational(812775, 1372), - mapOf(x to 8u, y to 8u) to Rational(-16461, 343) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(164202773, 230400), - mapOf(x to 1u) to Rational(-70345303, 518400), - mapOf(x to 2u) to Rational(-4229702731, 4665600), - mapOf(x to 3u) to Rational(3262171027, 6998400), - mapOf(x to 4u) to Rational(-25423104169, 13996800), - mapOf(x to 5u) to Rational(64061869, 349920), - mapOf(x to 6u) to Rational(-1655878091, 116640), - mapOf(x to 7u) to Rational(-7991441, 648), - mapOf(x to 8u) to Rational(-502591, 18), - mapOf(y to 1u) to Rational(-8780429, 3840), - mapOf(x to 1u, y to 1u) to Rational(434272361, 115200), - mapOf(x to 2u, y to 1u) to Rational(429825727, 41472), - mapOf(x to 3u, y to 1u) to Rational(-10066790339, 6998400), - mapOf(x to 4u, y to 1u) to Rational(70022035471, 20995200), - mapOf(x to 5u, y to 1u) to Rational(-32070283493, 1399680), - mapOf(x to 6u, y to 1u) to Rational(-22051101001, 1399680), - mapOf(x to 7u, y to 1u) to Rational(-126493427, 12960), - mapOf(x to 8u, y to 1u) to Rational(3050245, 864), - mapOf(y to 2u) to Rational(-1194654631, 345600), - mapOf(x to 1u, y to 2u) to Rational(-542961452671, 31104000), - mapOf(x to 2u, y to 2u) to Rational(-234000873607, 48988800), - mapOf(x to 3u, y to 2u) to Rational(140520538087, 3628800), - mapOf(x to 4u, y to 2u) to Rational(9215088876563, 130636800), - mapOf(x to 5u, y to 2u) to Rational(27590569647253, 293932800), - mapOf(x to 6u, y to 2u) to Rational(5129057792891, 97977600), - mapOf(x to 7u, y to 2u) to Rational(-106334191, 5103), - mapOf(x to 8u, y to 2u) to Rational(-1024113911, 435456), - mapOf(y to 3u) to Rational(76223843, 6000), - mapOf(x to 1u, y to 3u) to Rational(57425857357, 2592000), - mapOf(x to 2u, y to 3u) to Rational(-2044736497573, 46656000), - mapOf(x to 3u, y to 3u) to Rational(-26155810120031, 293932800), - mapOf(x to 4u, y to 3u) to Rational(-1064419459813, 6998400), - mapOf(x to 5u, y to 3u) to Rational(-753782018389, 4082400), - mapOf(x to 6u, y to 3u) to Rational(-291973360873, 2799360), - mapOf(x to 7u, y to 3u) to Rational(-46372122599, 816480), - mapOf(x to 8u, y to 3u) to Rational(3579859657, 653184), - mapOf(y to 4u) to Rational(-13374241901, 4320000), - mapOf(x to 1u, y to 4u) to Rational(306606499811, 54432000), - mapOf(x to 2u, y to 4u) to Rational(964267124745437, 13716864000), - mapOf(x to 3u, y to 4u) to Rational(21603809415373, 182891520), - mapOf(x to 4u, y to 4u) to Rational(1097860214654027, 6858432000), - mapOf(x to 5u, y to 4u) to Rational(161615254570669, 914457600), - mapOf(x to 6u, y to 4u) to Rational(758415239461, 22861440), - mapOf(x to 7u, y to 4u) to Rational(2585568355471, 274337280), - mapOf(x to 8u, y to 4u) to Rational(-70433747863, 9144576), - mapOf(y to 5u) to Rational(-9582586217, 2520000), - mapOf(x to 1u, y to 5u) to Rational(-19093471394171, 635040000), - mapOf(x to 2u, y to 5u) to Rational(-13010261944411, 381024000), - mapOf(x to 3u, y to 5u) to Rational(-259039825301861, 4572288000), - mapOf(x to 4u, y to 5u) to Rational(-305081119071079, 2286144000), - mapOf(x to 5u, y to 5u) to Rational(-1923114383311, 19595520), - mapOf(x to 6u, y to 5u) to Rational(-14181787253231, 228614400), - mapOf(x to 7u, y to 5u) to Rational(-3959584789, 4354560), - mapOf(x to 8u, y to 5u) to Rational(4691742523, 762048), - mapOf(y to 6u) to Rational(-588323437, 180000), - mapOf(x to 1u, y to 6u) to Rational(5952234691, 52920000), - mapOf(x to 2u, y to 6u) to Rational(21001851056959, 1088640000), - mapOf(x to 3u, y to 6u) to Rational(84668034357563, 2133734400), - mapOf(x to 4u, y to 6u) to Rational(2029754605811557, 25604812800), - mapOf(x to 5u, y to 6u) to Rational(11721216739823, 426746880), - mapOf(x to 6u, y to 6u) to Rational(-8275903187003, 2133734400), - mapOf(x to 7u, y to 6u) to Rational(-4730447299, 2540160), - mapOf(x to 8u, y to 6u) to Rational(-46069985, 21168), - mapOf(y to 7u) to Rational(-75711301, 117600), - mapOf(x to 1u, y to 7u) to Rational(32430417413, 7056000), - mapOf(x to 2u, y to 7u) to Rational(677988533153, 98784000), - mapOf(x to 3u, y to 7u) to Rational(-948417645827, 71124480), - mapOf(x to 4u, y to 7u) to Rational(-11320265215207, 711244800), - mapOf(x to 5u, y to 7u) to Rational(-676438627783, 50803200), - mapOf(x to 6u, y to 7u) to Rational(-7382274253, 1975680), - mapOf(x to 7u, y to 7u) to Rational(6505733, 2205), - mapOf(x to 8u, y to 7u) to Rational(450137, 882), - mapOf(y to 8u) to Rational(-8368253, 78400), - mapOf(x to 1u, y to 8u) to Rational(6833783, 117600), - mapOf(x to 2u, y to 8u) to Rational(4528971133, 5927040), - mapOf(x to 3u, y to 8u) to Rational(146252636617, 29635200), - mapOf(x to 4u, y to 8u) to Rational(8321882556889, 1659571200), - mapOf(x to 5u, y to 8u) to Rational(-4686033011, 1975680), - mapOf(x to 6u, y to 8u) to Rational(-1074445963, 987840), - mapOf(x to 7u, y to 8u) to Rational(-142313, 588), - mapOf(x to 8u, y to 8u) to Rational(-4281, 49) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-17, 5), - mapOf(x to 1u) to Rational(2, 6), - mapOf(x to 2u) to Rational(14, 1), - mapOf(y to 1u) to Rational(-6, 6), - mapOf(x to 1u, y to 1u) to Rational(-7, 3), - mapOf(x to 2u, y to 1u) to Rational(-2, 9), - mapOf(y to 2u) to Rational(-9, 6), - mapOf(x to 1u, y to 2u) to Rational(17, 4), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5, 4), - mapOf(x to 1u) to Rational(-5, 9), - mapOf(x to 2u) to Rational(-3, 6), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(14, 5), - mapOf(x to 2u, y to 1u) to Rational(5, 2), - mapOf(y to 2u) to Rational(-18, 7), - mapOf(x to 1u, y to 2u) to Rational(-8, 2), - mapOf(x to 2u, y to 2u) to Rational(18, 9), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(14, 4), - mapOf(x to 1u) to Rational(7, 6), - mapOf(x to 2u) to Rational(7, 2), - mapOf(y to 1u) to Rational(-15, 2), - mapOf(x to 1u, y to 1u) to Rational(-13, 8), - mapOf(x to 2u, y to 1u) to Rational(-14, 3), - mapOf(y to 2u) to Rational(-7, 6), - mapOf(x to 1u, y to 2u) to Rational(7, 4), - mapOf(x to 2u, y to 2u) to Rational(9, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-7, 4), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(-16, 2), - mapOf(y to 1u) to Rational(-15, 5), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(5, 4), - mapOf(y to 2u) to Rational(-12, 5), - mapOf(x to 1u, y to 2u) to Rational(-18, 2), - mapOf(x to 2u, y to 2u) to Rational(6, 7), - ) - ), - )), - "test 3" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-130778291, 76800), - mapOf(x to 1u) to Rational(-445270919, 230400), - mapOf(x to 2u) to Rational(44578444937, 14515200), - mapOf(x to 3u) to Rational(17329402153, 1555200), - mapOf(x to 4u) to Rational(89239926809, 2332800), - mapOf(x to 5u) to Rational(2808812267, 145152), - mapOf(x to 6u) to Rational(-21362661007, 725760), - mapOf(x to 7u) to Rational(-258455443, 2016), - mapOf(x to 8u) to Rational(-21454693, 96), - mapOf(y to 1u) to Rational(-1002137, 15360), - mapOf(x to 1u, y to 1u) to Rational(-1704849697, 430080), - mapOf(x to 2u, y to 1u) to Rational(-57657676789, 4838400), - mapOf(x to 3u, y to 1u) to Rational(-101331731, 89600), - mapOf(x to 4u, y to 1u) to Rational(5362280079329, 130636800), - mapOf(x to 5u, y to 1u) to Rational(4069896167053, 130636800), - mapOf(x to 6u, y to 1u) to Rational(12011514569, 544320), - mapOf(x to 7u, y to 1u) to Rational(138293195623, 725760), - mapOf(x to 8u, y to 1u) to Rational(6228779419, 48384), - mapOf(y to 2u) to Rational(-32395872823, 8064000), - mapOf(x to 1u, y to 2u) to Rational(-7398505523, 2304000), - mapOf(x to 2u, y to 2u) to Rational(95217051699521, 3048192000), - mapOf(x to 3u, y to 2u) to Rational(198026968812079, 3657830400), - mapOf(x to 4u, y to 2u) to Rational(4291645618499, 228614400), - mapOf(x to 5u, y to 2u) to Rational(-33211690942439, 914457600), - mapOf(x to 6u, y to 2u) to Rational(-637385538163153, 1371686400), - mapOf(x to 7u, y to 2u) to Rational(-138671528276273, 182891520), - mapOf(x to 8u, y to 2u) to Rational(-14566368751, 217728), - mapOf(y to 3u) to Rational(-10538718719, 2016000), - mapOf(x to 1u, y to 3u) to Rational(-1844485375199, 84672000), - mapOf(x to 2u, y to 3u) to Rational(103968665891, 12096000), - mapOf(x to 3u, y to 3u) to Rational(175402107278351, 1828915200), - mapOf(x to 4u, y to 3u) to Rational(8020699588879, 114307200), - mapOf(x to 5u, y to 3u) to Rational(3414841894991, 38102400), - mapOf(x to 6u, y to 3u) to Rational(1848405591611, 4665600), - mapOf(x to 7u, y to 3u) to Rational(39486708738989, 137168640), - mapOf(x to 8u, y to 3u) to Rational(255926289517, 9144576), - mapOf(y to 4u) to Rational(-655379564629, 105840000), - mapOf(x to 1u, y to 4u) to Rational(-208336039441, 127008000), - mapOf(x to 2u, y to 4u) to Rational(40173146771411, 1143072000), - mapOf(x to 3u, y to 4u) to Rational(150473493581239, 2667168000), - mapOf(x to 4u, y to 4u) to Rational(38833783990483, 1143072000), - mapOf(x to 5u, y to 4u) to Rational(-1963676248203053, 4800902400), - mapOf(x to 6u, y to 4u) to Rational(-2598759412825747, 3200601600), - mapOf(x to 7u, y to 4u) to Rational(-192895352019667, 1280240640), - mapOf(x to 8u, y to 4u) to Rational(3737382679, 6858432), - mapOf(y to 5u) to Rational(-16959378721, 1890000), - mapOf(x to 1u, y to 5u) to Rational(-1864802244743, 79380000), - mapOf(x to 2u, y to 5u) to Rational(13449261536489, 666792000), - mapOf(x to 3u, y to 5u) to Rational(215272234137329, 2667168000), - mapOf(x to 4u, y to 5u) to Rational(6040691379277, 83349000), - mapOf(x to 5u, y to 5u) to Rational(153687143525887, 800150400), - mapOf(x to 6u, y to 5u) to Rational(475602854903563, 2400451200), - mapOf(x to 7u, y to 5u) to Rational(27315599358749, 640120320), - mapOf(x to 8u, y to 5u) to Rational(-2630413357, 10668672), - mapOf(y to 6u) to Rational(-6654999511, 2646000), - mapOf(x to 1u, y to 6u) to Rational(-67885252327, 15876000), - mapOf(x to 2u, y to 6u) to Rational(5786776220983, 2667168000), - mapOf(x to 3u, y to 6u) to Rational(60615922629083, 1143072000), - mapOf(x to 4u, y to 6u) to Rational(-34703539637627407, 672126336000), - mapOf(x to 5u, y to 6u) to Rational(-744694192134101, 2240421120), - mapOf(x to 6u, y to 6u) to Rational(-1782470617231, 14817600), - mapOf(x to 7u, y to 6u) to Rational(59123208433, 8890560), - mapOf(x to 8u, y to 6u) to Rational(-141653, 5292), - mapOf(y to 7u) to Rational(-338051969, 441000), - mapOf(x to 1u, y to 7u) to Rational(468850013, 1764000), - mapOf(x to 2u, y to 7u) to Rational(2102343426101, 222264000), - mapOf(x to 3u, y to 7u) to Rational(7836130602007, 1333584000), - mapOf(x to 4u, y to 7u) to Rational(16239111865997, 746807040), - mapOf(x to 5u, y to 7u) to Rational(3824649185383, 88905600), - mapOf(x to 6u, y to 7u) to Rational(56058614459, 3457440), - mapOf(x to 7u, y to 7u) to Rational(-396766339, 493920), - mapOf(x to 8u, y to 7u) to Rational(-165147, 2744), - mapOf(y to 8u) to Rational(-3088619, 58800), - mapOf(x to 1u, y to 8u) to Rational(155343347, 88200), - mapOf(x to 2u, y to 8u) to Rational(100098736469, 7408800), - mapOf(x to 3u, y to 8u) to Rational(109725511381, 7408800), - mapOf(x to 4u, y to 8u) to Rational(-2431199641013, 59270400), - mapOf(x to 5u, y to 8u) to Rational(-102872383249, 3457440), - mapOf(x to 6u, y to 8u) to Rational(1449461309, 576240), - mapOf(x to 7u, y to 8u) to Rational(812775, 1372), - mapOf(x to 8u, y to 8u) to Rational(-16461, 343) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(164202773, 230400), - mapOf(x to 1u) to Rational(-70345303, 518400), - mapOf(x to 2u) to Rational(-4229702731, 4665600), - mapOf(x to 3u) to Rational(3262171027, 6998400), - mapOf(x to 4u) to Rational(-25423104169, 13996800), - mapOf(x to 5u) to Rational(64061869, 349920), - mapOf(x to 6u) to Rational(-1655878091, 116640), - mapOf(x to 7u) to Rational(-7991441, 648), - mapOf(x to 8u) to Rational(-502591, 18), - mapOf(y to 1u) to Rational(-8780429, 3840), - mapOf(x to 1u, y to 1u) to Rational(434272361, 115200), - mapOf(x to 2u, y to 1u) to Rational(429825727, 41472), - mapOf(x to 3u, y to 1u) to Rational(-10066790339, 6998400), - mapOf(x to 4u, y to 1u) to Rational(70022035471, 20995200), - mapOf(x to 5u, y to 1u) to Rational(-32070283493, 1399680), - mapOf(x to 6u, y to 1u) to Rational(-22051101001, 1399680), - mapOf(x to 7u, y to 1u) to Rational(-126493427, 12960), - mapOf(x to 8u, y to 1u) to Rational(3050245, 864), - mapOf(y to 2u) to Rational(-1194654631, 345600), - mapOf(x to 1u, y to 2u) to Rational(-542961452671, 31104000), - mapOf(x to 2u, y to 2u) to Rational(-234000873607, 48988800), - mapOf(x to 3u, y to 2u) to Rational(140520538087, 3628800), - mapOf(x to 4u, y to 2u) to Rational(9215088876563, 130636800), - mapOf(x to 5u, y to 2u) to Rational(27590569647253, 293932800), - mapOf(x to 6u, y to 2u) to Rational(5129057792891, 97977600), - mapOf(x to 7u, y to 2u) to Rational(-106334191, 5103), - mapOf(x to 8u, y to 2u) to Rational(-1024113911, 435456), - mapOf(y to 3u) to Rational(76223843, 6000), - mapOf(x to 1u, y to 3u) to Rational(57425857357, 2592000), - mapOf(x to 2u, y to 3u) to Rational(-2044736497573, 46656000), - mapOf(x to 3u, y to 3u) to Rational(-26155810120031, 293932800), - mapOf(x to 4u, y to 3u) to Rational(-1064419459813, 6998400), - mapOf(x to 5u, y to 3u) to Rational(-753782018389, 4082400), - mapOf(x to 6u, y to 3u) to Rational(-291973360873, 2799360), - mapOf(x to 7u, y to 3u) to Rational(-46372122599, 816480), - mapOf(x to 8u, y to 3u) to Rational(3579859657, 653184), - mapOf(y to 4u) to Rational(-13374241901, 4320000), - mapOf(x to 1u, y to 4u) to Rational(306606499811, 54432000), - mapOf(x to 2u, y to 4u) to Rational(964267124745437, 13716864000), - mapOf(x to 3u, y to 4u) to Rational(21603809415373, 182891520), - mapOf(x to 4u, y to 4u) to Rational(1097860214654027, 6858432000), - mapOf(x to 5u, y to 4u) to Rational(161615254570669, 914457600), - mapOf(x to 6u, y to 4u) to Rational(758415239461, 22861440), - mapOf(x to 7u, y to 4u) to Rational(2585568355471, 274337280), - mapOf(x to 8u, y to 4u) to Rational(-70433747863, 9144576), - mapOf(y to 5u) to Rational(-9582586217, 2520000), - mapOf(x to 1u, y to 5u) to Rational(-19093471394171, 635040000), - mapOf(x to 2u, y to 5u) to Rational(-13010261944411, 381024000), - mapOf(x to 3u, y to 5u) to Rational(-259039825301861, 4572288000), - mapOf(x to 4u, y to 5u) to Rational(-305081119071079, 2286144000), - mapOf(x to 5u, y to 5u) to Rational(-1923114383311, 19595520), - mapOf(x to 6u, y to 5u) to Rational(-14181787253231, 228614400), - mapOf(x to 7u, y to 5u) to Rational(-3959584789, 4354560), - mapOf(x to 8u, y to 5u) to Rational(4691742523, 762048), - mapOf(y to 6u) to Rational(-588323437, 180000), - mapOf(x to 1u, y to 6u) to Rational(5952234691, 52920000), - mapOf(x to 2u, y to 6u) to Rational(21001851056959, 1088640000), - mapOf(x to 3u, y to 6u) to Rational(84668034357563, 2133734400), - mapOf(x to 4u, y to 6u) to Rational(2029754605811557, 25604812800), - mapOf(x to 5u, y to 6u) to Rational(11721216739823, 426746880), - mapOf(x to 6u, y to 6u) to Rational(-8275903187003, 2133734400), - mapOf(x to 7u, y to 6u) to Rational(-4730447299, 2540160), - mapOf(x to 8u, y to 6u) to Rational(-46069985, 21168), - mapOf(y to 7u) to Rational(-75711301, 117600), - mapOf(x to 1u, y to 7u) to Rational(32430417413, 7056000), - mapOf(x to 2u, y to 7u) to Rational(677988533153, 98784000), - mapOf(x to 3u, y to 7u) to Rational(-948417645827, 71124480), - mapOf(x to 4u, y to 7u) to Rational(-11320265215207, 711244800), - mapOf(x to 5u, y to 7u) to Rational(-676438627783, 50803200), - mapOf(x to 6u, y to 7u) to Rational(-7382274253, 1975680), - mapOf(x to 7u, y to 7u) to Rational(6505733, 2205), - mapOf(x to 8u, y to 7u) to Rational(450137, 882), - mapOf(y to 8u) to Rational(-8368253, 78400), - mapOf(x to 1u, y to 8u) to Rational(6833783, 117600), - mapOf(x to 2u, y to 8u) to Rational(4528971133, 5927040), - mapOf(x to 3u, y to 8u) to Rational(146252636617, 29635200), - mapOf(x to 4u, y to 8u) to Rational(8321882556889, 1659571200), - mapOf(x to 5u, y to 8u) to Rational(-4686033011, 1975680), - mapOf(x to 6u, y to 8u) to Rational(-1074445963, 987840), - mapOf(x to 7u, y to 8u) to Rational(-142313, 588), - mapOf(x to 8u, y to 8u) to Rational(-4281, 49) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-17, 5), - mapOf(x to 1u) to Rational(2, 6), - mapOf(x to 2u) to Rational(14, 1), - mapOf(y to 1u) to Rational(-6, 6), - mapOf(x to 1u, y to 1u) to Rational(-7, 3), - mapOf(x to 2u, y to 1u) to Rational(-2, 9), - mapOf(y to 2u) to Rational(-9, 6), - mapOf(x to 1u, y to 2u) to Rational(17, 4), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5, 4), - mapOf(x to 1u) to Rational(-5, 9), - mapOf(x to 2u) to Rational(-3, 6), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(14, 5), - mapOf(x to 2u, y to 1u) to Rational(5, 2), - mapOf(y to 2u) to Rational(-18, 7), - mapOf(x to 1u, y to 2u) to Rational(-8, 2), - mapOf(x to 2u, y to 2u) to Rational(18, 9), - ) - ), - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(14, 4), - mapOf(x to 1u) to Rational(7, 6), - mapOf(x to 2u) to Rational(7, 2), - mapOf(y to 1u) to Rational(-15, 2), - mapOf(x to 1u, y to 1u) to Rational(-13, 8), - mapOf(x to 2u, y to 1u) to Rational(-14, 3), - mapOf(y to 2u) to Rational(-7, 6), - mapOf(x to 1u, y to 2u) to Rational(7, 4), - mapOf(x to 2u, y to 2u) to Rational(9, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-7, 4), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(-16, 2), - mapOf(y to 1u) to Rational(-15, 5), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(5, 4), - mapOf(y to 2u) to Rational(-12, 5), - mapOf(x to 1u, y to 2u) to Rational(-18, 2), - mapOf(x to 2u, y to 2u) to Rational(6, 7), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 8), - mapOf(x to 1u) to Rational(-12, 6), - mapOf(x to 2u) to Rational(7, 6), - mapOf(y to 1u) to Rational(-10, 4), - mapOf(x to 1u, y to 1u) to Rational(-7, 6), - mapOf(x to 2u, y to 1u) to Rational(8, 9), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(5, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(10, 6), - mapOf(x to 1u) to Rational(-18, 6), - mapOf(x to 2u) to Rational(5, 1), - mapOf(y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(8, 4), - mapOf(x to 2u, y to 1u) to Rational(-4, 9), - mapOf(y to 2u) to Rational(-6, 5), - mapOf(x to 1u, y to 2u) to Rational(-15, 8), - mapOf(x to 2u, y to 2u) to Rational(-18, 5), - ) - ), - )), - "test 3'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(2303, 64), - mapOf(x to 1u) to Rational(31843, 192), - mapOf(x to 2u) to Rational(118891, 576), - mapOf(x to 3u) to Rational(94453, 168), - mapOf(x to 4u) to Rational(-179203, 1512), - mapOf(x to 5u) to Rational(-16979, 126), - mapOf(x to 6u) to Rational(-13499, 12), - mapOf(y to 1u) to Rational(-4767, 64), - mapOf(x to 1u, y to 1u) to Rational(-58689, 256), - mapOf(x to 2u, y to 1u) to Rational(-757333, 4032), - mapOf(x to 3u, y to 1u) to Rational(-4921205, 4032), - mapOf(x to 4u, y to 1u) to Rational(-2930815, 4032), - mapOf(x to 5u, y to 1u) to Rational(-398803, 1512), - mapOf(x to 6u, y to 1u) to Rational(18835, 36), - mapOf(y to 2u) to Rational(224101, 960), - mapOf(x to 1u, y to 2u) to Rational(9139699, 40320), - mapOf(x to 2u, y to 2u) to Rational(3848803, 5760), - mapOf(x to 3u, y to 2u) to Rational(93102371, 241920), - mapOf(x to 4u, y to 2u) to Rational(-65821229, 141120), - mapOf(x to 5u, y to 2u) to Rational(-15675899, 7056), - mapOf(x to 6u, y to 2u) to Rational(10459, 189), - mapOf(y to 3u) to Rational(2411, 16), - mapOf(x to 1u, y to 3u) to Rational(1294543, 10080), - mapOf(x to 2u, y to 3u) to Rational(-1740199, 1440), - mapOf(x to 3u, y to 3u) to Rational(-266994841, 282240), - mapOf(x to 4u, y to 3u) to Rational(-41261893, 211680), - mapOf(x to 5u, y to 3u) to Rational(1717357, 3528), - mapOf(x to 6u, y to 3u) to Rational(69, 14), - mapOf(y to 4u) to Rational(13231, 360), - mapOf(x to 1u, y to 4u) to Rational(4858831, 25200), - mapOf(x to 2u, y to 4u) to Rational(15565759, 75600), - mapOf(x to 3u, y to 4u) to Rational(-15583391, 35280), - mapOf(x to 4u, y to 4u) to Rational(-13345747, 11760), - mapOf(x to 5u, y to 4u) to Rational(140103, 686), - mapOf(x to 6u, y to 4u) to Rational(-765, 49) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(31409, 576), - mapOf(x to 1u) to Rational(-337099, 1728), - mapOf(x to 2u) to Rational(-211429, 1728), - mapOf(x to 3u) to Rational(-259241, 432), - mapOf(x to 4u) to Rational(-13777, 36), - mapOf(x to 5u) to Rational(-41389, 72), - mapOf(x to 6u) to Rational(-7679, 48), - mapOf(y to 1u) to Rational(-3269, 12), - mapOf(x to 1u, y to 1u) to Rational(629569, 864), - mapOf(x to 2u, y to 1u) to Rational(53867, 324), - mapOf(x to 3u, y to 1u) to Rational(2290577, 1728), - mapOf(x to 4u, y to 1u) to Rational(101507, 216), - mapOf(x to 5u, y to 1u) to Rational(213109, 288), - mapOf(x to 6u, y to 1u) to Rational(17927, 144), - mapOf(y to 2u) to Rational(314587, 1080), - mapOf(x to 1u, y to 2u) to Rational(-109771, 144), - mapOf(x to 2u, y to 2u) to Rational(-6469, 16), - mapOf(x to 3u, y to 2u) to Rational(-298291681, 181440), - mapOf(x to 4u, y to 2u) to Rational(-59147357, 48384), - mapOf(x to 5u, y to 2u) to Rational(-4982365, 6048), - mapOf(x to 6u, y to 2u) to Rational(-18727, 576), - mapOf(y to 3u) to Rational(12379, 90), - mapOf(x to 1u, y to 3u) to Rational(-542911, 1620), - mapOf(x to 2u, y to 3u) to Rational(143123, 1260), - mapOf(x to 3u, y to 3u) to Rational(9859177, 30240), - mapOf(x to 4u, y to 3u) to Rational(9312529, 20160), - mapOf(x to 5u, y to 3u) to Rational(207001, 672), - mapOf(x to 6u, y to 3u) to Rational(203, 24), - mapOf(y to 4u) to Rational(9442, 675), - mapOf(x to 1u, y to 4u) to Rational(-13729, 300), - mapOf(x to 2u, y to 4u) to Rational(-3490471, 25200), - mapOf(x to 3u, y to 4u) to Rational(-333031, 840), - mapOf(x to 4u, y to 4u) to Rational(-7572211, 47040), - mapOf(x to 5u, y to 4u) to Rational(-1189, 56), - mapOf(x to 6u, y to 4u) to Rational(-405, 196) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(14, 4), - mapOf(x to 1u) to Rational(7, 6), - mapOf(x to 2u) to Rational(7, 2), - mapOf(y to 1u) to Rational(-15, 2), - mapOf(x to 1u, y to 1u) to Rational(-13, 8), - mapOf(x to 2u, y to 1u) to Rational(-14, 3), - mapOf(y to 2u) to Rational(-7, 6), - mapOf(x to 1u, y to 2u) to Rational(7, 4), - mapOf(x to 2u, y to 2u) to Rational(9, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-7, 4), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(-16, 2), - mapOf(y to 1u) to Rational(-15, 5), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(5, 4), - mapOf(y to 2u) to Rational(-12, 5), - mapOf(x to 1u, y to 2u) to Rational(-18, 2), - mapOf(x to 2u, y to 2u) to Rational(6, 7), - ) - ), - )), - "test 4" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(2303, 64), - mapOf(x to 1u) to Rational(31843, 192), - mapOf(x to 2u) to Rational(118891, 576), - mapOf(x to 3u) to Rational(94453, 168), - mapOf(x to 4u) to Rational(-179203, 1512), - mapOf(x to 5u) to Rational(-16979, 126), - mapOf(x to 6u) to Rational(-13499, 12), - mapOf(y to 1u) to Rational(-4767, 64), - mapOf(x to 1u, y to 1u) to Rational(-58689, 256), - mapOf(x to 2u, y to 1u) to Rational(-757333, 4032), - mapOf(x to 3u, y to 1u) to Rational(-4921205, 4032), - mapOf(x to 4u, y to 1u) to Rational(-2930815, 4032), - mapOf(x to 5u, y to 1u) to Rational(-398803, 1512), - mapOf(x to 6u, y to 1u) to Rational(18835, 36), - mapOf(y to 2u) to Rational(224101, 960), - mapOf(x to 1u, y to 2u) to Rational(9139699, 40320), - mapOf(x to 2u, y to 2u) to Rational(3848803, 5760), - mapOf(x to 3u, y to 2u) to Rational(93102371, 241920), - mapOf(x to 4u, y to 2u) to Rational(-65821229, 141120), - mapOf(x to 5u, y to 2u) to Rational(-15675899, 7056), - mapOf(x to 6u, y to 2u) to Rational(10459, 189), - mapOf(y to 3u) to Rational(2411, 16), - mapOf(x to 1u, y to 3u) to Rational(1294543, 10080), - mapOf(x to 2u, y to 3u) to Rational(-1740199, 1440), - mapOf(x to 3u, y to 3u) to Rational(-266994841, 282240), - mapOf(x to 4u, y to 3u) to Rational(-41261893, 211680), - mapOf(x to 5u, y to 3u) to Rational(1717357, 3528), - mapOf(x to 6u, y to 3u) to Rational(69, 14), - mapOf(y to 4u) to Rational(13231, 360), - mapOf(x to 1u, y to 4u) to Rational(4858831, 25200), - mapOf(x to 2u, y to 4u) to Rational(15565759, 75600), - mapOf(x to 3u, y to 4u) to Rational(-15583391, 35280), - mapOf(x to 4u, y to 4u) to Rational(-13345747, 11760), - mapOf(x to 5u, y to 4u) to Rational(140103, 686), - mapOf(x to 6u, y to 4u) to Rational(-765, 49) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(31409, 576), - mapOf(x to 1u) to Rational(-337099, 1728), - mapOf(x to 2u) to Rational(-211429, 1728), - mapOf(x to 3u) to Rational(-259241, 432), - mapOf(x to 4u) to Rational(-13777, 36), - mapOf(x to 5u) to Rational(-41389, 72), - mapOf(x to 6u) to Rational(-7679, 48), - mapOf(y to 1u) to Rational(-3269, 12), - mapOf(x to 1u, y to 1u) to Rational(629569, 864), - mapOf(x to 2u, y to 1u) to Rational(53867, 324), - mapOf(x to 3u, y to 1u) to Rational(2290577, 1728), - mapOf(x to 4u, y to 1u) to Rational(101507, 216), - mapOf(x to 5u, y to 1u) to Rational(213109, 288), - mapOf(x to 6u, y to 1u) to Rational(17927, 144), - mapOf(y to 2u) to Rational(314587, 1080), - mapOf(x to 1u, y to 2u) to Rational(-109771, 144), - mapOf(x to 2u, y to 2u) to Rational(-6469, 16), - mapOf(x to 3u, y to 2u) to Rational(-298291681, 181440), - mapOf(x to 4u, y to 2u) to Rational(-59147357, 48384), - mapOf(x to 5u, y to 2u) to Rational(-4982365, 6048), - mapOf(x to 6u, y to 2u) to Rational(-18727, 576), - mapOf(y to 3u) to Rational(12379, 90), - mapOf(x to 1u, y to 3u) to Rational(-542911, 1620), - mapOf(x to 2u, y to 3u) to Rational(143123, 1260), - mapOf(x to 3u, y to 3u) to Rational(9859177, 30240), - mapOf(x to 4u, y to 3u) to Rational(9312529, 20160), - mapOf(x to 5u, y to 3u) to Rational(207001, 672), - mapOf(x to 6u, y to 3u) to Rational(203, 24), - mapOf(y to 4u) to Rational(9442, 675), - mapOf(x to 1u, y to 4u) to Rational(-13729, 300), - mapOf(x to 2u, y to 4u) to Rational(-3490471, 25200), - mapOf(x to 3u, y to 4u) to Rational(-333031, 840), - mapOf(x to 4u, y to 4u) to Rational(-7572211, 47040), - mapOf(x to 5u, y to 4u) to Rational(-1189, 56), - mapOf(x to 6u, y to 4u) to Rational(-405, 196) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - y to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(14, 4), - mapOf(x to 1u) to Rational(7, 6), - mapOf(x to 2u) to Rational(7, 2), - mapOf(y to 1u) to Rational(-15, 2), - mapOf(x to 1u, y to 1u) to Rational(-13, 8), - mapOf(x to 2u, y to 1u) to Rational(-14, 3), - mapOf(y to 2u) to Rational(-7, 6), - mapOf(x to 1u, y to 2u) to Rational(7, 4), - mapOf(x to 2u, y to 2u) to Rational(9, 7), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-7, 4), - mapOf(x to 1u) to Rational(-6, 3), - mapOf(x to 2u) to Rational(-16, 2), - mapOf(y to 1u) to Rational(-15, 5), - mapOf(x to 1u, y to 1u) to Rational(4, 6), - mapOf(x to 2u, y to 1u) to Rational(5, 4), - mapOf(y to 2u) to Rational(-12, 5), - mapOf(x to 1u, y to 2u) to Rational(-18, 2), - mapOf(x to 2u, y to 2u) to Rational(6, 7), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 8), - mapOf(x to 1u) to Rational(-12, 6), - mapOf(x to 2u) to Rational(7, 6), - mapOf(y to 1u) to Rational(-10, 4), - mapOf(x to 1u, y to 1u) to Rational(-7, 6), - mapOf(x to 2u, y to 1u) to Rational(8, 9), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(5, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(10, 6), - mapOf(x to 1u) to Rational(-18, 6), - mapOf(x to 2u) to Rational(5, 1), - mapOf(y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(8, 4), - mapOf(x to 2u, y to 1u) to Rational(-4, 9), - mapOf(y to 2u) to Rational(-6, 5), - mapOf(x to 1u, y to 2u) to Rational(-15, 8), - mapOf(x to 2u, y to 2u) to Rational(-18, 5), - ) - ), - )), - "test 4'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-506213, 2800), - mapOf(x to 1u) to Rational(9859, 315), - mapOf(x to 2u) to Rational(17384377, 11340), - mapOf(x to 3u) to Rational(-9662, 63), - mapOf(x to 4u) to Rational(-12563, 4), - mapOf(y to 1u) to Rational(-486293, 22400), - mapOf(x to 1u, y to 1u) to Rational(-6530947, 25200), - mapOf(x to 2u, y to 1u) to Rational(866125, 18144), - mapOf(x to 3u, y to 1u) to Rational(2948747, 2520), - mapOf(x to 4u, y to 1u) to Rational(1196611, 2016), - mapOf(y to 2u) to Rational(-20266021, 117600), - mapOf(x to 1u, y to 2u) to Rational(26656339, 44100), - mapOf(x to 2u, y to 2u) to Rational(19499183, 18144), - mapOf(x to 3u, y to 2u) to Rational(-19801849, 7560), - mapOf(x to 4u, y to 2u) to Rational(-2639635, 1296), - mapOf(y to 3u) to Rational(-5017697, 29400), - mapOf(x to 1u, y to 3u) to Rational(-606007, 1575), - mapOf(x to 2u, y to 3u) to Rational(127494487, 132300), - mapOf(x to 3u, y to 3u) to Rational(166567, 105), - mapOf(x to 4u, y to 3u) to Rational(486403, 18144), - mapOf(y to 4u) to Rational(-32182, 735), - mapOf(x to 1u, y to 4u) to Rational(2420671, 8820), - mapOf(x to 2u, y to 4u) to Rational(-12619193, 26460), - mapOf(x to 3u, y to 4u) to Rational(-6823067, 5670), - mapOf(x to 4u, y to 4u) to Rational(-2311693, 13608), - mapOf(y to 5u) to Rational(-13324, 245), - mapOf(x to 1u, y to 5u) to Rational(1966, 35), - mapOf(x to 2u, y to 5u) to Rational(1052719, 2520), - mapOf(x to 3u, y to 5u) to Rational(19153, 270), - mapOf(x to 4u, y to 5u) to Rational(701, 54), - mapOf(y to 6u) to Rational(4647, 196), - mapOf(x to 1u, y to 6u) to Rational(2197, 28), - mapOf(x to 2u, y to 6u) to Rational(-43853, 336), - mapOf(x to 3u, y to 6u) to Rational(-301, 3), - mapOf(x to 4u, y to 6u) to Rational(34, 3) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-2843, 1600), - mapOf(x to 1u) to Rational(-1483, 240), - mapOf(x to 2u) to Rational(110623, 1296), - mapOf(x to 3u) to Rational(1265, 72), - mapOf(x to 4u) to Rational(-5011, 16), - mapOf(y to 1u) to Rational(47743, 1800), - mapOf(x to 1u, y to 1u) to Rational(619229, 32400), - mapOf(x to 2u, y to 1u) to Rational(-5978369, 58320), - mapOf(x to 3u, y to 1u) to Rational(-86081, 1620), - mapOf(x to 4u, y to 1u) to Rational(6325, 72), - mapOf(y to 2u) to Rational(110951, 3360), - mapOf(x to 1u, y to 2u) to Rational(-9550649, 302400), - mapOf(x to 2u, y to 2u) to Rational(6542933, 85050), - mapOf(x to 3u, y to 2u) to Rational(4708291, 38880), - mapOf(x to 4u, y to 2u) to Rational(-433327, 1296), - mapOf(y to 3u) to Rational(56143, 600), - mapOf(x to 1u, y to 3u) to Rational(94243, 720), - mapOf(x to 2u, y to 3u) to Rational(-46779139, 226800), - mapOf(x to 3u, y to 3u) to Rational(-6948253, 12960), - mapOf(x to 4u, y to 3u) to Rational(-260261, 486), - mapOf(y to 4u) to Rational(-3205317, 19600), - mapOf(x to 1u, y to 4u) to Rational(-201253, 1050), - mapOf(x to 2u, y to 4u) to Rational(332192677, 302400), - mapOf(x to 3u, y to 4u) to Rational(351511, 360), - mapOf(x to 4u, y to 4u) to Rational(-40547, 81), - mapOf(y to 5u) to Rational(-65421, 1960), - mapOf(x to 1u, y to 5u) to Rational(-10118, 35), - mapOf(x to 2u, y to 5u) to Rational(-4341709, 10080), - mapOf(x to 3u, y to 5u) to Rational(-91703, 360), - mapOf(x to 4u, y to 5u) to Rational(-85, 9), - mapOf(y to 6u) to Rational(-25965, 784), - mapOf(x to 1u, y to 6u) to Rational(3351, 16), - mapOf(x to 2u, y to 6u) to Rational(595159, 1344), - mapOf(x to 3u, y to 6u) to Rational(-1381, 12), - mapOf(x to 4u, y to 6u) to Rational(-155, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-17, 5), - mapOf(x to 1u) to Rational(2, 6), - mapOf(x to 2u) to Rational(14, 1), - mapOf(y to 1u) to Rational(-6, 6), - mapOf(x to 1u, y to 1u) to Rational(-7, 3), - mapOf(x to 2u, y to 1u) to Rational(-2, 9), - mapOf(y to 2u) to Rational(-9, 6), - mapOf(x to 1u, y to 2u) to Rational(17, 4), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5, 4), - mapOf(x to 1u) to Rational(-5, 9), - mapOf(x to 2u) to Rational(-3, 6), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(14, 5), - mapOf(x to 2u, y to 1u) to Rational(5, 2), - mapOf(y to 2u) to Rational(-18, 7), - mapOf(x to 1u, y to 2u) to Rational(-8, 2), - mapOf(x to 2u, y to 2u) to Rational(18, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-506213, 2800), - mapOf(x to 1u) to Rational(9859, 315), - mapOf(x to 2u) to Rational(17384377, 11340), - mapOf(x to 3u) to Rational(-9662, 63), - mapOf(x to 4u) to Rational(-12563, 4), - mapOf(y to 1u) to Rational(-486293, 22400), - mapOf(x to 1u, y to 1u) to Rational(-6530947, 25200), - mapOf(x to 2u, y to 1u) to Rational(866125, 18144), - mapOf(x to 3u, y to 1u) to Rational(2948747, 2520), - mapOf(x to 4u, y to 1u) to Rational(1196611, 2016), - mapOf(y to 2u) to Rational(-20266021, 117600), - mapOf(x to 1u, y to 2u) to Rational(26656339, 44100), - mapOf(x to 2u, y to 2u) to Rational(19499183, 18144), - mapOf(x to 3u, y to 2u) to Rational(-19801849, 7560), - mapOf(x to 4u, y to 2u) to Rational(-2639635, 1296), - mapOf(y to 3u) to Rational(-5017697, 29400), - mapOf(x to 1u, y to 3u) to Rational(-606007, 1575), - mapOf(x to 2u, y to 3u) to Rational(127494487, 132300), - mapOf(x to 3u, y to 3u) to Rational(166567, 105), - mapOf(x to 4u, y to 3u) to Rational(486403, 18144), - mapOf(y to 4u) to Rational(-32182, 735), - mapOf(x to 1u, y to 4u) to Rational(2420671, 8820), - mapOf(x to 2u, y to 4u) to Rational(-12619193, 26460), - mapOf(x to 3u, y to 4u) to Rational(-6823067, 5670), - mapOf(x to 4u, y to 4u) to Rational(-2311693, 13608), - mapOf(y to 5u) to Rational(-13324, 245), - mapOf(x to 1u, y to 5u) to Rational(1966, 35), - mapOf(x to 2u, y to 5u) to Rational(1052719, 2520), - mapOf(x to 3u, y to 5u) to Rational(19153, 270), - mapOf(x to 4u, y to 5u) to Rational(701, 54), - mapOf(y to 6u) to Rational(4647, 196), - mapOf(x to 1u, y to 6u) to Rational(2197, 28), - mapOf(x to 2u, y to 6u) to Rational(-43853, 336), - mapOf(x to 3u, y to 6u) to Rational(-301, 3), - mapOf(x to 4u, y to 6u) to Rational(34, 3) - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-2843, 1600), - mapOf(x to 1u) to Rational(-1483, 240), - mapOf(x to 2u) to Rational(110623, 1296), - mapOf(x to 3u) to Rational(1265, 72), - mapOf(x to 4u) to Rational(-5011, 16), - mapOf(y to 1u) to Rational(47743, 1800), - mapOf(x to 1u, y to 1u) to Rational(619229, 32400), - mapOf(x to 2u, y to 1u) to Rational(-5978369, 58320), - mapOf(x to 3u, y to 1u) to Rational(-86081, 1620), - mapOf(x to 4u, y to 1u) to Rational(6325, 72), - mapOf(y to 2u) to Rational(110951, 3360), - mapOf(x to 1u, y to 2u) to Rational(-9550649, 302400), - mapOf(x to 2u, y to 2u) to Rational(6542933, 85050), - mapOf(x to 3u, y to 2u) to Rational(4708291, 38880), - mapOf(x to 4u, y to 2u) to Rational(-433327, 1296), - mapOf(y to 3u) to Rational(56143, 600), - mapOf(x to 1u, y to 3u) to Rational(94243, 720), - mapOf(x to 2u, y to 3u) to Rational(-46779139, 226800), - mapOf(x to 3u, y to 3u) to Rational(-6948253, 12960), - mapOf(x to 4u, y to 3u) to Rational(-260261, 486), - mapOf(y to 4u) to Rational(-3205317, 19600), - mapOf(x to 1u, y to 4u) to Rational(-201253, 1050), - mapOf(x to 2u, y to 4u) to Rational(332192677, 302400), - mapOf(x to 3u, y to 4u) to Rational(351511, 360), - mapOf(x to 4u, y to 4u) to Rational(-40547, 81), - mapOf(y to 5u) to Rational(-65421, 1960), - mapOf(x to 1u, y to 5u) to Rational(-10118, 35), - mapOf(x to 2u, y to 5u) to Rational(-4341709, 10080), - mapOf(x to 3u, y to 5u) to Rational(-91703, 360), - mapOf(x to 4u, y to 5u) to Rational(-85, 9), - mapOf(y to 6u) to Rational(-25965, 784), - mapOf(x to 1u, y to 6u) to Rational(3351, 16), - mapOf(x to 2u, y to 6u) to Rational(595159, 1344), - mapOf(x to 3u, y to 6u) to Rational(-1381, 12), - mapOf(x to 4u, y to 6u) to Rational(-155, 3) - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - x to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(-17, 5), - mapOf(x to 1u) to Rational(2, 6), - mapOf(x to 2u) to Rational(14, 1), - mapOf(y to 1u) to Rational(-6, 6), - mapOf(x to 1u, y to 1u) to Rational(-7, 3), - mapOf(x to 2u, y to 1u) to Rational(-2, 9), - mapOf(y to 2u) to Rational(-9, 6), - mapOf(x to 1u, y to 2u) to Rational(17, 4), - mapOf(x to 2u, y to 2u) to Rational(2, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(5, 4), - mapOf(x to 1u) to Rational(-5, 9), - mapOf(x to 2u) to Rational(-3, 6), - mapOf(y to 1u) to Rational(6, 5), - mapOf(x to 1u, y to 1u) to Rational(14, 5), - mapOf(x to 2u, y to 1u) to Rational(5, 2), - mapOf(y to 2u) to Rational(-18, 7), - mapOf(x to 1u, y to 2u) to Rational(-8, 2), - mapOf(x to 2u, y to 2u) to Rational(18, 9), - ) - ), - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 8), - mapOf(x to 1u) to Rational(-12, 6), - mapOf(x to 2u) to Rational(7, 6), - mapOf(y to 1u) to Rational(-10, 4), - mapOf(x to 1u, y to 1u) to Rational(-7, 6), - mapOf(x to 2u, y to 1u) to Rational(8, 9), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(5, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(10, 6), - mapOf(x to 1u) to Rational(-18, 6), - mapOf(x to 2u) to Rational(5, 1), - mapOf(y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(8, 4), - mapOf(x to 2u, y to 1u) to Rational(-4, 9), - mapOf(y to 2u) to Rational(-6, 5), - mapOf(x to 1u, y to 2u) to Rational(-15, 8), - mapOf(x to 2u, y to 2u) to Rational(-18, 5), - ) - ), - )), - "test 5'" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ), - LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(10, 2), - mapOf(x to 1u) to Rational(6, 7), - mapOf(x to 2u) to Rational(-16, 1), - mapOf(y to 1u) to Rational(13, 8), - mapOf(x to 1u, y to 1u) to Rational(-12, 1), - mapOf(x to 2u, y to 1u) to Rational(16, 8), - mapOf(y to 2u) to Rational(10, 4), - mapOf(x to 1u, y to 2u) to Rational(4, 1), - mapOf(x to 2u, y to 2u) to Rational(-11, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1, 4), - mapOf(x to 1u) to Rational(-17, 4), - mapOf(x to 2u) to Rational(-14, 8), - mapOf(y to 1u) to Rational(17, 9), - mapOf(x to 1u, y to 1u) to Rational(1, 3), - mapOf(x to 2u, y to 1u) to Rational(7, 6), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-17, 1), - mapOf(x to 2u, y to 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - iota to LabeledRationalFunction( - LabeledPolynomialAsIs( - mapOf() to Rational(5, 8), - mapOf(x to 1u) to Rational(-12, 6), - mapOf(x to 2u) to Rational(7, 6), - mapOf(y to 1u) to Rational(-10, 4), - mapOf(x to 1u, y to 1u) to Rational(-7, 6), - mapOf(x to 2u, y to 1u) to Rational(8, 9), - mapOf(y to 2u) to Rational(16, 3), - mapOf(x to 1u, y to 2u) to Rational(-13, 4), - mapOf(x to 2u, y to 2u) to Rational(5, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(10, 6), - mapOf(x to 1u) to Rational(-18, 6), - mapOf(x to 2u) to Rational(5, 1), - mapOf(y to 1u) to Rational(17, 7), - mapOf(x to 1u, y to 1u) to Rational(8, 4), - mapOf(x to 2u, y to 1u) to Rational(-4, 9), - mapOf(y to 2u) to Rational(-6, 5), - mapOf(x to 1u, y to 2u) to Rational(-15, 8), - mapOf(x to 2u, y to 2u) to Rational(-18, 5), - ) - ), - )), - "test 6'" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_derivativeWithRespectTo_variable() { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2), - mapOf(x to 1u) to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).derivativeWithRespectTo(RationalField, x), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 3), - mapOf(x to 1u) to Rational(1, 1), - mapOf(x to 2u) to Rational(-33, 8), - mapOf(x to 3u) to Rational(72, 1), - mapOf(y to 1u) to Rational(2, 3), - mapOf(x to 1u, y to 1u) to Rational(-22, 1), - mapOf(x to 2u, y to 1u) to Rational(-1, 1), - mapOf(x to 3u, y to 1u) to Rational(-36, 1), - mapOf(y to 2u) to Rational(-8, 5), - mapOf(x to 1u, y to 2u) to Rational(-1, 4), - mapOf(x to 2u, y to 2u) to Rational(12, 7), - mapOf(x to 3u, y to 2u) to Rational(-2, 1), - mapOf(y to 3u) to Rational(16, 8), - mapOf(x to 1u, y to 3u) to Rational(-4, 1), - mapOf(x to 2u, y to 3u) to Rational(9, 2), - mapOf(x to 3u, y to 3u) to Rational(20, 9), - mapOf(y to 4u) to Rational(-10, 1), - mapOf(x to 1u, y to 4u) to Rational(-14, 1), - mapOf(x to 2u, y to 4u) to Rational(3, 7), - mapOf(x to 3u, y to 4u) to Rational(20, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, x), - "test 2a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-18, 3), - mapOf(x to 1u) to Rational(2, 3), - mapOf(x to 2u) to Rational(-11, 1), - mapOf(x to 3u) to Rational(-1, 3), - mapOf(x to 4u) to Rational(-18, 2), - mapOf(y to 1u) to Rational(-20, 3), - mapOf(x to 1u, y to 1u) to Rational(-16, 5), - mapOf(x to 2u, y to 1u) to Rational(-1, 4), - mapOf(x to 3u, y to 1u) to Rational(8, 7), - mapOf(x to 4u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(9, 7), - mapOf(x to 1u, y to 2u) to Rational(6, 1), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(x to 3u, y to 2u) to Rational(9, 2), - mapOf(x to 4u, y to 2u) to Rational(5, 3), - mapOf(y to 3u) to Rational(-9, 1), - mapOf(x to 1u, y to 3u) to Rational(-40, 1), - mapOf(x to 2u, y to 3u) to Rational(-28, 1), - mapOf(x to 3u, y to 3u) to Rational(4, 7), - mapOf(x to 4u, y to 3u) to Rational(20, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, y), - "test 2b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(-1, 4), - mapOf(x to 2u, y to 2u) to Rational(12, 7), - mapOf(x to 3u, y to 2u) to Rational(-2, 1), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(-4, 1), - mapOf(x to 2u, y to 3u) to Rational(9, 2), - mapOf(x to 3u, y to 3u) to Rational(20, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(-14, 1), - mapOf(x to 2u, y to 4u) to Rational(3, 7), - mapOf(x to 3u, y to 4u) to Rational(20, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, x), - "test 3a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(-1, 4), - mapOf(x to 3u, y to 1u) to Rational(8, 7), - mapOf(x to 4u, y to 1u) to Rational(-1, 1), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(x to 3u, y to 2u) to Rational(9, 2), - mapOf(x to 4u, y to 2u) to Rational(5, 3), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-28, 1), - mapOf(x to 3u, y to 3u) to Rational(4, 7), - mapOf(x to 4u, y to 3u) to Rational(20, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, y), - "test 3b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2, 3), - mapOf(x to 1u) to Rational(1, 1), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(y to 1u) to Rational(2, 3), - mapOf(x to 1u, y to 1u) to Rational(-22, 1), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-8, 5), - mapOf(x to 1u, y to 2u) to Rational(-1, 4), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).derivativeWithRespectTo(RationalField, x), - "test 4a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-18, 3), - mapOf(x to 1u) to Rational(2, 3), - mapOf(x to 2u) to Rational(-11, 1), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-20, 3), - mapOf(x to 1u, y to 1u) to Rational(-16, 5), - mapOf(x to 2u, y to 1u) to Rational(-1, 4), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).derivativeWithRespectTo(RationalField, y), - "test 4b" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, iota), - "test 5" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthDerivativeWithRespectTo_variable_order() { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2), - mapOf(x to 1u) to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, x, 1u), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, x, 0u), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, x, 2u), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, x, 3u), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, x, 4u), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, y, 0u), - "test 6" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, y, 1u), - "test 7" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, y, 2u), - "test 8" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1, 1), - mapOf(x to 1u) to Rational(-33, 4), - mapOf(x to 2u) to Rational(216, 1), - mapOf(y to 1u) to Rational(-22, 1), - mapOf(x to 1u, y to 1u) to Rational(-2, 1), - mapOf(x to 2u, y to 1u) to Rational(-108, 1), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(24, 7), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(y to 3u) to Rational(-4, 1), - mapOf(x to 1u, y to 3u) to Rational(9, 1), - mapOf(x to 2u, y to 3u) to Rational(20, 3), - mapOf(y to 4u) to Rational(-14, 1), - mapOf(x to 1u, y to 4u) to Rational(6, 7), - mapOf(x to 2u, y to 4u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, x, 2u), - "test 9a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-20, 3), - mapOf(x to 1u) to Rational(-16, 5), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(8, 7), - mapOf(x to 4u) to Rational(-1, 1), - mapOf(y to 1u) to Rational(18, 7), - mapOf(x to 1u, y to 1u) to Rational(12, 1), - mapOf(x to 2u, y to 1u) to Rational(-12, 1), - mapOf(x to 3u, y to 1u) to Rational(9, 1), - mapOf(x to 4u, y to 1u) to Rational(10, 3), - mapOf(y to 2u) to Rational(-27, 1), - mapOf(x to 1u, y to 2u) to Rational(-120, 1), - mapOf(x to 2u, y to 2u) to Rational(-84, 1), - mapOf(x to 3u, y to 2u) to Rational(12, 7), - mapOf(x to 4u, y to 2u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, y, 2u), - "test 9b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(24, 7), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(y to 3u) to Rational(-4, 1), - mapOf(x to 1u, y to 3u) to Rational(9, 1), - mapOf(x to 2u, y to 3u) to Rational(20, 3), - mapOf(y to 4u) to Rational(-14, 1), - mapOf(x to 1u, y to 4u) to Rational(6, 7), - mapOf(x to 2u, y to 4u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, x, 2u), - "test 10a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(8, 7), - mapOf(x to 4u) to Rational(-1, 1), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(-12, 1), - mapOf(x to 3u, y to 1u) to Rational(9, 1), - mapOf(x to 4u, y to 1u) to Rational(10, 3), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-84, 1), - mapOf(x to 3u, y to 2u) to Rational(12, 7), - mapOf(x to 4u, y to 2u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, y, 2u), - "test 10b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1, 1), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(y to 1u) to Rational(-22, 1), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, x, 2u), - "test 11a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-20, 3), - mapOf(x to 1u) to Rational(-16, 5), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, y, 2u), - "test 11b" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthDerivativeWithRespectTo_variablesAndOrders() { - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2), - mapOf(x to 1u) to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 1u)), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 0u)), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 3u)), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 4u)), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 0u)), - "test 6" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 1u)), - "test 7" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 8" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf()), - "test 9" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-2), - mapOf(x to 1u) to Rational(2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf( - x to 1u, - y to 0u - )), - "test 10" - ) - assertEquals( - LabeledPolynomialAsIs(), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf( - x to 0u, - y to 1u - )), - "test 11" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1, 1), - mapOf(x to 1u) to Rational(-33, 4), - mapOf(x to 2u) to Rational(216, 1), - mapOf(y to 1u) to Rational(-22, 1), - mapOf(x to 1u, y to 1u) to Rational(-2, 1), - mapOf(x to 2u, y to 1u) to Rational(-108, 1), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(24, 7), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(y to 3u) to Rational(-4, 1), - mapOf(x to 1u, y to 3u) to Rational(9, 1), - mapOf(x to 2u, y to 3u) to Rational(20, 3), - mapOf(y to 4u) to Rational(-14, 1), - mapOf(x to 1u, y to 4u) to Rational(6, 7), - mapOf(x to 2u, y to 4u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 12a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(2, 3), - mapOf(x to 1u) to Rational(-22, 1), - mapOf(x to 2u) to Rational(-1, 1), - mapOf(x to 3u) to Rational(-36, 1), - mapOf(y to 1u) to Rational(-16, 5), - mapOf(x to 1u, y to 1u) to Rational(-1, 2), - mapOf(x to 2u, y to 1u) to Rational(24, 7), - mapOf(x to 3u, y to 1u) to Rational(-4, 1), - mapOf(y to 2u) to Rational(6, 1), - mapOf(x to 1u, y to 2u) to Rational(-12, 1), - mapOf(x to 2u, y to 2u) to Rational(27, 2), - mapOf(x to 3u, y to 2u) to Rational(20, 3), - mapOf(y to 3u) to Rational(-40, 1), - mapOf(x to 1u, y to 3u) to Rational(-56, 1), - mapOf(x to 2u, y to 3u) to Rational(12, 7), - mapOf(x to 3u, y to 3u) to Rational(80, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 12b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-20, 3), - mapOf(x to 1u) to Rational(-16, 5), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(8, 7), - mapOf(x to 4u) to Rational(-1, 1), - mapOf(y to 1u) to Rational(18, 7), - mapOf(x to 1u, y to 1u) to Rational(12, 1), - mapOf(x to 2u, y to 1u) to Rational(-12, 1), - mapOf(x to 3u, y to 1u) to Rational(9, 1), - mapOf(x to 4u, y to 1u) to Rational(10, 3), - mapOf(y to 2u) to Rational(-27, 1), - mapOf(x to 1u, y to 2u) to Rational(-120, 1), - mapOf(x to 2u, y to 2u) to Rational(-84, 1), - mapOf(x to 3u, y to 2u) to Rational(12, 7), - mapOf(x to 4u, y to 2u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 12c" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(24, 7), - mapOf(x to 2u, y to 2u) to Rational(-6, 1), - mapOf(y to 3u) to Rational(-4, 1), - mapOf(x to 1u, y to 3u) to Rational(9, 1), - mapOf(x to 2u, y to 3u) to Rational(20, 3), - mapOf(y to 4u) to Rational(-14, 1), - mapOf(x to 1u, y to 4u) to Rational(6, 7), - mapOf(x to 2u, y to 4u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 13a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(-1, 2), - mapOf(x to 2u, y to 1u) to Rational(24, 7), - mapOf(x to 3u, y to 1u) to Rational(-4, 1), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(-12, 1), - mapOf(x to 2u, y to 2u) to Rational(27, 2), - mapOf(x to 3u, y to 2u) to Rational(20, 3), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(-56, 1), - mapOf(x to 2u, y to 3u) to Rational(12, 7), - mapOf(x to 3u, y to 3u) to Rational(80, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 13b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(8, 7), - mapOf(x to 4u) to Rational(-1, 1), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(-12, 1), - mapOf(x to 3u, y to 1u) to Rational(9, 1), - mapOf(x to 4u, y to 1u) to Rational(10, 3), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-84, 1), - mapOf(x to 3u, y to 2u) to Rational(12, 7), - mapOf(x to 4u, y to 2u) to Rational(60, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 13c" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1, 1), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(y to 1u) to Rational(-22, 1), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-1, 4), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 14a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(2, 3), - mapOf(x to 1u) to Rational(-22, 1), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(y to 1u) to Rational(-16, 5), - mapOf(x to 1u, y to 1u) to Rational(-1, 2), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 14b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(-20, 3), - mapOf(x to 1u) to Rational(-16, 5), - mapOf(x to 2u) to Rational(-1, 4), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 14c" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_antiderivativeWithRespectTo_variable() { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(x to 2u) to Rational(-1), - mapOf(x to 3u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).antiderivativeWithRespectTo(RationalField, x), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-6, 8), - mapOf(x to 2u) to Rational(-1, 3), - mapOf(x to 3u) to Rational(1, 6), - mapOf(x to 4u) to Rational(-11, 32), - mapOf(x to 5u) to Rational(18, 5), - mapOf(x to 1u, y to 1u) to Rational(-18, 3), - mapOf(x to 2u, y to 1u) to Rational(1, 3), - mapOf(x to 3u, y to 1u) to Rational(-11, 3), - mapOf(x to 4u, y to 1u) to Rational(-1, 12), - mapOf(x to 5u, y to 1u) to Rational(-18, 10), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(-4, 5), - mapOf(x to 3u, y to 2u) to Rational(-1, 24), - mapOf(x to 4u, y to 2u) to Rational(1, 7), - mapOf(x to 5u, y to 2u) to Rational(-1, 10), - mapOf(x to 1u, y to 3u) to Rational(3, 7), - mapOf(x to 2u, y to 3u) to Rational(1, 1), - mapOf(x to 3u, y to 3u) to Rational(-2, 3), - mapOf(x to 4u, y to 3u) to Rational(3, 8), - mapOf(x to 5u, y to 3u) to Rational(1, 9), - mapOf(x to 1u, y to 4u) to Rational(-18, 8), - mapOf(x to 2u, y to 4u) to Rational(-5, 1), - mapOf(x to 3u, y to 4u) to Rational(-7, 3), - mapOf(x to 4u, y to 4u) to Rational(1, 28), - mapOf(x to 5u, y to 4u) to Rational(1, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, x), - "test 2a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(-6, 8), - mapOf(x to 1u, y to 1u) to Rational(-2, 3), - mapOf(x to 2u, y to 1u) to Rational(1, 2), - mapOf(x to 3u, y to 1u) to Rational(-11, 8), - mapOf(x to 4u, y to 1u) to Rational(18, 1), - mapOf(y to 2u) to Rational(-9, 3), - mapOf(x to 1u, y to 2u) to Rational(1, 3), - mapOf(x to 2u, y to 2u) to Rational(-11, 2), - mapOf(x to 3u, y to 2u) to Rational(-1, 6), - mapOf(x to 4u, y to 2u) to Rational(-9, 2), - mapOf(y to 3u) to Rational(-10, 9), - mapOf(x to 1u, y to 3u) to Rational(-8, 15), - mapOf(x to 2u, y to 3u) to Rational(-1, 24), - mapOf(x to 3u, y to 3u) to Rational(4, 21), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(y to 4u) to Rational(3, 28), - mapOf(x to 1u, y to 4u) to Rational(1, 2), - mapOf(x to 2u, y to 4u) to Rational(-1, 2), - mapOf(x to 3u, y to 4u) to Rational(3, 8), - mapOf(x to 4u, y to 4u) to Rational(5, 36), - mapOf(y to 5u) to Rational(-9, 20), - mapOf(x to 1u, y to 5u) to Rational(-2, 1), - mapOf(x to 2u, y to 5u) to Rational(-7, 5), - mapOf(x to 3u, y to 5u) to Rational(1, 35), - mapOf(x to 4u, y to 5u) to Rational(1, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, y), - "test 2b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(-1, 24), - mapOf(x to 4u, y to 2u) to Rational(1, 7), - mapOf(x to 5u, y to 2u) to Rational(-1, 10), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(-2, 3), - mapOf(x to 4u, y to 3u) to Rational(3, 8), - mapOf(x to 5u, y to 3u) to Rational(1, 9), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(-7, 3), - mapOf(x to 4u, y to 4u) to Rational(1, 28), - mapOf(x to 5u, y to 4u) to Rational(1, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, x), - "test 3a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-1, 24), - mapOf(x to 3u, y to 3u) to Rational(4, 21), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-1, 2), - mapOf(x to 3u, y to 4u) to Rational(3, 8), - mapOf(x to 4u, y to 4u) to Rational(5, 36), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(-7, 5), - mapOf(x to 3u, y to 5u) to Rational(1, 35), - mapOf(x to 4u, y to 5u) to Rational(1, 1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, y), - "test 3b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(-6, 8), - mapOf(x to 2u) to Rational(-1, 3), - mapOf(x to 3u) to Rational(1, 6), - mapOf(x to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(-18, 3), - mapOf(x to 2u, y to 1u) to Rational(1, 3), - mapOf(x to 3u, y to 1u) to Rational(-11, 3), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(-10, 3), - mapOf(x to 2u, y to 2u) to Rational(-4, 5), - mapOf(x to 3u, y to 2u) to Rational(-1, 24), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(x to 5u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(x to 5u, y to 3u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(x to 5u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).antiderivativeWithRespectTo(RationalField, x), - "test 4a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(-6, 8), - mapOf(x to 1u, y to 1u) to Rational(-2, 3), - mapOf(x to 2u, y to 1u) to Rational(1, 2), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-9, 3), - mapOf(x to 1u, y to 2u) to Rational(1, 3), - mapOf(x to 2u, y to 2u) to Rational(-11, 2), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(-10, 9), - mapOf(x to 1u, y to 3u) to Rational(-8, 15), - mapOf(x to 2u, y to 3u) to Rational(-1, 24), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(0), - mapOf(x to 3u, y to 5u) to Rational(0), - mapOf(x to 4u, y to 5u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).antiderivativeWithRespectTo(RationalField, y), - "test 4b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(iota to 1u) to Rational(-6, 8), - mapOf(x to 1u, iota to 1u) to Rational(-2, 3), - mapOf(x to 2u, iota to 1u) to Rational(1, 2), - mapOf(x to 3u, iota to 1u) to Rational(-11, 8), - mapOf(x to 4u, iota to 1u) to Rational(18, 1), - mapOf(y to 1u, iota to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u, iota to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u, iota to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u, iota to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u, iota to 1u) to Rational(-18, 2), - mapOf(y to 2u, iota to 1u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u, iota to 1u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u, iota to 1u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u, iota to 1u) to Rational(4, 7), - mapOf(x to 4u, y to 2u, iota to 1u) to Rational(-4, 8), - mapOf(y to 3u, iota to 1u) to Rational(3, 7), - mapOf(x to 1u, y to 3u, iota to 1u) to Rational(16, 8), - mapOf(x to 2u, y to 3u, iota to 1u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u, iota to 1u) to Rational(12, 8), - mapOf(x to 4u, y to 3u, iota to 1u) to Rational(5, 9), - mapOf(y to 4u, iota to 1u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u, iota to 1u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u, iota to 1u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u, iota to 1u) to Rational(1, 7), - mapOf(x to 4u, y to 4u, iota to 1u) to Rational(15, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, iota), - "test 5" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthAntiderivativeWithRespectTo_variable_order() { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(x to 2u) to Rational(-1), - mapOf(x to 3u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 1u), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 0u), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-1, 3), - mapOf(x to 4u) to Rational(1, 12), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 2u), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 3u) to Rational(1, 6), - mapOf(x to 4u) to Rational(-1, 12), - mapOf(x to 5u) to Rational(1, 60), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 3u), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(-1, 60), - mapOf(x to 6u) to Rational(1, 360), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 4u), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 0u), - "test 6" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(1), - mapOf(x to 1u, y to 1u) to Rational(-2), - mapOf(x to 2u, y to 1u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 1u), - "test 7" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(1, 2), - mapOf(x to 1u, y to 2u) to Rational(-1), - mapOf(x to 2u, y to 2u) to Rational(1, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 2u), - "test 8" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(-3, 8), - mapOf(x to 3u) to Rational(-1, 9), - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(-11, 160), - mapOf(x to 6u) to Rational(3, 5), - mapOf(x to 2u, y to 1u) to Rational(-9, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 9), - mapOf(x to 4u, y to 1u) to Rational(-11, 12), - mapOf(x to 5u, y to 1u) to Rational(-1, 60), - mapOf(x to 6u, y to 1u) to Rational(-3, 10), - mapOf(x to 2u, y to 2u) to Rational(-5, 3), - mapOf(x to 3u, y to 2u) to Rational(-4, 15), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(1, 35), - mapOf(x to 6u, y to 2u) to Rational(-1, 60), - mapOf(x to 2u, y to 3u) to Rational(3, 14), - mapOf(x to 3u, y to 3u) to Rational(1, 3), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(x to 5u, y to 3u) to Rational(3, 40), - mapOf(x to 6u, y to 3u) to Rational(1, 54), - mapOf(x to 2u, y to 4u) to Rational(-9, 8), - mapOf(x to 3u, y to 4u) to Rational(-5, 3), - mapOf(x to 4u, y to 4u) to Rational(-7, 12), - mapOf(x to 5u, y to 4u) to Rational(1, 140), - mapOf(x to 6u, y to 4u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, x, 2u), - "test 9a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(-3, 8), - mapOf(x to 1u, y to 2u) to Rational(-1, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 4), - mapOf(x to 3u, y to 2u) to Rational(-11, 16), - mapOf(x to 4u, y to 2u) to Rational(9, 1), - mapOf(y to 3u) to Rational(-1, 1), - mapOf(x to 1u, y to 3u) to Rational(1, 9), - mapOf(x to 2u, y to 3u) to Rational(-11, 6), - mapOf(x to 3u, y to 3u) to Rational(-1, 18), - mapOf(x to 4u, y to 3u) to Rational(-9, 6), - mapOf(y to 4u) to Rational(-5, 18), - mapOf(x to 1u, y to 4u) to Rational(-2, 15), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(1, 21), - mapOf(x to 4u, y to 4u) to Rational(-1, 24), - mapOf(y to 5u) to Rational(3, 140), - mapOf(x to 1u, y to 5u) to Rational(1, 10), - mapOf(x to 2u, y to 5u) to Rational(-1, 10), - mapOf(x to 3u, y to 5u) to Rational(3, 40), - mapOf(x to 4u, y to 5u) to Rational(1, 36), - mapOf(y to 6u) to Rational(-3, 40), - mapOf(x to 1u, y to 6u) to Rational(-1, 3), - mapOf(x to 2u, y to 6u) to Rational(-7, 30), - mapOf(x to 3u, y to 6u) to Rational(1, 210), - mapOf(x to 4u, y to 6u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, y, 2u), - "test 9b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - mapOf(x to 6u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 6u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(1, 35), - mapOf(x to 6u, y to 2u) to Rational(-1, 60), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(x to 5u, y to 3u) to Rational(3, 40), - mapOf(x to 6u, y to 3u) to Rational(1, 54), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(-7, 12), - mapOf(x to 5u, y to 4u) to Rational(1, 140), - mapOf(x to 6u, y to 4u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, x, 2u), - "test 10a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(1, 21), - mapOf(x to 4u, y to 4u) to Rational(-1, 24), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(-1, 10), - mapOf(x to 3u, y to 5u) to Rational(3, 40), - mapOf(x to 4u, y to 5u) to Rational(1, 36), - mapOf(y to 6u) to Rational(0), - mapOf(x to 1u, y to 6u) to Rational(0), - mapOf(x to 2u, y to 6u) to Rational(-7, 30), - mapOf(x to 3u, y to 6u) to Rational(1, 210), - mapOf(x to 4u, y to 6u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, y, 2u), - "test 10b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(-3, 8), - mapOf(x to 3u) to Rational(-1, 9), - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(0), - mapOf(x to 6u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(-9, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 9), - mapOf(x to 4u, y to 1u) to Rational(-11, 12), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 6u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-5, 3), - mapOf(x to 3u, y to 2u) to Rational(-4, 15), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(0), - mapOf(x to 6u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(x to 5u, y to 3u) to Rational(0), - mapOf(x to 6u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(x to 5u, y to 4u) to Rational(0), - mapOf(x to 6u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, x, 2u), - "test 11a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(-3, 8), - mapOf(x to 1u, y to 2u) to Rational(-1, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 4), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(-1, 1), - mapOf(x to 1u, y to 3u) to Rational(1, 9), - mapOf(x to 2u, y to 3u) to Rational(-11, 6), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(-5, 18), - mapOf(x to 1u, y to 4u) to Rational(-2, 15), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(0), - mapOf(x to 3u, y to 5u) to Rational(0), - mapOf(x to 4u, y to 5u) to Rational(0), - mapOf(y to 6u) to Rational(0), - mapOf(x to 1u, y to 6u) to Rational(0), - mapOf(x to 2u, y to 6u) to Rational(0), - mapOf(x to 3u, y to 6u) to Rational(0), - mapOf(x to 4u, y to 6u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, y, 2u), - "test 11b" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthAntiderivativeWithRespectTo_variablesAndOrders() { - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(x to 2u) to Rational(-1), - mapOf(x to 3u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 1u)), - "test 1" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 0u), - "test 2" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-1, 3), - mapOf(x to 4u) to Rational(1, 12), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 2u), - "test 3" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 3u) to Rational(1, 6), - mapOf(x to 4u) to Rational(-1, 12), - mapOf(x to 5u) to Rational(1, 60), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 3u), - "test 4" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(-1, 60), - mapOf(x to 6u) to Rational(1, 360), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, x, 4u), - "test 5" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 0u), - "test 6" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(1), - mapOf(x to 1u, y to 1u) to Rational(-2), - mapOf(x to 2u, y to 1u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 1u), - "test 7" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(1, 2), - mapOf(x to 1u, y to 2u) to Rational(-1), - mapOf(x to 2u, y to 2u) to Rational(1, 2), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, y, 2u), - "test 8" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf()), - "test 9" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u) to Rational(1), - mapOf(x to 2u) to Rational(-1), - mapOf(x to 3u) to Rational(1, 3), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf( - x to 1u, - y to 0u - )), - "test 10" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 1u) to Rational(1), - mapOf(x to 1u, y to 1u) to Rational(-2), - mapOf(x to 2u, y to 1u) to Rational(1), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(1), - mapOf(x to 1u) to Rational(-2), - mapOf(x to 2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf( - x to 0u, - y to 1u - )), - "test 11" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(-3, 8), - mapOf(x to 3u) to Rational(-1, 9), - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(-11, 160), - mapOf(x to 6u) to Rational(3, 5), - mapOf(x to 2u, y to 1u) to Rational(-9, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 9), - mapOf(x to 4u, y to 1u) to Rational(-11, 12), - mapOf(x to 5u, y to 1u) to Rational(-1, 60), - mapOf(x to 6u, y to 1u) to Rational(-3, 10), - mapOf(x to 2u, y to 2u) to Rational(-5, 3), - mapOf(x to 3u, y to 2u) to Rational(-4, 15), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(1, 35), - mapOf(x to 6u, y to 2u) to Rational(-1, 60), - mapOf(x to 2u, y to 3u) to Rational(3, 14), - mapOf(x to 3u, y to 3u) to Rational(1, 3), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(x to 5u, y to 3u) to Rational(3, 40), - mapOf(x to 6u, y to 3u) to Rational(1, 54), - mapOf(x to 2u, y to 4u) to Rational(-9, 8), - mapOf(x to 3u, y to 4u) to Rational(-5, 3), - mapOf(x to 4u, y to 4u) to Rational(-7, 12), - mapOf(x to 5u, y to 4u) to Rational(1, 140), - mapOf(x to 6u, y to 4u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 12a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u, y to 1u) to Rational(-6, 8), - mapOf(x to 2u, y to 1u) to Rational(-1, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 6), - mapOf(x to 4u, y to 1u) to Rational(-11, 32), - mapOf(x to 5u, y to 1u) to Rational(18, 5), - mapOf(x to 1u, y to 2u) to Rational(-9, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 6), - mapOf(x to 3u, y to 2u) to Rational(-11, 6), - mapOf(x to 4u, y to 2u) to Rational(-1, 24), - mapOf(x to 5u, y to 2u) to Rational(-9, 10), - mapOf(x to 1u, y to 3u) to Rational(-10, 9), - mapOf(x to 2u, y to 3u) to Rational(-4, 15), - mapOf(x to 3u, y to 3u) to Rational(-1, 72), - mapOf(x to 4u, y to 3u) to Rational(1, 21), - mapOf(x to 5u, y to 3u) to Rational(-1, 30), - mapOf(x to 1u, y to 4u) to Rational(3, 28), - mapOf(x to 2u, y to 4u) to Rational(1, 4), - mapOf(x to 3u, y to 4u) to Rational(-1, 6), - mapOf(x to 4u, y to 4u) to Rational(3, 32), - mapOf(x to 5u, y to 4u) to Rational(1, 36), - mapOf(x to 1u, y to 5u) to Rational(-9, 20), - mapOf(x to 2u, y to 5u) to Rational(-1, 1), - mapOf(x to 3u, y to 5u) to Rational(-7, 15), - mapOf(x to 4u, y to 5u) to Rational(1, 140), - mapOf(x to 5u, y to 5u) to Rational(1, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 12b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(-3, 8), - mapOf(x to 1u, y to 2u) to Rational(-1, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 4), - mapOf(x to 3u, y to 2u) to Rational(-11, 16), - mapOf(x to 4u, y to 2u) to Rational(9, 1), - mapOf(y to 3u) to Rational(-1, 1), - mapOf(x to 1u, y to 3u) to Rational(1, 9), - mapOf(x to 2u, y to 3u) to Rational(-11, 6), - mapOf(x to 3u, y to 3u) to Rational(-1, 18), - mapOf(x to 4u, y to 3u) to Rational(-9, 6), - mapOf(y to 4u) to Rational(-5, 18), - mapOf(x to 1u, y to 4u) to Rational(-2, 15), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(1, 21), - mapOf(x to 4u, y to 4u) to Rational(-1, 24), - mapOf(y to 5u) to Rational(3, 140), - mapOf(x to 1u, y to 5u) to Rational(1, 10), - mapOf(x to 2u, y to 5u) to Rational(-1, 10), - mapOf(x to 3u, y to 5u) to Rational(3, 40), - mapOf(x to 4u, y to 5u) to Rational(1, 36), - mapOf(y to 6u) to Rational(-3, 40), - mapOf(x to 1u, y to 6u) to Rational(-1, 3), - mapOf(x to 2u, y to 6u) to Rational(-7, 30), - mapOf(x to 3u, y to 6u) to Rational(1, 210), - mapOf(x to 4u, y to 6u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(-11, 8), - mapOf(x to 4u) to Rational(18, 1), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(-1, 3), - mapOf(x to 4u, y to 1u) to Rational(-18, 2), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(3, 7), - mapOf(x to 1u, y to 3u) to Rational(16, 8), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(-18, 8), - mapOf(x to 1u, y to 4u) to Rational(-10, 1), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 12c" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(x to 5u) to Rational(0), - mapOf(x to 6u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 6u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(1, 35), - mapOf(x to 6u, y to 2u) to Rational(-1, 60), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(-1, 6), - mapOf(x to 5u, y to 3u) to Rational(3, 40), - mapOf(x to 6u, y to 3u) to Rational(1, 54), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(-7, 12), - mapOf(x to 5u, y to 4u) to Rational(1, 140), - mapOf(x to 6u, y to 4u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 13a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(x to 5u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(-1, 72), - mapOf(x to 4u, y to 3u) to Rational(1, 21), - mapOf(x to 5u, y to 3u) to Rational(-1, 30), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(-1, 6), - mapOf(x to 4u, y to 4u) to Rational(3, 32), - mapOf(x to 5u, y to 4u) to Rational(1, 36), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(0), - mapOf(x to 3u, y to 5u) to Rational(-7, 15), - mapOf(x to 4u, y to 5u) to Rational(1, 140), - mapOf(x to 5u, y to 5u) to Rational(1, 5), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 13b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(0), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(1, 21), - mapOf(x to 4u, y to 4u) to Rational(-1, 24), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(-1, 10), - mapOf(x to 3u, y to 5u) to Rational(3, 40), - mapOf(x to 4u, y to 5u) to Rational(1, 36), - mapOf(y to 6u) to Rational(0), - mapOf(x to 1u, y to 6u) to Rational(0), - mapOf(x to 2u, y to 6u) to Rational(-7, 30), - mapOf(x to 3u, y to 6u) to Rational(1, 210), - mapOf(x to 4u, y to 6u) to Rational(1, 6), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(0), - mapOf(x to 1u) to Rational(0), - mapOf(x to 2u) to Rational(0), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(0), - mapOf(x to 1u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(0), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(4, 7), - mapOf(x to 4u, y to 2u) to Rational(-4, 8), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(-16, 8), - mapOf(x to 3u, y to 3u) to Rational(12, 8), - mapOf(x to 4u, y to 3u) to Rational(5, 9), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(-14, 2), - mapOf(x to 3u, y to 4u) to Rational(1, 7), - mapOf(x to 4u, y to 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 13c" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 2u) to Rational(-3, 8), - mapOf(x to 3u) to Rational(-1, 9), - mapOf(x to 4u) to Rational(1, 24), - mapOf(x to 5u) to Rational(0), - mapOf(x to 6u) to Rational(0), - mapOf(x to 2u, y to 1u) to Rational(-9, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 9), - mapOf(x to 4u, y to 1u) to Rational(-11, 12), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 6u, y to 1u) to Rational(0), - mapOf(x to 2u, y to 2u) to Rational(-5, 3), - mapOf(x to 3u, y to 2u) to Rational(-4, 15), - mapOf(x to 4u, y to 2u) to Rational(-1, 96), - mapOf(x to 5u, y to 2u) to Rational(0), - mapOf(x to 6u, y to 2u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(x to 5u, y to 3u) to Rational(0), - mapOf(x to 6u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(x to 5u, y to 4u) to Rational(0), - mapOf(x to 6u, y to 4u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 2u)), - "test 14a" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(x to 1u, y to 1u) to Rational(-6, 8), - mapOf(x to 2u, y to 1u) to Rational(-1, 3), - mapOf(x to 3u, y to 1u) to Rational(1, 6), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(x to 5u, y to 1u) to Rational(0), - mapOf(x to 1u, y to 2u) to Rational(-9, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 6), - mapOf(x to 3u, y to 2u) to Rational(-11, 6), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(x to 5u, y to 2u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(-10, 9), - mapOf(x to 2u, y to 3u) to Rational(-4, 15), - mapOf(x to 3u, y to 3u) to Rational(-1, 72), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(x to 5u, y to 3u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(x to 5u, y to 4u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(0), - mapOf(x to 3u, y to 5u) to Rational(0), - mapOf(x to 4u, y to 5u) to Rational(0), - mapOf(x to 5u, y to 5u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(x to 1u, y to 1u)), - "test 14b" - ) - assertEquals( - LabeledPolynomialAsIs( - mapOf(y to 2u) to Rational(-3, 8), - mapOf(x to 1u, y to 2u) to Rational(-1, 3), - mapOf(x to 2u, y to 2u) to Rational(1, 4), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(-1, 1), - mapOf(x to 1u, y to 3u) to Rational(1, 9), - mapOf(x to 2u, y to 3u) to Rational(-11, 6), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(-5, 18), - mapOf(x to 1u, y to 4u) to Rational(-2, 15), - mapOf(x to 2u, y to 4u) to Rational(-1, 96), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - mapOf(y to 5u) to Rational(0), - mapOf(x to 1u, y to 5u) to Rational(0), - mapOf(x to 2u, y to 5u) to Rational(0), - mapOf(x to 3u, y to 5u) to Rational(0), - mapOf(x to 4u, y to 5u) to Rational(0), - mapOf(y to 6u) to Rational(0), - mapOf(x to 1u, y to 6u) to Rational(0), - mapOf(x to 2u, y to 6u) to Rational(0), - mapOf(x to 3u, y to 6u) to Rational(0), - mapOf(x to 4u, y to 6u) to Rational(0), - ), - LabeledPolynomialAsIs( - mapOf() to Rational(-6, 8), - mapOf(x to 1u) to Rational(-2, 3), - mapOf(x to 2u) to Rational(1, 2), - mapOf(x to 3u) to Rational(0), - mapOf(x to 4u) to Rational(0), - mapOf(y to 1u) to Rational(-18, 3), - mapOf(x to 1u, y to 1u) to Rational(2, 3), - mapOf(x to 2u, y to 1u) to Rational(-11, 1), - mapOf(x to 3u, y to 1u) to Rational(0), - mapOf(x to 4u, y to 1u) to Rational(0), - mapOf(y to 2u) to Rational(-10, 3), - mapOf(x to 1u, y to 2u) to Rational(-8, 5), - mapOf(x to 2u, y to 2u) to Rational(-1, 8), - mapOf(x to 3u, y to 2u) to Rational(0), - mapOf(x to 4u, y to 2u) to Rational(0), - mapOf(y to 3u) to Rational(0), - mapOf(x to 1u, y to 3u) to Rational(0), - mapOf(x to 2u, y to 3u) to Rational(0), - mapOf(x to 3u, y to 3u) to Rational(0), - mapOf(x to 4u, y to 3u) to Rational(0), - mapOf(y to 4u) to Rational(0), - mapOf(x to 1u, y to 4u) to Rational(0), - mapOf(x to 2u, y to 4u) to Rational(0), - mapOf(x to 3u, y to 4u) to Rational(0), - mapOf(x to 4u, y to 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(y to 2u)), - "test 14c" - ) - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialTest.kt deleted file mode 100644 index e7d8dfd8c..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialTest.kt +++ /dev/null @@ -1,544 +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:Suppress("LocalVariableName") - -package space.kscience.kmath.functions - -import space.kscience.kmath.functions.testUtils.IntModuloRing -import space.kscience.kmath.functions.testUtils.ListPolynomial -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import kotlin.test.* - - -class ListPolynomialTest { - @Test - fun test_Polynomial_Int_plus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) + -3, - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)) + 2, - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(-2)) + 2, - "test 3" - ) - val polynomial_4 = ListPolynomial() - assertSame( - polynomial_4, - polynomial_4 + 0, - "test 4" - ) - val polynomial_5 = ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)) - assertSame( - polynomial_5, - polynomial_5 + 0, - "test 5" - ) - assertEquals( - ListPolynomial(Rational(-1), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)) + 1, - "test 6" - ) - assertEquals( - ListPolynomial(Rational(-1)), - ListPolynomial(Rational(-2)) + 1, - "test 7" - ) - assertEquals( - ListPolynomial(Rational(2)), - ListPolynomial() + 2, - "test 8" - ) - } - } - @Test - fun test_Polynomial_Int_minus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(32, 9), Rational(-8, 9), Rational(-8, 7)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) - -3, - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(2), Rational(0), Rational(0), Rational(0)) - 2, - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(2)) - 2, - "test 3" - ) - val polynomial_4 = ListPolynomial() - assertSame( - polynomial_4, - polynomial_4 - 0, - "test 4" - ) - val polynomial_5 = ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)) - assertEquals( - polynomial_5, - polynomial_5 - 0, - "test 5" - ) - assertEquals( - ListPolynomial(Rational(1), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(2), Rational(0), Rational(0), Rational(0)) - 1, - "test 6" - ) - assertEquals( - ListPolynomial(Rational(1)), - ListPolynomial(Rational(2)) - 1, - "test 7" - ) - assertEquals( - ListPolynomial(Rational(-2)), - ListPolynomial() - 2, - "test 8" - ) - } - } - @Test - fun test_Polynomial_Int_times() { - IntModuloRing(35).listPolynomialSpace { - assertEquals( - ListPolynomial(34, 2, 1, 20, 2), - ListPolynomial(22, 26, 13, 15, 26) * 27, - "test 1" - ) - assertEquals( - ListPolynomial(0, 0, 0, 0, 0), - ListPolynomial(7, 0, 49, 21, 14) * 15, - "test 2" - ) - val polynomial = ListPolynomial(22, 26, 13, 15, 26) - assertSame( - zero, - polynomial * 0, - "test 3" - ) - assertSame( - polynomial, - polynomial * 1, - "test 4" - ) - } - } - @Test - fun test_Int_Polynomial_plus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)), - -3 + ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - 2 + ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - 2 + ListPolynomial(Rational(-2)), - "test 3" - ) - val polynomial_4 = ListPolynomial() - assertSame( - polynomial_4, - 0 + polynomial_4, - "test 4" - ) - val polynomial_5 = ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)) - assertSame( - polynomial_5, - 0 + polynomial_5, - "test 5" - ) - assertEquals( - ListPolynomial(Rational(-1), Rational(0), Rational(0), Rational(0)), - 1 + ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(-1)), - 1 + ListPolynomial(Rational(-2)), - "test 7" - ) - assertEquals( - ListPolynomial(Rational(2)), - 2 + ListPolynomial(), - "test 8" - ) - } - } - @Test - fun test_Int_Polynomial_minus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(32, 9), Rational(-8, 9), Rational(-8, 7)), - 3 - ListPolynomial(Rational(-5, 9), Rational(8, 9), Rational(8, 7)), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - -2 - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - -2 - ListPolynomial(Rational(-2)), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(-32, 9), Rational(-8, -9), Rational(8, 7)), - 0 - ListPolynomial(Rational(32, 9), Rational(-8, 9), Rational(-8, 7)), - "test 4" - ) - assertEquals( - ListPolynomial(), - 0 - ListPolynomial(), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(1), Rational(0), Rational(0), Rational(0)), - -1 - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(1)), - -1 - ListPolynomial(Rational(-2)), - "test 7" - ) - assertEquals( - ListPolynomial(Rational(-2)), - -2 - ListPolynomial(), - "test 8" - ) - } - } - @Test - fun test_Int_Polynomial_times() { - IntModuloRing(35).listPolynomialSpace { - assertEquals( - ListPolynomial(34, 2, 1, 20, 2), - 27 * ListPolynomial(22, 26, 13, 15, 26), - "test 1" - ) - assertEquals( - ListPolynomial(0, 0, 0, 0, 0), - 15 * ListPolynomial(7, 0, 49, 21, 14), - "test 2" - ) - val polynomial = ListPolynomial(22, 26, 13, 15, 26) - assertSame( - zero, - 0 * polynomial, - "test 3" - ) - assertSame( - polynomial, - 1 * polynomial, - "test 4" - ) - } - } - @Test - fun test_Polynomial_Constant_plus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) + Rational(-3), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)) + Rational(2), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(-2)) + Rational(2), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial() + Rational(0), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(-1), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)) + Rational(1), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(-1)), - ListPolynomial(Rational(-2)) + Rational(1), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(2)), - ListPolynomial() + Rational(2), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_minus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(32, 9), Rational(-8, 9), Rational(-8, 7)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) - Rational(-3), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(2), Rational(0), Rational(0), Rational(0)) - Rational(2), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(2)) - Rational(2), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial() - Rational(0), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(1), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(2), Rational(0), Rational(0), Rational(0)) - Rational(1), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(1)), - ListPolynomial(Rational(2)) - Rational(1), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(-2)), - ListPolynomial() - Rational(2), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_times() { - IntModuloRing(35).listPolynomialSpace { - assertEquals( - ListPolynomial(34, 2, 1, 20, 2), - ListPolynomial(22, 26, 13, 15, 26) * 27.asConstant(), - "test 1" - ) - assertEquals( - ListPolynomial(0, 0, 0, 0, 0), - ListPolynomial(7, 0, 49, 21, 14) * 15.asConstant(), - "test 2" - ) - } - } - @Test - fun test_Constant_Polynomial_plus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(-22, 9), Rational(-8, 9), Rational(-8, 7)), - Rational(-3) + ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - Rational(2) + ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - Rational(2) + ListPolynomial(Rational(-2)), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0)), - Rational(0) + ListPolynomial(), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(-1), Rational(0), Rational(0), Rational(0)), - Rational(1) + ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(-1)), - Rational(1) + ListPolynomial(Rational(-2)), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(2)), - Rational(2) + ListPolynomial(), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_minus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(32, 9), Rational(-8, 9), Rational(-8, 7)), - Rational(3) - ListPolynomial(Rational(-5, 9), Rational(8, 9), Rational(8, 7)), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0)), - Rational(-2) - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0)), - Rational(-2) - ListPolynomial(Rational(-2)), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0)), - Rational(0) - ListPolynomial(), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(1), Rational(0), Rational(0), Rational(0)), - Rational(-1) - ListPolynomial(Rational(-2), Rational(0), Rational(0), Rational(0)), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(1)), - Rational(-1) - ListPolynomial(Rational(-2)), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(-2)), - Rational(-2) - ListPolynomial(), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_times() { - IntModuloRing(35).listPolynomialSpace { - assertEquals( - ListPolynomial(34, 2, 1, 20, 2), - 27 * ListPolynomial(22, 26, 13, 15, 26), - "test 1" - ) - assertEquals( - ListPolynomial(0, 0, 0, 0, 0), - 15 * ListPolynomial(7, 0, 49, 21, 14), - "test 2" - ) - } - } - @Test - fun test_Polynomial_unaryMinus() { - RationalField.listPolynomialSpace { - assertEquals( - ListPolynomial(Rational(-5, 9), Rational(8, 9), Rational(8, 7)), - -ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(-5, 9), Rational(8, 9), Rational(8, 7), Rational(0), Rational(0)), - -ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7), Rational(0), Rational(0)), - "test 2" - ) - } - } - @Test - fun test_Polynomial_Polynomial_plus() { - RationalField.listPolynomialSpace { - // (5/9 - 8/9 x - 8/7 x^2) + (-5/7 + 5/1 x + 5/8 x^2) ?= -10/63 + 37/9 x - 29/56 x^2 - assertEquals( - ListPolynomial(Rational(-10, 63), Rational(37, 9), Rational(-29, 56)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) + - ListPolynomial(Rational(-5, 7), Rational(5, 1), Rational(5, 8)), - "test 1" - ) - // (-2/9 - 8/3 x) + (0 + 9/4 x + 2/4 x^2) ?= -2/9 - 5/12 x + 2/4 x^2 - assertEquals( - ListPolynomial(Rational(-2, 9), Rational(-5, 12), Rational(2, 4)), - ListPolynomial(Rational(-2, 9), Rational(-8, 3)) + - ListPolynomial(Rational(0), Rational(9, 4), Rational(2, 4)), - "test 2" - ) - // (-4/7 - 2/6 x + 0 x^2 + 0 x^3) + (-6/3 - 7/2 x + 2/3 x^2) ?= -18/7 - 23/6 x + 2/3 x^2 - assertEquals( - ListPolynomial(Rational(-18, 7), Rational(-23, 6), Rational(2, 3), Rational(0)), - ListPolynomial(Rational(-4, 7), Rational(-2, 6), Rational(0), Rational(0)) + - ListPolynomial(Rational(-6, 3), Rational(-7, 2), Rational(2, 3)), - "test 3" - ) - // (-2/4 - 6/9 x - 4/9 x^2) + (2/4 + 6/9 x + 4/9 x^2) ?= 0 - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2, 4), Rational(-6, 9), Rational(-4, 9)) + - ListPolynomial(Rational(2, 4), Rational(6, 9), Rational(4, 9)), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_minus() { - RationalField.listPolynomialSpace { - // (5/9 - 8/9 x - 8/7 x^2) - (-5/7 + 5/1 x + 5/8 x^2) ?= 80/63 - 53/9 x - 99/56 x^2 - assertEquals( - ListPolynomial(Rational(80, 63), Rational(-53, 9), Rational(-99, 56)), - ListPolynomial(Rational(5, 9), Rational(-8, 9), Rational(-8, 7)) - - ListPolynomial(Rational(-5, 7), Rational(5, 1), Rational(5, 8)), - "test 1" - ) - // (-2/9 - 8/3 x) - (0 + 9/4 x + 2/4 x^2) ?= -2/9 - 59/12 x - 2/4 x^2 - assertEquals( - ListPolynomial(Rational(-2, 9), Rational(-59, 12), Rational(-2, 4)), - ListPolynomial(Rational(-2, 9), Rational(-8, 3)) - - ListPolynomial(Rational(0), Rational(9, 4), Rational(2, 4)), - "test 2" - ) - // (-4/7 - 2/6 x + 0 x^2 + 0 x^3) - (-6/3 - 7/2 x + 2/3 x^2) ?= 10/7 + 19/6 x - 2/3 x^2 - assertEquals( - ListPolynomial(Rational(10, 7), Rational(19, 6), Rational(-2, 3), Rational(0)), - ListPolynomial(Rational(-4, 7), Rational(-2, 6), Rational(0), Rational(0)) - - ListPolynomial(Rational(-6, 3), Rational(-7, 2), Rational(2, 3)), - "test 3" - ) - // (-2/4 - 6/9 x - 4/9 x^2) - (-2/4 - 6/9 x - 4/9 x^2) ?= 0 - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(-2, 4), Rational(-6, 9), Rational(-4, 9)) - - ListPolynomial(Rational(-2, 4), Rational(-6, 9), Rational(-4, 9)), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_times() { - IntModuloRing(35).listPolynomialSpace { - // (1 + x + x^2) * (1 - x + x^2) ?= 1 + x^2 + x^4 - assertEquals( - ListPolynomial(1, 0, 1, 0, 1), - ListPolynomial(1, -1, 1) * ListPolynomial(1, 1, 1), - "test 1" - ) - // Spoiler: 5 * 7 = 0 - assertEquals( - ListPolynomial(0, 0, 0, 0, 0), - ListPolynomial(5, -25, 10) * ListPolynomial(21, 14, -7), - "test 2" - ) - } - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialUtilTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialUtilTest.kt deleted file mode 100644 index 339643d02..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/ListPolynomialUtilTest.kt +++ /dev/null @@ -1,982 +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.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.functions.testUtils.assertFailsWithTypeAndMessage -import kotlin.test.Ignore -import kotlin.test.Test -import kotlin.test.assertEquals - - -@OptIn(UnstableKMathAPI::class) -class ListPolynomialUtilTest { - @Test - fun test_Polynomial_substitute_Double() { - assertEquals( - 0.0, - ListPolynomial(1.0, -2.0, 1.0).substitute(1.0), - 0.001, - "test 1" - ) - assertEquals( - 0.0, - ListPolynomial(1.0, -2.0, 1.0).substitute(1.0), - 0.001, - "test 1" - ) - assertEquals( - 1.1931904761904761, - ListPolynomial(0.625, 2.6666666666666665, 0.5714285714285714, 1.5).substitute(0.2), - 0.001, - "test 2" - ) - assertEquals( - 0.5681904761904762, - ListPolynomial(0.0, 2.6666666666666665, 0.5714285714285714, 1.5).substitute(0.2), - 0.001, - "test 3" - ) - assertEquals( - 1.1811904761904761, - ListPolynomial(0.625, 2.6666666666666665, 0.5714285714285714, 0.0).substitute(0.2), - 0.001, - "test 4" - ) - assertEquals( - 1.1703333333333332, - ListPolynomial(0.625, 2.6666666666666665, 0.0, 1.5).substitute(0.2), - 0.001, - "test 5" - ) - } - @Test - fun test_Polynomial_substitute_Constant() { - assertEquals( - Rational(0), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).substitute(RationalField, Rational(1)), - "test 1" - ) - assertEquals( - Rational(25057, 21000), - ListPolynomial(Rational(5, 8), Rational(8, 3), Rational(4, 7), Rational(3, 2)) - .substitute(RationalField, Rational(1, 5)), - "test 2" - ) - assertEquals( - Rational(2983, 5250), - ListPolynomial(Rational(0), Rational(8, 3), Rational(4, 7), Rational(3, 2)) - .substitute(RationalField, Rational(1, 5)), - "test 3" - ) - assertEquals( - Rational(4961, 4200), - ListPolynomial(Rational(5, 8), Rational(8, 3), Rational(4, 7), Rational(0)) - .substitute(RationalField, Rational(1, 5)), - "test 4" - ) - assertEquals( - Rational(3511, 3000), - ListPolynomial(Rational(5, 8), Rational(8, 3), Rational(0), Rational(3, 2)) - .substitute(RationalField, Rational(1, 5)), - "test 5" - ) - } - @Test - fun test_Polynomial_substitute_Polynomial() { - assertEquals( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).substitute(RationalField, ListPolynomial(Rational(1))), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(709, 378), Rational(155, 252), Rational(19, 525), Rational(2, 875)), - ListPolynomial(Rational(1, 7), Rational(9, 4), Rational(1, 3), Rational(2, 7)) - .substitute(RationalField, ListPolynomial(Rational(6, 9), Rational(1, 5))), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(655, 378), Rational(155, 252), Rational(19, 525), Rational(2, 875)), - ListPolynomial(Rational(0), Rational(9, 4), Rational(1, 3), Rational(2, 7)) - .substitute(RationalField, ListPolynomial(Rational(6, 9), Rational(1, 5))), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(677, 378), Rational(97, 180), Rational(1, 75), Rational(0)), - ListPolynomial(Rational(1, 7), Rational(9, 4), Rational(1, 3), Rational(0)) - .substitute(RationalField, ListPolynomial(Rational(6, 9), Rational(1, 5))), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(653, 378), Rational(221, 420), Rational(4, 175), Rational(2, 875)), - ListPolynomial(Rational(1, 7), Rational(9, 4), Rational(0), Rational(2, 7)) - .substitute(RationalField, ListPolynomial(Rational(6, 9), Rational(1, 5))), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(89, 54), Rational(0), Rational(0), Rational(0)), - ListPolynomial(Rational(0), Rational(9, 4), Rational(1, 3), Rational(0)) - .substitute(RationalField, ListPolynomial(Rational(6, 9), Rational(0))), - "test 6" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_Polynomial_substitute_RationalFunction() { - assertEquals( - ListRationalFunction(ListPolynomial(Rational(0)), ListPolynomial(Rational(1))), - ListPolynomial(Rational(1), Rational(-2), Rational(1)) - .substitute(RationalField, ListRationalFunction(ListPolynomial(Rational(1)), ListPolynomial(Rational(1)))), - "test 1" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(66349, 243), - Rational(-17873, 405), - Rational(173533, 3780), - Rational(-91141, 567), - Rational(5773909, 105840), - Rational(-23243, 630), - Rational(1573, 27) - ), - ListPolynomial( - Rational(169, 81), - Rational(-130, 27), - Rational(115, 18), - Rational(-797, 54), - Rational(1985, 144), - Rational(-55, 6), - Rational(121, 9) - ) - ), - ListPolynomial( - Rational(13, 3), - Rational(-9, 5), - Rational(5, 5) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(15, 1), - Rational(6, 9), - Rational(-3, 7) - ), - ListPolynomial( - Rational(-13, 9), - Rational(10, 6), - Rational(-10, 8), - Rational(11, 3) - ) - ) - ), - "test 2" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(0, 1), - Rational(0, 1), - Rational(-14, 9), - Rational(31, 14), - Rational(-5077, 980), - Rational(99, 35) - ), - ListPolynomial( - Rational(0, 1), - Rational(0, 1), - Rational(25, 9), - Rational(-25, 6), - Rational(1985, 144), - Rational(-55, 6), - Rational(121, 9) - ) - ), - ListPolynomial( - Rational(0), - Rational(-9, 5), - Rational(5, 5) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(0), - Rational(6, 9), - Rational(-3, 7) - ), - ListPolynomial( - Rational(0), - Rational(10, 6), - Rational(-10, 8), - Rational(11, 3) - ) - ) - ), - "test 3" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(-898, 27), - Rational(271, 45), - Rational(-65, 12) , - Rational(0), - Rational(0), - Rational(0), - Rational(0) - ), - ListPolynomial( - Rational(-13, 9), - Rational(5, 3), - Rational(-5, 4), - Rational(0), - Rational(0), - Rational(0), - Rational(0) - ) - ), - ListPolynomial( - Rational(13, 3), - Rational(-9, 5), - Rational(0) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(15, 1), - Rational(6, 9), - Rational(0) - ), - ListPolynomial( - Rational(-13, 9), - Rational(10, 6), - Rational(-10, 8), - Rational(0) - ) - ) - ), - "test 4" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(56872, 243), - Rational(0, 1), - Rational(-90, 7), - Rational(-3718, 81), - Rational(9, 49), - Rational(0, 1), - Rational(1573, 27) - ), - ListPolynomial( - Rational(169, 81), - Rational(0, 1), - Rational(0, 1), - Rational(-286, 27), - Rational(0, 1), - Rational(0, 1), - Rational(121, 9) - ) - ), - ListPolynomial( - Rational(13, 3), - Rational(0), - Rational(5, 5) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(15, 1), - Rational(0), - Rational(-3, 7) - ), - ListPolynomial( - Rational(-13, 9), - Rational(0), - Rational(0), - Rational(11, 3) - ) - ) - ), - "test 5" - ) - } - @Test - fun test_RationalFunction_substitute_Double() { - assertEquals( - 0.0, - ListRationalFunction( - ListPolynomial(1.0, -2.0, 1.0), - ListPolynomial(-6.302012278484357, 5.831971885376948, -9.271604788393432, 5.494387848015814, -3.7187384450880785) - ).substitute(1.0), - 0.001, - "test 1" - ) - assertEquals( - 2.693702616649797, - ListRationalFunction( - ListPolynomial(-5.848840571263625, -1.660411278951134, -3.793740946372443, -9.624569269490076), - ListPolynomial(-2.9680680215311073, -1.862973627119981, 4.776550592888336, -2.7320154512368466) - ).substitute(-7.53452770353279), - 0.001, - "test 2" - ) - assertEquals( - 2.692226268901378, - ListRationalFunction( - ListPolynomial(0.0, -1.660411278951134, -3.793740946372443, -9.624569269490076), - ListPolynomial(0.0, -1.862973627119981, 4.776550592888336, -2.7320154512368466) - ).substitute(-7.53452770353279), - 0.001, - "test 3" - ) - assertEquals( - -0.7394904842099175, - ListRationalFunction( - ListPolynomial(-5.848840571263625, -1.660411278951134, -3.793740946372443, 0.0), - ListPolynomial(-2.9680680215311073, -1.862973627119981, 4.776550592888336, 0.0) - ).substitute(-7.53452770353279), - 0.001, - "test 4" - ) - assertEquals( - 3.526835209398159, - ListRationalFunction( - ListPolynomial(-5.848840571263625, 0.0, 0.0, -9.624569269490076), - ListPolynomial(-2.9680680215311073, 0.0, 0.0, -2.7320154512368466) - ).substitute(-7.53452770353279), - 0.001, - "test 5" - ) - } - @Test - fun test_RationalFunction_substitute_Constant() { - assertEquals( - Rational(0), - ListRationalFunction( - ListPolynomial(Rational(1), Rational(-2), Rational(1)), - ListPolynomial(Rational(1)), - ).substitute(RationalField, Rational(1)), - "test 1" - ) - assertEquals( - Rational(1149615, 61306), - ListRationalFunction( - ListPolynomial(Rational(17, 7), Rational(18, 3), Rational(18, 8), Rational(9, 1)), - ListPolynomial(Rational(11, 9), Rational(-6, 5), Rational(-12, 7), Rational(2, 1)), - ).substitute(RationalField, Rational(-7, 8)), - "test 2" - ) - assertEquals( - Rational(3495, 586), - ListRationalFunction( - ListPolynomial(Rational(0), Rational(18, 3), Rational(18, 8), Rational(9, 1)), - ListPolynomial(Rational(0), Rational(-6, 5), Rational(-12, 7), Rational(2, 1)), - ).substitute(RationalField, Rational(-7, 8)), - "test 3" - ) - assertEquals( - Rational(-88605, 77392), - ListRationalFunction( - ListPolynomial(Rational(17, 7), Rational(18, 3), Rational(18, 8), Rational(0)), - ListPolynomial(Rational(11, 9), Rational(-6, 5), Rational(-12, 7), Rational(0)), - ).substitute(RationalField, Rational(-7, 8)), - "test 4" - ) - assertEquals( - Rational(116145, 3794), - ListRationalFunction( - ListPolynomial(Rational(17, 7), Rational(0), Rational(0), Rational(9, 1)), - ListPolynomial(Rational(11, 9), Rational(0), Rational(0), Rational(2, 1)), - ).substitute(RationalField, Rational(-7, 8)), - "test 5" - ) - } - @Test - fun test_RationalFunction_substitute_Polynomial() { - assertEquals( - ListRationalFunction( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(1)) - ), - ListRationalFunction( - ListPolynomial(Rational(1), Rational(-2), Rational(1)), - ListPolynomial(Rational(1)), - ).substitute(RationalField, ListPolynomial(Rational(1))), - "test 1" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(-283303, 36), - Rational(-23593, 24), - Rational(368713, 192), - Rational(1455, 8), - Rational(-272171, 1536), - Rational(-2149, 192), - Rational(469, 64), - Rational(11, 48), - Rational(-11, 96) - ), - ListPolynomial( - Rational(5797, 12), - Rational(595, 16), - Rational(-5285, 72), - Rational(-745, 192), - Rational(1105, 288), - Rational(5, 48), - Rational(-5, 72) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(2, 9), - Rational(11, 3), - Rational(-9, 4), - Rational(-6, 1), - Rational(-11, 6) - ), - ListPolynomial( - Rational(-2, 3), - Rational(-15, 4), - Rational(5, 9), - Rational(-5, 9) - ) - ).substitute(RationalField, - ListPolynomial( - Rational(-9, 1), - Rational(-1, 4), - Rational(2, 4) - ) - ), - "test 2" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(0, 1), - Rational(-11, 12), - Rational(325, 192), - Rational(21, 32), - Rational(-1739, 1536), - Rational(227, 192), - Rational(-59, 64), - Rational(11, 48), - Rational(-11, 96) - ), - ListPolynomial( - Rational(0, 1), - Rational(15, 16), - Rational(-265, 144), - Rational(-25, 192), - Rational(25, 288), - Rational(5, 48), - Rational(-5, 72) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(0, 9), - Rational(11, 3), - Rational(-9, 4), - Rational(-6, 1), - Rational(-11, 6) - ), - ListPolynomial( - Rational(0, 3), - Rational(-15, 4), - Rational(5, 9), - Rational(-5, 9) - ) - ).substitute(RationalField, - ListPolynomial( - Rational(0, 1), - Rational(-1, 4), - Rational(2, 4) - ) - ), - "test 3" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(149723, 36), - Rational(8483, 24), - Rational(639, 64), - Rational(3, 32), - Rational(0), - Rational(0), - Rational(0), - Rational(0), - Rational(0) - ), - ListPolynomial( - Rational(937, 12), - Rational(55, 16), - Rational(5, 144), - Rational(0), - Rational(0), - Rational(0), - Rational(0) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(2, 9), - Rational(11, 3), - Rational(-9, 4), - Rational(-6, 1), - Rational(0) - ), - ListPolynomial( - Rational(-2, 3), - Rational(-15, 4), - Rational(5, 9), - Rational(0) - ) - ).substitute(RationalField, - ListPolynomial( - Rational(-9, 1), - Rational(-1, 4), - Rational(0) - ) - ), - "test 4" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(-216509, 18), - Rational(0, 1), - Rational(2673, 1), - Rational(0, 1), - Rational(-891, 4), - Rational(0, 1), - Rational(33, 4), - Rational(0, 1), - Rational(-11, 96) - ), - ListPolynomial( - Rational(1213, 3), - Rational(0, 1), - Rational(-135, 2), - Rational(0, 1), - Rational(15, 4), - Rational(0, 1), - Rational(-5, 72) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(2, 9), - Rational(0), - Rational(0), - Rational(0), - Rational(-11, 6) - ), - ListPolynomial( - Rational(-2, 3), - Rational(0), - Rational(0), - Rational(-5, 9) - ) - ).substitute(RationalField, - ListPolynomial( - Rational(-9, 1), - Rational(0), - Rational(2, 4) - ) - ), - "test 5" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_RationalFunction_substitute_RationalFunction() { - assertEquals( - ListRationalFunction( - ListPolynomial(Rational(0)), - ListPolynomial(Rational(1)) - ), - ListRationalFunction( - ListPolynomial(Rational(1), Rational(-2), Rational(1)), - ListPolynomial(Rational(1)) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial(Rational(1)), - ListPolynomial(Rational(1)) - ) - ), - "test 1" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(130087, 3888), - Rational(-2866333, 65610), - Rational(-5076229, 97200), - Rational(222136997, 3280500), - Rational(754719329, 20995200), - Rational(-12010283, 324000), - Rational(-2011967, 172800), - Rational(18607, 2880), - Rational(4705, 4096) - ), - ListPolynomial( - Rational(-143820355, 3779136), - Rational(73886869, 1574640), - Rational(1440175193, 15746400), - Rational(-5308968857, 52488000), - Rational(-186910083731, 2099520000), - Rational(125043463, 1555200), - Rational(5299123, 388800), - Rational(-213757, 15360), - Rational(1380785, 147456) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(1, 1), - Rational(-10, 5), - Rational(18, 8), - Rational(-8, 8) - ), - ListPolynomial( - Rational(-14, 8), - Rational(-14, 8), - Rational(-19, 6), - Rational(14, 3), - Rational(8, 9) - ) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(14, 9), - Rational(-2, 5), - Rational(-14, 7) - ), - ListPolynomial( - Rational(-6, 4), - Rational(5, 9), - Rational(1, 8) - ) - ) - ), - "test 2" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(5173, 18225), - Rational(904291, 364500), - Rational(283127, 43200), - Rational(37189, 5760), - Rational(147, 128) - ), - ListPolynomial( - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(-163589, 911250), - Rational(-881831, 291600), - Rational(-10722229, 777600), - Rational(-640921, 46080), - Rational(86303, 9216) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(0), - Rational(-10, 5), - Rational(18, 8), - Rational(-8, 8) - ), - ListPolynomial( - Rational(0), - Rational(-14, 8), - Rational(-19, 6), - Rational(14, 3), - Rational(8, 9) - ) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(0), - Rational(-2, 5), - Rational(-14, 7) - ), - ListPolynomial( - Rational(0), - Rational(5, 9), - Rational(1, 8) - ) - ) - ), - "test 3" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(445, 16), - Rational(-2011, 54), - Rational(1359199, 72900), - Rational(-135733, 32805), - Rational(2254, 6561), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1) - ), - ListPolynomial( - Rational(-2018387, 46656), - Rational(82316437, 1574640), - Rational(-9335047, 393660), - Rational(15765889, 3280500), - Rational(-242089, 656100), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1), - Rational(0, 1) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(1, 1), - Rational(-10, 5), - Rational(18, 8), - Rational(0) - ), - ListPolynomial( - Rational(-14, 8), - Rational(-14, 8), - Rational(-19, 6), - Rational(14, 3), - Rational(0) - ) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(14, 9), - Rational(-2, 5), - Rational(0) - ), - ListPolynomial( - Rational(-6, 4), - Rational(5, 9), - Rational(0) - ) - ) - ), - "test 4" - ) - assertEquals( - ListRationalFunction( - ListPolynomial( - Rational(41635, 3888), - Rational(0, 1), - Rational(-279187, 11664), - Rational(0, 1), - Rational(103769, 3456), - Rational(0, 1), - Rational(-11017, 768), - Rational(0, 1), - Rational(4097, 4096) - ), - ListPolynomial( - Rational(-13811791, 3779136), - Rational(0, 1), - Rational(-9999395, 419904), - Rational(0, 1), - Rational(6376601, 124416), - Rational(0, 1), - Rational(-3668315, 82944), - Rational(0, 1), - Rational(2097089, 147456) - ) - ), - ListRationalFunction( - ListPolynomial( - Rational(1, 1), - Rational(0), - Rational(0), - Rational(-8, 8) - ), - ListPolynomial( - Rational(-14, 8), - Rational(0), - Rational(0), - Rational(0), - Rational(8, 9) - ) - ).substitute(RationalField, - ListRationalFunction( - ListPolynomial( - Rational(14, 9), - Rational(0), - Rational(-14, 7) - ), - ListPolynomial( - Rational(-6, 4), - Rational(0), - Rational(1, 8) - ) - ) - ), - "test 5" - ) - } - @Test - fun test_Polynomial_derivative() { - assertEquals( - ListPolynomial(Rational(-2), Rational(2)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).derivative(RationalField), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(-8, 3), Rational(8, 9), Rational(15, 7), Rational(-20, 9)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).derivative(RationalField), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(8, 9), Rational(15, 7), Rational(-20, 9)), - ListPolynomial(Rational(0), Rational(0), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).derivative(RationalField), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(-8, 3), Rational(8, 9), Rational(15, 7), Rational(0)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(0)).derivative(RationalField), - "test 4" - ) - } - @Test - fun test_Polynomial_nthDerivative() { - assertEquals( - ListPolynomial(Rational(-2), Rational(2)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, 1), - "test 1" - ) - assertFailsWithTypeAndMessage( - "Order of derivative must be non-negative", - "test2" - ) { - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, -1) - } - assertEquals( - ListPolynomial(Rational(1), Rational(-2), Rational(1)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, 0), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(2)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, 2), - "test 4" - ) - assertEquals( - ListPolynomial(), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, 3), - "test 5" - ) - assertEquals( - ListPolynomial(), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthDerivative(RationalField, 4), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(8, 9), Rational(30, 7), Rational(-20, 3)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).nthDerivative(RationalField, 2), - "test 7" - ) - assertEquals( - ListPolynomial(Rational(8, 9), Rational(30, 7), Rational(-20, 3)), - ListPolynomial(Rational(0), Rational(0), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).nthDerivative(RationalField, 2), - "test 8" - ) - assertEquals( - ListPolynomial(Rational(8, 9), Rational(30, 7), Rational(0)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(0)).nthDerivative(RationalField, 2), - "test 9" - ) - } - @Test - fun test_Polynomial_antiderivative() { - assertEquals( - ListPolynomial(Rational(0), Rational(1), Rational(-1), Rational(1, 3)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).antiderivative(RationalField), - "test 1" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(1, 5), Rational(-4, 3), Rational(4, 27), Rational(5, 28), Rational(-1, 9)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).antiderivative(RationalField), - "test 2" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(4, 27), Rational(5, 28), Rational(-1, 9)), - ListPolynomial(Rational(0), Rational(0), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).antiderivative(RationalField), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(1, 5), Rational(-4, 3), Rational(4, 27), Rational(5, 28), Rational(0)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(0)).antiderivative(RationalField), - "test 4" - ) - } - @Test - fun test_Polynomial_nthAntiderivative() { - assertEquals( - ListPolynomial(Rational(0), Rational(1), Rational(-1), Rational(1, 3)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, 1), - "test 1" - ) - assertFailsWithTypeAndMessage( - "Order of antiderivative must be non-negative", - "test2" - ) { - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, -1) - } - assertEquals( - ListPolynomial(Rational(1), Rational(-2), Rational(1)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, 0), - "test 3" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(1, 2), Rational(-1, 3), Rational(1, 12)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, 2), - "test 4" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(1, 6), Rational(-1, 12), Rational(1, 60)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, 3), - "test 5" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0), Rational(1, 24), Rational(-1, 60), Rational(1, 360)), - ListPolynomial(Rational(1), Rational(-2), Rational(1)).nthAntiderivative(RationalField, 4), - "test 6" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(1, 10), Rational(-4, 9), Rational(1, 27), Rational(1, 28), Rational(-1, 54)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).nthAntiderivative(RationalField, 2), - "test 7" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(0), Rational(0), Rational(1, 27), Rational(1, 28), Rational(-1, 54)), - ListPolynomial(Rational(0), Rational(0), Rational(4, 9), Rational(5, 7), Rational(-5, 9)).nthAntiderivative(RationalField, 2), - "test 8" - ) - assertEquals( - ListPolynomial(Rational(0), Rational(0), Rational(1, 10), Rational(-4, 9), Rational(1, 27), Rational(1, 28), Rational(0)), - ListPolynomial(Rational(1, 5), Rational(-8, 3), Rational(4, 9), Rational(5, 7), Rational(0)).nthAntiderivative(RationalField, 2), - "test 9" - ) - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedConstructorsTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedConstructorsTest.kt deleted file mode 100644 index 1815749ce..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedConstructorsTest.kt +++ /dev/null @@ -1,123 +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.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.algebra -import space.kscience.kmath.operations.invoke -import kotlin.test.Test -import kotlin.test.assertEquals - - -class NumberedConstructorsTest { - @Test - @UnstableKMathAPI - fun testDSL1() { - assertEquals( - NumberedPolynomialAsIs( - listOf(2u, 0u, 3u) to 5, - listOf(0u, 1u) to -6, - ), - Int.algebra.numberedPolynomialSpace { - NumberedPolynomialDSL1 { - 5 { 0 pow 2u; 2 pow 3u } - (-6) { 1 pow 1u } - } - }, - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to -1, - ), - Int.algebra.numberedPolynomialSpace { - NumberedPolynomialDSL1 { - 5 { } - (-6) { } - } - }, - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to -1, - ), - Int.algebra.numberedPolynomialSpace { - NumberedPolynomialDSL1 { - 5 { 0 pow 1u; 0 pow 1u } - (-6) { 0 pow 2u } - } - }, - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to -1, - ), - Int.algebra.numberedPolynomialSpace { - NumberedPolynomialDSL1 { - 5 { 0 pow 1u; 0 pow 1u } - (-6) { 0 pow 2u; 2 pow 0u } - } - }, - "test 3" - ) - } - @Test - @UnstableKMathAPI - fun testFabric() { - assertEquals( - NumberedPolynomialAsIs( - listOf(2u, 0u, 3u) to 5, - listOf(0u, 1u) to -6, - ), - Int.algebra { - NumberedPolynomial( - listOf(2u, 0u, 3u) to 5, - listOf(0u, 1u) to -6, - ) - }, - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u, 0u, 3u) to 5, - listOf(0u, 1u) to -6, - ), - Int.algebra { - NumberedPolynomial( - listOf(2u, 0u, 3u, 0u) to 5, - listOf(0u, 1u, 0u, 0u) to -6, - ) - }, - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to -1, - ), - Int.algebra { - NumberedPolynomial( - listOf(0u) to 5, - listOf(0u, 0u) to -6, - ) - }, - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0, - ), - Int.algebra { - NumberedPolynomial( - listOf(0u) to 5, - listOf(0u, 0u) to -5, - ) - }, - "test 4" - ) - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialTest.kt deleted file mode 100644 index ec2e34520..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialTest.kt +++ /dev/null @@ -1,1740 +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:Suppress("LocalVariableName") - -package space.kscience.kmath.functions - -import space.kscience.kmath.functions.testUtils.IntModuloRing -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.functions.testUtils.m -import space.kscience.kmath.functions.testUtils.o -import kotlin.test.Test -import kotlin.test.assertEquals -import kotlin.test.assertSame -import kotlin.test.fail - - -class NumberedPolynomialTest { - @Test - fun test_Polynomial_Int_plus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + -3, - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + -3, - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + -3, - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ) + -3, - "test 4" - ) - val polynomial_5 = NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - polynomial_5 + 0, - "test 5" - ) - val polynomial_6 = NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - polynomial_6 + 0, - "test 6" - ) - val polynomial_7 = NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - polynomial_7 + 0, - "test 7" - ) - } - } - @Test - fun test_Polynomial_Int_minus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - 3, - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - 3, - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - 3, - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ) - 3, - "test 4" - ) - val polynomial_5 = NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - polynomial_5 - 0, - "test 5" - ) - val polynomial_6 = NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - polynomial_6 - 0, - "test 6" - ) - val polynomial_7 = NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - polynomial_7 - 0, - "test 7" - ) - } - } - @Test - fun test_Polynomial_Int_times() { - IntModuloRing(35).numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to m(34), - listOf(3u) to m(2), - listOf(0u, 1u) to m(1), - listOf(1u) to m(20), - listOf(0u, 0u, 2u) to m(2), - ), - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) * 27, - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - NumberedPolynomial( - listOf() to m(7), - listOf(3u) to m(0), - listOf(0u, 1u) to m(49), - listOf(1u) to m(21), - listOf(0u, 0u, 2u) to m(14), - ) * 15, - "test 2" - ) - val polynomial = NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) - assertSame( - zero, - polynomial * 0, - "test 3" - ) - assertSame( - polynomial, - polynomial * 1, - "test 4" - ) - } - } - @Test - fun test_Int_Polynomial_plus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - -3 + NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - -3 + NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - -3 + NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - -3 + NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - "test 4" - ) - val polynomial_5 = NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_5, - 0 + polynomial_5, - "test 5" - ) - val polynomial_6 = NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_6, - 0 + polynomial_6, - "test 6" - ) - val polynomial_7 = NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - assertSame( - polynomial_7, - 0 + polynomial_7, - "test 7" - ) - } - } - @Test - fun test_Int_Polynomial_minus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(22, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 3 - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(3, 1), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 3 - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 3 - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - 3 - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(22, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 0 - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 0 - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - NumberedPolynomial( - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - 0 - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Int_Polynomial_times() { - IntModuloRing(35).numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to m(34), - listOf(3u) to m(2), - listOf(0u, 1u) to m(1), - listOf(1u) to m(20), - listOf(0u, 0u, 2u) to m(2), - ), - 27 * NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - 15 * NumberedPolynomial( - listOf() to m(7), - listOf(3u) to m(0), - listOf(0u, 1u) to m(49), - listOf(1u) to m(21), - listOf(0u, 0u, 2u) to m(14), - ), - "test 2" - ) - val polynomial = NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) - assertSame( - zero, - 0 * polynomial, - "test 3" - ) - assertSame( - polynomial, - 1 * polynomial, - "test 4" - ) - } - } - @Test - fun test_Polynomial_Constant_plus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(-3), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ) + Rational(-3), - "test 4" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(0), - "test 5" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(0), - "test 6" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) + Rational(0), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_minus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(3), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(3), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(3), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ) - Rational(3), - "test 4" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(0), - "test 5" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(0), - "test 6" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ) - Rational(0), - "test 7" - ) - } - } - @Test - fun test_Polynomial_Constant_times() { - IntModuloRing(35).numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to m(34), - listOf(3u) to m(2), - listOf(0u, 1u) to m(1), - listOf(1u) to m(20), - listOf(0u, 0u, 2u) to m(2), - ), - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) * m(27), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - NumberedPolynomial( - listOf() to m(7), - listOf(3u) to m(0), - listOf(0u, 1u) to m(49), - listOf(1u) to m(21), - listOf(0u, 0u, 2u) to m(14), - ) * m(15), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) * m(0), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ) * m(1), - "test 4" - ) - } - } - @Test - fun test_Constant_Polynomial_plus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(-3) + NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-3, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(-3) + NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(-3) + NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - Rational(-3) + NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(0) + NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(0) + NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - Rational(0) + NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_minus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(22, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(3) - NumberedPolynomial( - listOf() to Rational(5, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(3, 1), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(3) - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 1), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(3) - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - Rational(3) - NumberedPolynomial( - listOf() to Rational(27, 9), - listOf(3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - ), - "test 4" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(22, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(0) - NumberedPolynomial( - listOf() to Rational(-22, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 5" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(0) - NumberedPolynomial( - listOf() to Rational(0, 9), - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 6" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(3u) to Rational(8, 9), - listOf(0u, 4u) to Rational(8, 7), - ), - Rational(0) - NumberedPolynomial( - listOf(3u) to Rational(-8, 9), - listOf(0u, 4u) to Rational(-8, 7), - ), - "test 7" - ) - } - } - @Test - fun test_Constant_Polynomial_times() { - IntModuloRing(35).numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to m(34), - listOf(3u) to m(2), - listOf(0u, 1u) to m(1), - listOf(1u) to m(20), - listOf(0u, 0u, 2u) to m(2), - ), - m(27) * NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - m(15) * NumberedPolynomial( - listOf() to m(7), - listOf(3u) to m(0), - listOf(0u, 1u) to m(49), - listOf(1u) to m(21), - listOf(0u, 0u, 2u) to m(14), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(0), - listOf(3u) to m(0), - listOf(0u, 1u) to m(0), - listOf(1u) to m(0), - listOf(0u, 0u, 2u) to m(0), - ), - m(0) * NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - m(1) * NumberedPolynomial( - listOf() to m(22), - listOf(3u) to m(26), - listOf(0u, 1u) to m(13), - listOf(1u) to m(15), - listOf(0u, 0u, 2u) to m(26), - ), - "test 4" - ) - } - } - @Test - fun test_Polynomial_unaryMinus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf(5u) to Rational(-5, 9), - listOf() to Rational(8, 9), - listOf(0u, 0u, 0u, 0u, 0u, 0u, 13u) to Rational(8, 7), - ), - -NumberedPolynomial( - listOf(5u) to Rational(5, 9), - listOf() to Rational(-8, 9), - listOf(0u, 0u, 0u, 0u, 0u, 0u, 13u) to Rational(-8, 7), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf(5u) to Rational(-5, 9), - listOf() to Rational(8, 9), - listOf(0u, 0u, 0u, 0u, 0u, 0u, 13u) to Rational(8, 7), - listOf(0u, 4u) to Rational(0), - listOf(5u) to Rational(0), - ), - -NumberedPolynomial( - listOf(5u) to Rational(5, 9), - listOf() to Rational(-8, 9), - listOf(0u, 0u, 0u, 0u, 0u, 0u, 13u) to Rational(-8, 7), - listOf(0u, 4u) to Rational(0), - listOf(5u) to Rational(0), - ), - "test 2" - ) - } - } - @Test - fun test_Polynomial_Polynomial_plus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(146, 63), - listOf(1u, 1u) to Rational(-3, 5), - listOf(2u, 1u) to Rational(61, 15), - listOf(0u, 2u) to Rational(157, 63), - listOf(1u, 2u) to Rational(-55, 21), - listOf(2u, 2u) to Rational(11, 24), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(-7, 7), - listOf(2u, 1u) to Rational(12, 5), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) + NumberedPolynomial( - listOf() to Rational(-20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(-20, 7), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(7, 9), - listOf(1u, 2u) to Rational(5, 7), - listOf(2u, 2u) to Rational(-2, 3), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(157, 63), - listOf(1u, 2u) to Rational(-55, 21), - listOf(2u, 2u) to Rational(11, 24), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) + NumberedPolynomial( - listOf() to Rational(-20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(-20, 7), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(7, 9), - listOf(1u, 2u) to Rational(5, 7), - listOf(2u, 2u) to Rational(-2, 3), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) + NumberedPolynomial( - listOf() to Rational(-20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(-20, 7), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(-7, 7), - listOf(2u, 1u) to Rational(12, 5), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) + NumberedPolynomial( - listOf() to Rational(-6, 4), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(-10, 6), - listOf(0u, 1u) to Rational(-17, 7), - listOf(1u, 1u) to Rational(7, 7), - listOf(2u, 1u) to Rational(-12, 5), - listOf(0u, 2u) to Rational(-12, 7), - listOf(1u, 2u) to Rational(10, 3), - listOf(2u, 2u) to Rational(-9, 8), - ), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_minus() { - RationalField.numberedPolynomialSpace { - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(146, 63), - listOf(1u, 1u) to Rational(-3, 5), - listOf(2u, 1u) to Rational(61, 15), - listOf(0u, 2u) to Rational(157, 63), - listOf(1u, 2u) to Rational(-55, 21), - listOf(2u, 2u) to Rational(11, 24), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(-7, 7), - listOf(2u, 1u) to Rational(12, 5), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) - NumberedPolynomial( - listOf() to Rational(20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(20, 7), - listOf(0u, 1u) to Rational(1, 9), - listOf(1u, 1u) to Rational(-2, 5), - listOf(2u, 1u) to Rational(-10, 6), - listOf(0u, 2u) to Rational(-7, 9), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(2, 3), - ), - "test 1" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(157, 63), - listOf(1u, 2u) to Rational(-55, 21), - listOf(2u, 2u) to Rational(11, 24), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) - NumberedPolynomial( - listOf() to Rational(20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(20, 7), - listOf(0u, 1u) to Rational(1, 9), - listOf(1u, 1u) to Rational(-2, 5), - listOf(2u, 1u) to Rational(-10, 6), - listOf(0u, 2u) to Rational(-7, 9), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(2, 3), - ), - "test 2" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(-17, 2), - listOf(1u) to Rational(-1, 3), - listOf(2u) to Rational(-25, 21), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(2, 5), - listOf(2u, 1u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) - NumberedPolynomial( - listOf() to Rational(20, 2), - listOf(1u) to Rational(0, 9), - listOf(2u) to Rational(20, 7), - listOf(0u, 1u) to Rational(1, 9), - listOf(1u, 1u) to Rational(-2, 5), - listOf(2u, 1u) to Rational(-10, 6), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - ), - "test 3" - ) - assertEquals( - NumberedPolynomial( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - ), - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(-7, 7), - listOf(2u, 1u) to Rational(12, 5), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ) - NumberedPolynomial( - listOf() to Rational(6, 4), - listOf(1u) to Rational(-2, 6), - listOf(2u) to Rational(10, 6), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(-7, 7), - listOf(2u, 1u) to Rational(12, 5), - listOf(0u, 2u) to Rational(12, 7), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(9, 8), - ), - "test 4" - ) - } - } - @Test - fun test_Polynomial_Polynomial_times() { - IntModuloRing(35).numberedPolynomialSpace { - // (p + q + r) * (p^2 + q^2 + r^2 - pq - pr - qr) = p^3 + q^3 + r^3 - 3pqr - assertEquals( - NumberedPolynomial( - listOf(3u) to m(1), - listOf(0u, 3u) to m(1), - listOf(0u, 0u, 3u) to m(1), - listOf(1u, 2u) to m(0), - listOf(0u, 1u, 2u) to m(0), - listOf(2u, 0u, 1u) to m(0), - listOf(1u, 0u, 2u) to m(0), - listOf(2u, 1u) to m(0), - listOf(0u, 2u, 1u) to m(0), - listOf(1u, 1u, 1u) to m(-3), - ), - NumberedPolynomial( - listOf(1u) to m(1), - listOf(0u, 1u) to m(1), - listOf(0u, 0u, 1u) to m(1), - ) * NumberedPolynomial( - listOf(2u) to m(1), - listOf(0u, 2u) to m(1), - listOf(0u, 0u, 2u) to m(1), - listOf(1u, 1u) to m(-1), - listOf(0u, 1u, 1u) to m(-1), - listOf(1u, 0u, 1u) to m(-1), - ), - "test 1" - ) - // Spoiler: 5 * 7 = 0 - assertEquals( - NumberedPolynomial( - listOf(2u) to m(0), - listOf(0u, 2u) to m(0), - listOf(0u, 0u, 2u) to m(0), - listOf(1u, 1u) to m(0), - listOf(0u, 1u, 1u) to m(0), - listOf(1u, 0u, 1u) to m(0), - ), - NumberedPolynomial( - listOf(1u) to m(5), - listOf(0u, 1u) to m(-25), - listOf(0u, 0u, 1u) to m(10), - ) * NumberedPolynomial( - listOf(1u) to m(21), - listOf(0u, 1u) to m(14), - listOf(0u, 0u, 1u) to m(-7), - ), - "test 2" - ) - } - } - @Test - fun test_lastVariable() { - RationalField.numberedPolynomialSpace { - assertEquals( - -1, - NumberedPolynomial().lastVariable, - "test 1" - ) - assertEquals( - -1, - NumberedPolynomial( - listOf() to o - ).lastVariable, - "test 2" - ) - assertEquals( - 2, - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).lastVariable, - "test 3" - ) - assertEquals( - 3, - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).also { println(it) }.lastVariable, - "test 4" - ) - assertEquals( - 2, - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).lastVariable, - "test 5" - ) - } - } - @Test - fun test_degree() { - RationalField.numberedPolynomialSpace { - assertEquals( - -1, - NumberedPolynomial().degree, - "test 1" - ) - assertEquals( - 0, - NumberedPolynomial( - listOf() to o - ).degree, - "test 2" - ) - assertEquals( - 6, - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).degree, - "test 3" - ) - assertEquals( - 4, - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).degree, - "test 4" - ) - assertEquals( - 3, - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).degree, - "test 5" - ) - assertEquals( - 4, - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ).degree, - "test 6" - ) - } - } - @Test - fun test_degrees() { - RationalField.numberedPolynomialSpace { - assertEquals( - listOf(), - NumberedPolynomial().degrees, - "test 1" - ) - assertEquals( - listOf(), - NumberedPolynomial( - listOf() to o - ).degrees, - "test 2" - ) - assertEquals( - listOf(1u, 2u, 3u), - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).degrees, - "test 3" - ) - assertEquals( - listOf(0u, 1u, 2u, 1u), - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).degrees, - "test 4" - ) - assertEquals( - listOf(2u, 1u, 1u), - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).degrees, - "test 5" - ) - assertEquals( - listOf(2u, 2u, 2u, 4u), - NumberedPolynomial( - listOf() to o, - listOf(1u, 2u) to o, - listOf(0u, 1u, 2u) to o, - listOf(2u, 0u, 1u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ).degrees, - "test 6" - ) - } - } - @Test - fun test_degreeBy() { - RationalField.numberedPolynomialSpace { - fun NumberedPolynomial.collectDegrees(limit: Int = lastVariable + 2): List = List(limit) { degreeBy(it) } - assertEquals( - listOf(0u), - NumberedPolynomial().collectDegrees(), - "test 1" - ) - assertEquals( - listOf(0u), - NumberedPolynomial( - listOf() to o - ).collectDegrees(), - "test 2" - ) - assertEquals( - listOf(1u, 2u, 3u, 0u), - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).collectDegrees(), - "test 3" - ) - assertEquals( - listOf(0u, 1u, 2u, 1u, 0u), - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).collectDegrees(), - "test 4" - ) - assertEquals( - listOf(2u, 1u, 1u, 0u), - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).collectDegrees(), - "test 5" - ) - assertEquals( - listOf(2u, 2u, 2u, 4u, 0u), - NumberedPolynomial( - listOf() to o, - listOf(1u, 2u) to o, - listOf(0u, 1u, 2u) to o, - listOf(2u, 0u, 1u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ).collectDegrees(), - "test 6" - ) - } - } - @Test - fun test_degreeBy_Collection() { - RationalField.numberedPolynomialSpace { - fun NumberedPolynomial.checkDegreeBy(message: String? = null) { - val lastVariable = lastVariable - val indexCollectionSequence: Sequence> = sequence { - val appearances = MutableList(lastVariable + 2) { 0 } - while (true) { - yield( - buildList { - for ((variable, count) in appearances.withIndex()) repeat(count) { add(variable) } - } - ) - val indexChange = appearances.indexOfFirst { it < 4 } - if (indexChange == -1) break - appearances[indexChange] += 1 - for (index in 0 until indexChange) appearances[index] = 0 - } - } - for (indexCollection in indexCollectionSequence) { - val expected = coefficients.keys.maxOfOrNull { degs -> degs.slice(indexCollection.distinct().filter { it in degs.indices }).sum() } ?: 0u - val actual = degreeBy(indexCollection) - if (actual != expected) - fail("${message ?: ""} Incorrect answer for variable collection $indexCollection: expected $expected, actual $actual") - } - } - NumberedPolynomial().checkDegreeBy("test 1") - NumberedPolynomial( - listOf() to o - ).checkDegreeBy("test 2") - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).checkDegreeBy("test 3") - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).checkDegreeBy("test 4") - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).checkDegreeBy("test 5") - NumberedPolynomial( - listOf() to o, - listOf(1u, 2u) to o, - listOf(0u, 1u, 2u) to o, - listOf(2u, 0u, 1u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ).checkDegreeBy("test 6") - } - } - @Test - fun test_countOfVariables() { - RationalField.numberedPolynomialSpace { - assertEquals( - 0, - NumberedPolynomial().countOfVariables, - "test 1" - ) - assertEquals( - 0, - NumberedPolynomial( - listOf() to o - ).countOfVariables, - "test 2" - ) - assertEquals( - 3, - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ).countOfVariables, - "test 3" - ) - assertEquals( - 3, - NumberedPolynomial( - listOf(0u, 1u, 2u, 1u, 0u) to o - ).countOfVariables, - "test 4" - ) - assertEquals( - 3, - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ).countOfVariables, - "test 5" - ) - assertEquals( - 4, - NumberedPolynomial( - listOf() to o, - listOf(1u, 2u) to o, - listOf(0u, 1u, 2u) to o, - listOf(2u, 0u, 1u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ).countOfVariables, - "test 6" - ) - } - } - @Test - fun test_RF_countOfVariables() { - RationalField.numberedRationalFunctionSpace { - assertEquals( - 0, - NumberedRationalFunction( - NumberedPolynomial() - ).countOfVariables, - "test 1" - ) - assertEquals( - 0, - NumberedRationalFunction( - NumberedPolynomial(), - NumberedPolynomial() - ).countOfVariables, - "test 2" - ) - assertEquals( - 0, - NumberedRationalFunction( - NumberedPolynomial( - listOf() to o - ) - ).countOfVariables, - "test 3" - ) - assertEquals( - 3, - NumberedRationalFunction( - NumberedPolynomial( - listOf(1u, 2u, 3u) to o - ) - ).countOfVariables, - "test 4" - ) - assertEquals( - 3, - NumberedRationalFunction( - NumberedPolynomial( - listOf(0u, 1u, 0u, 1u) to o - ), - NumberedPolynomial( - listOf(0u, 0u, 2u) to o - ) - ).countOfVariables, - "test 5" - ) - assertEquals( - 3, - NumberedRationalFunction( - NumberedPolynomial( - listOf() to o, - listOf(0u, 1u) to o, - listOf(2u, 0u, 1u) to o, - ) - ).countOfVariables, - "test 6" - ) - assertEquals( - 4, - NumberedRationalFunction( - NumberedPolynomial( - listOf() to o, - listOf(1u, 2u) to o, - listOf(2u, 0u, 1u) to o, - ), NumberedPolynomial( - listOf(0u, 1u, 2u) to o, - listOf(0u, 0u, 0u, 4u) to o, - ) - ).countOfVariables, - "test 7" - ) - } - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialUtilTest.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialUtilTest.kt deleted file mode 100644 index 82f1e561a..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/NumberedPolynomialUtilTest.kt +++ /dev/null @@ -1,12021 +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.functions - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.functions.testUtils.Rational -import space.kscience.kmath.functions.testUtils.RationalField -import space.kscience.kmath.functions.testUtils.assertFailsWithTypeAndMessage -import kotlin.test.Ignore -import kotlin.test.Test -import kotlin.test.assertEquals -import space.kscience.kmath.functions.testUtils.bufferOf -import space.kscience.kmath.functions.testUtils.assertEquals - - -class NumberedPolynomialUtilTest { - @Test - fun test_Polynomial_substitute_Double_Map() { - assertEquals( - NumberedPolynomialAsIs(emptyList() to 0.0), - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ).substitute(mapOf( - 0 to 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf()), - 0.001, - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 5 to 0.9211194782050933 - )), - 0.001, - "test 2'" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(0u, 1u) to 0.4561746111587508, - listOf(0u, 2u) to 0.2700930201481795, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 0 to 0.0 - )), - 0.001, - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(0u, 1u) to 0.4561746111587508, - listOf(0u, 2u) to 0.2700930201481795, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 0 to 0.0, - 5 to 0.9211194782050933 - )), - 0.001, - "test 3'" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.433510890645169, - listOf(1u) to 0.6264844682514724, - listOf(2u) to 0.8405727903771333, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 1 to 0.8400458576651112 - )), - 0.001, - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.433510890645169, - listOf(1u) to 0.6264844682514724, - listOf(2u) to 0.8405727903771333, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 1 to 0.8400458576651112, - 5 to 0.9211194782050933 - )), - 0.001, - "test 4'" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.934530767358133, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 0 to 0.4846192734143442, - 1 to 0.8400458576651112, - )), - 0.001, - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.934530767358133, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(mapOf( - 0 to 0.4846192734143442, - 1 to 0.8400458576651112, - 5 to 0.9211194782050933 - )), - 0.001, - "test 5'" - ) - } - @Test - fun test_Polynomial_substitute_Constant_Map() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, mapOf( - 0 to Rational(1) - )), - "test 1" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5%2C+y+%3D+12%2F9 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(143, 150) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to Rational(-2, 5), - 1 to Rational(12, 9), - )), - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(143, 150) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to Rational(-2, 5), - 1 to Rational(12, 9), - 5 to Rational(57, 179), - )), - "test 2'" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+y+%3D+12%2F9 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-67, 18), - listOf(1u) to Rational(-70, 9), - listOf(2u) to Rational(88, 9), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 1 to Rational(12, 9), - )), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-67, 18), - listOf(1u) to Rational(-70, 9), - listOf(2u) to Rational(88, 9), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 1 to Rational(12, 9), - 5 to Rational(57, 179), - )), - "test 3'" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-83, 50), - listOf(0u, 1u) to Rational(29, 25), - listOf(0u, 2u) to Rational(3, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to Rational(-2, 5), - )), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-83, 50), - listOf(0u, 1u) to Rational(29, 25), - listOf(0u, 2u) to Rational(3, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to Rational(-2, 5), - 5 to Rational(57, 179), - )), - "test 4'" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf()), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 5 to Rational(57, 179), - )), - "test 5'" - ) - // https://www.wolframalpha.com/input?i=%28%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2%29+p%5E8+where+x+%3D+q%2Fp%2C+y+%3D+x%5E3%2C+p+%3D+-2%2F5%2C+q+%3D+12%2F9 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(47639065216, 2562890625) - ), - NumberedPolynomialAsIs( - listOf(8u) to Rational(-3, 2), - listOf(7u, 1u) to Rational(8, 6), - listOf(6u, 2u) to Rational(14, 6), - listOf(5u, 3u) to Rational(-3, 1), - listOf(4u, 4u) to Rational(-19, 2), - listOf(3u, 5u) to Rational(9, 4), - listOf(2u, 6u) to Rational(5, 5), - listOf(1u, 7u) to Rational(18, 9), - listOf(0u, 8u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to Rational(-2, 5), - 1 to Rational(12, 9), - )), - "test 6" - ) - } - @Test - fun test_Polynomial_substitute_Polynomial_Map() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - )), - "test 1" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-5%2F1+s+%2B+2%2F8+t%2C+y+%3D+11%2F7+t - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(0u, 1u) to Rational(-92, 21), - listOf(0u, 2u) to Rational(-2627, 2352), - listOf(0u, 3u) to Rational(4565, 3136), - listOf(0u, 4u) to Rational(605, 1568), - listOf(1u) to Rational(-20, 3), - listOf(1u, 1u) to Rational(1445, 21), - listOf(1u, 2u) to Rational(-13145, 392), - listOf(1u, 3u) to Rational(-3025, 196), - listOf(2u) to Rational(175, 3), - listOf(2u, 1u) to Rational(2475, 28), - listOf(2u, 2u) to Rational(15125, 98), - listOf(3u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf(1u) to Rational(-5, 1), - listOf(0u, 1u) to Rational(2, 8), - ), - 1 to NumberedPolynomialAsIs( - listOf(1u) to Rational(0, 5), - listOf(0u, 1u) to Rational(11, 7), - ), - )), - "test 2" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = (-9/2 + 2/7 s + 9/1 s^2) + (13/1 + -1/8 s + 2/8 s^2) t + (19/4 + 15/7 s + -19/4 s^2) t^2 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(48583, 336), - listOf(2u) to Rational(-913477, 1568), - listOf(3u) to Rational(-967567, 672), - listOf(4u) to Rational(4722043, 1344), - listOf(5u) to Rational(8855, 2), - listOf(6u) to Rational(-311971, 32), - listOf(7u) to Rational(-17325, 4), - listOf(8u) to Rational(19845, 2), - listOf(0u, 1u) to Rational(-827, 4), - listOf(1u, 1u) to Rational(191927, 840), - listOf(2u, 1u) to Rational(9592627, 2352), - listOf(3u, 1u) to Rational(-105400711, 53760), - listOf(4u, 1u) to Rational(-10054101459, 439040), - listOf(5u, 1u) to Rational(2127351, 128), - listOf(6u, 1u) to Rational(116680973, 3136), - listOf(7u, 1u) to Rational(-220445, 7), - listOf(8u, 1u) to Rational(-2655, 4), - listOf(0u, 2u) to Rational(30567, 100), - listOf(1u, 2u) to Rational(-156284953, 39200), - listOf(2u, 2u) to Rational(-57661541711, 6585600), - listOf(3u, 2u) to Rational(131931579, 3136), - listOf(4u, 2u) to Rational(98818124791, 3512320), - listOf(5u, 2u) to Rational(-94458855053, 878080), - listOf(6u, 2u) to Rational(13937705305, 1229312), - listOf(7u, 2u) to Rational(335706887, 21952), - listOf(8u, 2u) to Rational(23549165, 1568), - listOf(0u, 3u) to Rational(111367, 1400), - listOf(1u, 3u) to Rational(4937369, 700), - listOf(2u, 3u) to Rational(-4449423711, 274400), - listOf(3u, 3u) to Rational(-351873325703, 4390400), - listOf(4u, 3u) to Rational(23495875029, 307328), - listOf(5u, 3u) to Rational(17576300919, 878080), - listOf(6u, 3u) to Rational(230316993, 12544), - listOf(7u, 3u) to Rational(-191130515, 21952), - listOf(8u, 3u) to Rational(332435, 392), - listOf(0u, 4u) to Rational(-275084, 1225), - listOf(1u, 4u) to Rational(-266774603, 137200), - listOf(2u, 4u) to Rational(2176279167121, 30732800), - listOf(3u, 4u) to Rational(10904913303, 2195200), - listOf(4u, 4u) to Rational(-10769286147, 2195200), - listOf(5u, 4u) to Rational(-26277119793, 439040), - listOf(6u, 4u) to Rational(25859735869, 6146560), - listOf(7u, 4u) to Rational(38906289, 2744), - listOf(8u, 4u) to Rational(-3072025, 392), - listOf(0u, 5u) to Rational(9573, 98), - listOf(1u, 5u) to Rational(-4154651399, 548800), - listOf(2u, 5u) to Rational(3446069019, 548800), - listOf(3u, 5u) to Rational(-7851500623, 137200), - listOf(4u, 5u) to Rational(-53205142903, 1920800), - listOf(5u, 5u) to Rational(-31953611, 3430), - listOf(6u, 5u) to Rational(1447380313, 109760), - listOf(7u, 5u) to Rational(764158625, 21952), - listOf(8u, 5u) to Rational(1153515, 784), - listOf(0u, 6u) to Rational(1722351, 7840), - listOf(1u, 6u) to Rational(-164554821, 109760), - listOf(2u, 6u) to Rational(-79096147243, 7683200), - listOf(3u, 6u) to Rational(-624721089, 15680), - listOf(4u, 6u) to Rational(11147305567, 548800), - listOf(5u, 6u) to Rational(8318333679, 109760), - listOf(6u, 6u) to Rational(32981871553, 1536640), - listOf(7u, 6u) to Rational(-225359619, 21952), - listOf(8u, 6u) to Rational(-3973995, 392), - listOf(0u, 7u) to Rational(67203, 784), - listOf(1u, 7u) to Rational(39281469, 54880), - listOf(2u, 7u) to Rational(70162551, 27440), - listOf(3u, 7u) to Rational(413630709, 54880), - listOf(4u, 7u) to Rational(4640410269, 192080), - listOf(5u, 7u) to Rational(802712247, 54880), - listOf(6u, 7u) to Rational(-473517603, 27440), - listOf(7u, 7u) to Rational(-17055459, 1568), - listOf(8u, 7u) to Rational(-12825, 14), - listOf(0u, 8u) to Rational(16245, 1568), - listOf(1u, 8u) to Rational(503253, 2744), - listOf(2u, 8u) to Rational(125292591, 96040), - listOf(3u, 8u) to Rational(12033171, 2744), - listOf(4u, 8u) to Rational(154352673, 27440), - listOf(5u, 8u) to Rational(-1302291, 392), - listOf(6u, 8u) to Rational(-20265741, 1960), - listOf(7u, 8u) to Rational(-26163, 56), - listOf(8u, 8u) to Rational(146205, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - 1 to NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - )), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(48583, 336), - listOf(2u) to Rational(-913477, 1568), - listOf(3u) to Rational(-967567, 672), - listOf(4u) to Rational(4722043, 1344), - listOf(5u) to Rational(8855, 2), - listOf(6u) to Rational(-311971, 32), - listOf(7u) to Rational(-17325, 4), - listOf(8u) to Rational(19845, 2), - listOf(0u, 1u) to Rational(-827, 4), - listOf(1u, 1u) to Rational(191927, 840), - listOf(2u, 1u) to Rational(9592627, 2352), - listOf(3u, 1u) to Rational(-105400711, 53760), - listOf(4u, 1u) to Rational(-10054101459, 439040), - listOf(5u, 1u) to Rational(2127351, 128), - listOf(6u, 1u) to Rational(116680973, 3136), - listOf(7u, 1u) to Rational(-220445, 7), - listOf(8u, 1u) to Rational(-2655, 4), - listOf(0u, 2u) to Rational(30567, 100), - listOf(1u, 2u) to Rational(-156284953, 39200), - listOf(2u, 2u) to Rational(-57661541711, 6585600), - listOf(3u, 2u) to Rational(131931579, 3136), - listOf(4u, 2u) to Rational(98818124791, 3512320), - listOf(5u, 2u) to Rational(-94458855053, 878080), - listOf(6u, 2u) to Rational(13937705305, 1229312), - listOf(7u, 2u) to Rational(335706887, 21952), - listOf(8u, 2u) to Rational(23549165, 1568), - listOf(0u, 3u) to Rational(111367, 1400), - listOf(1u, 3u) to Rational(4937369, 700), - listOf(2u, 3u) to Rational(-4449423711, 274400), - listOf(3u, 3u) to Rational(-351873325703, 4390400), - listOf(4u, 3u) to Rational(23495875029, 307328), - listOf(5u, 3u) to Rational(17576300919, 878080), - listOf(6u, 3u) to Rational(230316993, 12544), - listOf(7u, 3u) to Rational(-191130515, 21952), - listOf(8u, 3u) to Rational(332435, 392), - listOf(0u, 4u) to Rational(-275084, 1225), - listOf(1u, 4u) to Rational(-266774603, 137200), - listOf(2u, 4u) to Rational(2176279167121, 30732800), - listOf(3u, 4u) to Rational(10904913303, 2195200), - listOf(4u, 4u) to Rational(-10769286147, 2195200), - listOf(5u, 4u) to Rational(-26277119793, 439040), - listOf(6u, 4u) to Rational(25859735869, 6146560), - listOf(7u, 4u) to Rational(38906289, 2744), - listOf(8u, 4u) to Rational(-3072025, 392), - listOf(0u, 5u) to Rational(9573, 98), - listOf(1u, 5u) to Rational(-4154651399, 548800), - listOf(2u, 5u) to Rational(3446069019, 548800), - listOf(3u, 5u) to Rational(-7851500623, 137200), - listOf(4u, 5u) to Rational(-53205142903, 1920800), - listOf(5u, 5u) to Rational(-31953611, 3430), - listOf(6u, 5u) to Rational(1447380313, 109760), - listOf(7u, 5u) to Rational(764158625, 21952), - listOf(8u, 5u) to Rational(1153515, 784), - listOf(0u, 6u) to Rational(1722351, 7840), - listOf(1u, 6u) to Rational(-164554821, 109760), - listOf(2u, 6u) to Rational(-79096147243, 7683200), - listOf(3u, 6u) to Rational(-624721089, 15680), - listOf(4u, 6u) to Rational(11147305567, 548800), - listOf(5u, 6u) to Rational(8318333679, 109760), - listOf(6u, 6u) to Rational(32981871553, 1536640), - listOf(7u, 6u) to Rational(-225359619, 21952), - listOf(8u, 6u) to Rational(-3973995, 392), - listOf(0u, 7u) to Rational(67203, 784), - listOf(1u, 7u) to Rational(39281469, 54880), - listOf(2u, 7u) to Rational(70162551, 27440), - listOf(3u, 7u) to Rational(413630709, 54880), - listOf(4u, 7u) to Rational(4640410269, 192080), - listOf(5u, 7u) to Rational(802712247, 54880), - listOf(6u, 7u) to Rational(-473517603, 27440), - listOf(7u, 7u) to Rational(-17055459, 1568), - listOf(8u, 7u) to Rational(-12825, 14), - listOf(0u, 8u) to Rational(16245, 1568), - listOf(1u, 8u) to Rational(503253, 2744), - listOf(2u, 8u) to Rational(125292591, 96040), - listOf(3u, 8u) to Rational(12033171, 2744), - listOf(4u, 8u) to Rational(154352673, 27440), - listOf(5u, 8u) to Rational(-1302291, 392), - listOf(6u, 8u) to Rational(-20265741, 1960), - listOf(7u, 8u) to Rational(-26163, 56), - listOf(8u, 8u) to Rational(146205, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - 1 to NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-11, 3), - listOf(1u) to Rational(5, 2), - listOf(2u) to Rational(13, 7), - listOf(0u, 1u) to Rational(16, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(6, 1), - listOf(0u, 2u) to Rational(-14, 3), - listOf(1u, 2u) to Rational(-2, 7), - listOf(2u, 2u) to Rational(-10, 8), - ) - )), - "test 3'" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = s, y = (-9/2 + 2/7 s + 9/1 s^2) + (13/1 + -1/8 s + 2/8 s^2) t + (19/4 + 15/7 s + -19/4 s^2) t^2 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(6817, 84), - listOf(2u) to Rational(-21445, 294), - listOf(3u) to Rational(-12151, 49), - listOf(4u) to Rational(-17789, 196), - listOf(5u) to Rational(1224, 7), - listOf(6u) to Rational(405, 2), - listOf(0u, 1u) to Rational(-156), - listOf(1u, 1u) to Rational(-2440, 7), - listOf(2u, 1u) to Rational(-1571, 112), - listOf(3u, 1u) to Rational(107515, 224), - listOf(4u, 1u) to Rational(64965, 112), - listOf(5u, 1u) to Rational(209, 56), - listOf(6u, 1u) to Rational(45, 4), - listOf(0u, 2u) to Rational(112), - listOf(1u, 2u) to Rational(1449, 8), - listOf(2u, 2u) to Rational(1306309, 3136), - listOf(3u, 2u) to Rational(483207, 1568), - listOf(4u, 2u) to Rational(1978437, 6272), - listOf(5u, 2u) to Rational(-18231, 224), - listOf(6u, 2u) to Rational(-6835, 32), - listOf(0u, 3u) to Rational(247, 2), - listOf(1u, 3u) to Rational(33771, 112), - listOf(2u, 3u) to Rational(2073, 7), - listOf(3u, 3u) to Rational(-23463, 224), - listOf(4u, 3u) to Rational(-33825, 112), - listOf(5u, 3u) to Rational(201, 224), - listOf(6u, 3u) to Rational(-95, 16), - listOf(0u, 4u) to Rational(361, 16), - listOf(1u, 4u) to Rational(3667, 56), - listOf(2u, 4u) to Rational(88729, 1568), - listOf(3u, 4u) to Rational(-2476, 49), - listOf(4u, 4u) to Rational(-23419, 196), - listOf(5u, 4u) to Rational(-323, 56), - listOf(6u, 4u) to Rational(1805, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 1 to NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - )), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(6817, 84), - listOf(2u) to Rational(-21445, 294), - listOf(3u) to Rational(-12151, 49), - listOf(4u) to Rational(-17789, 196), - listOf(5u) to Rational(1224, 7), - listOf(6u) to Rational(405, 2), - listOf(0u, 1u) to Rational(-156), - listOf(1u, 1u) to Rational(-2440, 7), - listOf(2u, 1u) to Rational(-1571, 112), - listOf(3u, 1u) to Rational(107515, 224), - listOf(4u, 1u) to Rational(64965, 112), - listOf(5u, 1u) to Rational(209, 56), - listOf(6u, 1u) to Rational(45, 4), - listOf(0u, 2u) to Rational(112), - listOf(1u, 2u) to Rational(1449, 8), - listOf(2u, 2u) to Rational(1306309, 3136), - listOf(3u, 2u) to Rational(483207, 1568), - listOf(4u, 2u) to Rational(1978437, 6272), - listOf(5u, 2u) to Rational(-18231, 224), - listOf(6u, 2u) to Rational(-6835, 32), - listOf(0u, 3u) to Rational(247, 2), - listOf(1u, 3u) to Rational(33771, 112), - listOf(2u, 3u) to Rational(2073, 7), - listOf(3u, 3u) to Rational(-23463, 224), - listOf(4u, 3u) to Rational(-33825, 112), - listOf(5u, 3u) to Rational(201, 224), - listOf(6u, 3u) to Rational(-95, 16), - listOf(0u, 4u) to Rational(361, 16), - listOf(1u, 4u) to Rational(3667, 56), - listOf(2u, 4u) to Rational(88729, 1568), - listOf(3u, 4u) to Rational(-2476, 49), - listOf(4u, 4u) to Rational(-23419, 196), - listOf(5u, 4u) to Rational(-323, 56), - listOf(6u, 4u) to Rational(1805, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 1 to NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-11, 3), - listOf(1u) to Rational(5, 2), - listOf(2u) to Rational(13, 7), - listOf(0u, 1u) to Rational(16, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(6, 1), - listOf(0u, 2u) to Rational(-14, 3), - listOf(1u, 2u) to Rational(-2, 7), - listOf(2u, 2u) to Rational(-10, 8), - ) - )), - "test 4'" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = t - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(7, 3), - listOf(2u) to Rational(-35, 16), - listOf(3u) to Rational(-343, 6), - listOf(4u) to Rational(343, 3), - listOf(0u, 1u) to Rational(-19, 5), - listOf(1u, 1u) to Rational(-823, 120), - listOf(2u, 1u) to Rational(1232417, 6720), - listOf(3u, 1u) to Rational(-9863, 24), - listOf(4u, 1u) to Rational(385, 4), - listOf(0u, 2u) to Rational(2439, 350), - listOf(1u, 2u) to Rational(-5793, 40), - listOf(2u, 2u) to Rational(1172113, 3360), - listOf(3u, 2u) to Rational(-13531, 40), - listOf(4u, 2u) to Rational(2824, 7), - listOf(0u, 3u) to Rational(3417, 700), - listOf(1u, 3u) to Rational(1191, 200), - listOf(2u, 3u) to Rational(8383, 28), - listOf(3u, 3u) to Rational(-220279, 280), - listOf(4u, 3u) to Rational(49179, 196), - listOf(0u, 4u) to Rational(57, 35), - listOf(1u, 4u) to Rational(-33771, 700), - listOf(2u, 4u) to Rational(196279, 1225), - listOf(3u, 4u) to Rational(-32259, 140), - listOf(4u, 4u) to Rational(23868, 49), - listOf(0u, 5u) to Rational(333, 196), - listOf(1u, 5u) to Rational(-204, 35), - listOf(2u, 5u) to Rational(-307233, 2450), - listOf(3u, 5u) to Rational(-12492, 35), - listOf(4u, 5u) to Rational(4563, 28), - listOf(0u, 6u) to Rational(45, 98), - listOf(1u, 6u) to Rational(54, 7), - listOf(2u, 6u) to Rational(1809, 35), - listOf(3u, 6u) to Rational(162), - listOf(4u, 6u) to Rational(405, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - )), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(7, 3), - listOf(2u) to Rational(-35, 16), - listOf(3u) to Rational(-343, 6), - listOf(4u) to Rational(343, 3), - listOf(0u, 1u) to Rational(-19, 5), - listOf(1u, 1u) to Rational(-823, 120), - listOf(2u, 1u) to Rational(1232417, 6720), - listOf(3u, 1u) to Rational(-9863, 24), - listOf(4u, 1u) to Rational(385, 4), - listOf(0u, 2u) to Rational(2439, 350), - listOf(1u, 2u) to Rational(-5793, 40), - listOf(2u, 2u) to Rational(1172113, 3360), - listOf(3u, 2u) to Rational(-13531, 40), - listOf(4u, 2u) to Rational(2824, 7), - listOf(0u, 3u) to Rational(3417, 700), - listOf(1u, 3u) to Rational(1191, 200), - listOf(2u, 3u) to Rational(8383, 28), - listOf(3u, 3u) to Rational(-220279, 280), - listOf(4u, 3u) to Rational(49179, 196), - listOf(0u, 4u) to Rational(57, 35), - listOf(1u, 4u) to Rational(-33771, 700), - listOf(2u, 4u) to Rational(196279, 1225), - listOf(3u, 4u) to Rational(-32259, 140), - listOf(4u, 4u) to Rational(23868, 49), - listOf(0u, 5u) to Rational(333, 196), - listOf(1u, 5u) to Rational(-204, 35), - listOf(2u, 5u) to Rational(-307233, 2450), - listOf(3u, 5u) to Rational(-12492, 35), - listOf(4u, 5u) to Rational(4563, 28), - listOf(0u, 6u) to Rational(45, 98), - listOf(1u, 6u) to Rational(54, 7), - listOf(2u, 6u) to Rational(1809, 35), - listOf(3u, 6u) to Rational(162), - listOf(4u, 6u) to Rational(405, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-11, 3), - listOf(1u) to Rational(5, 2), - listOf(2u) to Rational(13, 7), - listOf(0u, 1u) to Rational(16, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(6, 1), - listOf(0u, 2u) to Rational(-14, 3), - listOf(1u, 2u) to Rational(-2, 7), - listOf(2u, 2u) to Rational(-10, 8), - ) - )), - "test 5'" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, mapOf( - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-11, 3), - listOf(1u) to Rational(5, 2), - listOf(2u) to Rational(13, 7), - listOf(0u, 1u) to Rational(16, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(6, 1), - listOf(0u, 2u) to Rational(-14, 3), - listOf(1u, 2u) to Rational(-2, 7), - listOf(2u, 2u) to Rational(-10, 8), - ) - )), - "test 6'" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_Polynomial_substitute_RationalFunction_Map() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(4u) to Rational(-194071, 4900), - listOf(3u, 1u) to Rational(394811, 225), - listOf(2u, 2u) to Rational(-444183161, 66150), - listOf(1u, 3u) to Rational(70537618, 59535), - listOf(0u, 4u) to Rational(9655504, 2835), - ), - NumberedPolynomialAsIs( - listOf(4u) to Rational(9, 1), - listOf(3u, 1u) to Rational(61, 1), - listOf(2u, 2u) to Rational(2137, 36), - listOf(1u, 3u) to Rational(-1342, 9), - listOf(0u, 4u) to Rational(484, 9), - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(17, 7), - listOf(0u, 1u) to Rational(-13, 1), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(-18, 6), - listOf(0u, 1u) to Rational(11, 6), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(18, 5), - listOf(0u, 1u) to Rational(-16, 3), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(-4, 1), - ) - ), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-6443599, 10000), - listOf(1u) to Rational(166251223, 210000), - listOf(2u) to Rational(-4606805099, 3528000), - listOf(3u) to Rational(51204379, 19600), - listOf(4u) to Rational(-529045460659, 277830000), - listOf(5u) to Rational(2630836709, 1488375), - listOf(6u) to Rational(-42675691369, 25004700), - listOf(7u) to Rational(495825223, 1250235), - listOf(8u) to Rational(-22531756, 1750329), - listOf(0u, 1u) to Rational(-2526552797, 420000), - listOf(1u, 1u) to Rational(31108840471, 2520000), - listOf(2u, 1u) to Rational(-4789740847, 1102500), - listOf(3u, 1u) to Rational(186594307807, 11340000), - listOf(4u, 1u) to Rational(-11677815943, 1488375), - listOf(5u, 1u) to Rational(-181118486447, 27783000), - listOf(6u, 1u) to Rational(-16123292162, 14586075), - listOf(7u, 1u) to Rational(-140339343808, 26254935), - listOf(8u, 1u) to Rational(4570171616, 5250987), - listOf(0u, 2u) to Rational(-181436530573, 10080000), - listOf(1u, 2u) to Rational(6700437957491, 105840000), - listOf(2u, 2u) to Rational(-3527267461, 1417500), - listOf(3u, 2u) to Rational(-38084563451, 5556600), - listOf(4u, 2u) to Rational(-565662040631, 13891500), - listOf(5u, 2u) to Rational(-35479071126397, 583443000), - listOf(6u, 2u) to Rational(-11717559078469, 525098700), - listOf(7u, 2u) to Rational(-2043385293517, 225042300), - listOf(8u, 2u) to Rational(-3644439630451, 551353635), - listOf(0u, 3u) to Rational(-1760423269, 126000), - listOf(1u, 3u) to Rational(310176758299, 2352000), - listOf(2u, 3u) to Rational(-907229584837, 21168000), - listOf(3u, 3u) to Rational(-16717135885963, 95256000), - listOf(4u, 3u) to Rational(-43762928025353, 333396000), - listOf(5u, 3u) to Rational(-328427480571607, 3000564000), - listOf(6u, 3u) to Rational(-7722675917197, 210039480), - listOf(7u, 3u) to Rational(1713350137019, 1225230300), - listOf(8u, 3u) to Rational(156695935643, 31505922), - listOf(0u, 4u) to Rational(18362364269, 1008000), - listOf(1u, 4u) to Rational(955674858553, 10584000), - listOf(2u, 4u) to Rational(-71937470607371, 444528000), - listOf(3u, 4u) to Rational(-34097985615163, 95256000), - listOf(4u, 4u) to Rational(-340736178775883, 2000376000), - listOf(5u, 4u) to Rational(-511324523441897, 10501974000), - listOf(6u, 4u) to Rational(-125375649409151, 8821658160), - listOf(7u, 4u) to Rational(-2813518533421, 1575296100), - listOf(8u, 4u) to Rational(-17044089109, 5250987), - listOf(0u, 5u) to Rational(600086461, 20160), - listOf(1u, 5u) to Rational(-18959931367, 423360), - listOf(2u, 5u) to Rational(-9178804929607, 44452800), - listOf(3u, 5u) to Rational(-1460114275979, 5334336), - listOf(4u, 5u) to Rational(-342533479090169, 4200789600), - listOf(5u, 5u) to Rational(20335453022963, 4200789600), - listOf(6u, 5u) to Rational(-21649775090197, 6301184400), - listOf(7u, 5u) to Rational(-197301716069, 131274675), - listOf(8u, 5u) to Rational(18711357470, 15752961), - listOf(0u, 6u) to Rational(621417991, 100800), - listOf(1u, 6u) to Rational(-159236792977, 2116800), - listOf(2u, 6u) to Rational(-6602528890883, 66679200), - listOf(3u, 6u) to Rational(-1086091664047, 19051200), - listOf(4u, 6u) to Rational(3769375009003, 1680315840), - listOf(5u, 6u) to Rational(-12920385574769, 1050197400), - listOf(6u, 6u) to Rational(-90219591809287, 6301184400), - listOf(7u, 6u) to Rational(656361553391, 1575296100), - listOf(8u, 6u) to Rational(757900793, 2250423), - listOf(0u, 7u) to Rational(-100770017, 15120), - listOf(1u, 7u) to Rational(-316364851, 17640), - listOf(2u, 7u) to Rational(-85118560057, 6667920), - listOf(3u, 7u) to Rational(6286563719, 416745), - listOf(4u, 7u) to Rational(26803885301, 1714608), - listOf(5u, 7u) to Rational(-13767154393, 4286520), - listOf(6u, 7u) to Rational(-3875138933, 1224720), - listOf(7u, 7u) to Rational(65193755, 333396), - listOf(8u, 7u) to Rational(90974351, 2500470), - listOf(0u, 8u) to Rational(-3182197, 1260), - listOf(1u, 8u) to Rational(24899923, 8820), - listOf(2u, 8u) to Rational(-19999556, 19845), - listOf(3u, 8u) to Rational(3276587, 3969), - listOf(4u, 8u) to Rational(13719549239, 5000940), - listOf(5u, 8u) to Rational(-961839938, 1250235), - listOf(6u, 8u) to Rational(-198184871, 833490), - listOf(7u, 8u) to Rational(230659711, 5000940), - listOf(8u, 8u) to Rational(292447, 35721) - ), - NumberedPolynomialAsIs( - listOf() to Rational(9, 100), - listOf(1u) to Rational(-21, 50), - listOf(2u) to Rational(293, 700), - listOf(3u) to Rational(29, 210), - listOf(4u) to Rational(3233, 8820), - listOf(5u) to Rational(-289, 441), - listOf(6u) to Rational(-1, 9), - listOf(7u) to Rational(-20, 441), - listOf(8u) to Rational(100, 441), - listOf(0u, 1u) to Rational(-57, 80), - listOf(1u, 1u) to Rational(-121, 400), - listOf(2u, 1u) to Rational(37117, 8400), - listOf(3u, 1u) to Rational(-4853, 3150), - listOf(4u, 1u) to Rational(1166203, 132300), - listOf(5u, 1u) to Rational(-2708, 567), - listOf(6u, 1u) to Rational(-287159, 416745), - listOf(7u, 1u) to Rational(-478204, 83349), - listOf(8u, 1u) to Rational(176320, 83349), - listOf(0u, 2u) to Rational(-6239, 6400), - listOf(1u, 2u) to Rational(264211, 11200), - listOf(2u, 2u) to Rational(-1591999, 100800), - listOf(3u, 2u) to Rational(12450091, 529200), - listOf(4u, 2u) to Rational(9230759, 226800), - listOf(5u, 2u) to Rational(18995554, 2083725), - listOf(6u, 2u) to Rational(136706258, 6251175), - listOf(7u, 2u) to Rational(-120907496, 3750705), - listOf(8u, 2u) to Rational(117200176, 15752961), - listOf(0u, 3u) to Rational(5653, 320), - listOf(1u, 3u) to Rational(-130853, 8400), - listOf(2u, 3u) to Rational(-20939327, 151200), - listOf(3u, 3u) to Rational(2566691, 25200), - listOf(4u, 3u) to Rational(-68441519, 476280), - listOf(5u, 3u) to Rational(2462904247, 12502350), - listOf(6u, 3u) to Rational(353667161, 18753525), - listOf(7u, 3u) to Rational(-1689134372, 26254935), - listOf(8u, 3u) to Rational(35084104, 2250423), - listOf(0u, 4u) to Rational(-3587, 300), - listOf(1u, 4u) to Rational(-10513243, 33600), - listOf(2u, 4u) to Rational(30766733, 176400), - listOf(3u, 4u) to Rational(-65680021, 198450), - listOf(4u, 4u) to Rational(-8108910547, 20003760), - listOf(5u, 4u) to Rational(2922125159, 6251175), - listOf(6u, 4u) to Rational(-4245279943, 131274675), - listOf(7u, 4u) to Rational(-371946872, 3750705), - listOf(8u, 4u) to Rational(61286752, 2250423), - listOf(0u, 5u) to Rational(-20477, 160), - listOf(1u, 5u) to Rational(215741, 1120), - listOf(2u, 5u) to Rational(30785843, 31752), - listOf(3u, 5u) to Rational(-357495959, 317520), - listOf(4u, 5u) to Rational(-1611242993, 10001880), - listOf(5u, 5u) to Rational(345925495, 500094), - listOf(6u, 5u) to Rational(-755948411, 3750705), - listOf(7u, 5u) to Rational(-108643496, 1250235), - listOf(8u, 5u) to Rational(1122512, 35721), - listOf(0u, 6u) to Rational(358037, 2880), - listOf(1u, 6u) to Rational(3895837, 3360), - listOf(2u, 6u) to Rational(359419201, 1270080), - listOf(3u, 6u) to Rational(-158522587, 105840), - listOf(4u, 6u) to Rational(10909002599, 20003760), - listOf(5u, 6u) to Rational(76846972, 138915), - listOf(6u, 6u) to Rational(-327696553, 1250235), - listOf(7u, 6u) to Rational(-1687328, 35721), - listOf(8u, 6u) to Rational(1016836, 35721), - listOf(0u, 7u) to Rational(658, 3), - listOf(1u, 7u) to Rational(48035, 168), - listOf(2u, 7u) to Rational(-5777875, 5292), - listOf(3u, 7u) to Rational(-7893899, 10584), - listOf(4u, 7u) to Rational(10191652, 11907), - listOf(5u, 7u) to Rational(2920121, 23814), - listOf(6u, 7u) to Rational(-2699780, 11907), - listOf(7u, 7u) to Rational(4556, 441), - listOf(8u, 7u) to Rational(3440, 189), - listOf(0u, 8u) to Rational(64, 1), - listOf(1u, 8u) to Rational(-808, 7), - listOf(2u, 8u) to Rational(-360895, 1764), - listOf(3u, 8u) to Rational(257657, 882), - listOf(4u, 8u) to Rational(3779917, 15876), - listOf(5u, 8u) to Rational(-610279, 3969), - listOf(6u, 8u) to Rational(-25091, 441), - listOf(7u, 8u) to Rational(9560, 567), - listOf(8u, 8u) to Rational(400, 81) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-6443599, 10000), - listOf(1u) to Rational(166251223, 210000), - listOf(2u) to Rational(-4606805099, 3528000), - listOf(3u) to Rational(51204379, 19600), - listOf(4u) to Rational(-529045460659, 277830000), - listOf(5u) to Rational(2630836709, 1488375), - listOf(6u) to Rational(-42675691369, 25004700), - listOf(7u) to Rational(495825223, 1250235), - listOf(8u) to Rational(-22531756, 1750329), - listOf(0u, 1u) to Rational(-2526552797, 420000), - listOf(1u, 1u) to Rational(31108840471, 2520000), - listOf(2u, 1u) to Rational(-4789740847, 1102500), - listOf(3u, 1u) to Rational(186594307807, 11340000), - listOf(4u, 1u) to Rational(-11677815943, 1488375), - listOf(5u, 1u) to Rational(-181118486447, 27783000), - listOf(6u, 1u) to Rational(-16123292162, 14586075), - listOf(7u, 1u) to Rational(-140339343808, 26254935), - listOf(8u, 1u) to Rational(4570171616, 5250987), - listOf(0u, 2u) to Rational(-181436530573, 10080000), - listOf(1u, 2u) to Rational(6700437957491, 105840000), - listOf(2u, 2u) to Rational(-3527267461, 1417500), - listOf(3u, 2u) to Rational(-38084563451, 5556600), - listOf(4u, 2u) to Rational(-565662040631, 13891500), - listOf(5u, 2u) to Rational(-35479071126397, 583443000), - listOf(6u, 2u) to Rational(-11717559078469, 525098700), - listOf(7u, 2u) to Rational(-2043385293517, 225042300), - listOf(8u, 2u) to Rational(-3644439630451, 551353635), - listOf(0u, 3u) to Rational(-1760423269, 126000), - listOf(1u, 3u) to Rational(310176758299, 2352000), - listOf(2u, 3u) to Rational(-907229584837, 21168000), - listOf(3u, 3u) to Rational(-16717135885963, 95256000), - listOf(4u, 3u) to Rational(-43762928025353, 333396000), - listOf(5u, 3u) to Rational(-328427480571607, 3000564000), - listOf(6u, 3u) to Rational(-7722675917197, 210039480), - listOf(7u, 3u) to Rational(1713350137019, 1225230300), - listOf(8u, 3u) to Rational(156695935643, 31505922), - listOf(0u, 4u) to Rational(18362364269, 1008000), - listOf(1u, 4u) to Rational(955674858553, 10584000), - listOf(2u, 4u) to Rational(-71937470607371, 444528000), - listOf(3u, 4u) to Rational(-34097985615163, 95256000), - listOf(4u, 4u) to Rational(-340736178775883, 2000376000), - listOf(5u, 4u) to Rational(-511324523441897, 10501974000), - listOf(6u, 4u) to Rational(-125375649409151, 8821658160), - listOf(7u, 4u) to Rational(-2813518533421, 1575296100), - listOf(8u, 4u) to Rational(-17044089109, 5250987), - listOf(0u, 5u) to Rational(600086461, 20160), - listOf(1u, 5u) to Rational(-18959931367, 423360), - listOf(2u, 5u) to Rational(-9178804929607, 44452800), - listOf(3u, 5u) to Rational(-1460114275979, 5334336), - listOf(4u, 5u) to Rational(-342533479090169, 4200789600), - listOf(5u, 5u) to Rational(20335453022963, 4200789600), - listOf(6u, 5u) to Rational(-21649775090197, 6301184400), - listOf(7u, 5u) to Rational(-197301716069, 131274675), - listOf(8u, 5u) to Rational(18711357470, 15752961), - listOf(0u, 6u) to Rational(621417991, 100800), - listOf(1u, 6u) to Rational(-159236792977, 2116800), - listOf(2u, 6u) to Rational(-6602528890883, 66679200), - listOf(3u, 6u) to Rational(-1086091664047, 19051200), - listOf(4u, 6u) to Rational(3769375009003, 1680315840), - listOf(5u, 6u) to Rational(-12920385574769, 1050197400), - listOf(6u, 6u) to Rational(-90219591809287, 6301184400), - listOf(7u, 6u) to Rational(656361553391, 1575296100), - listOf(8u, 6u) to Rational(757900793, 2250423), - listOf(0u, 7u) to Rational(-100770017, 15120), - listOf(1u, 7u) to Rational(-316364851, 17640), - listOf(2u, 7u) to Rational(-85118560057, 6667920), - listOf(3u, 7u) to Rational(6286563719, 416745), - listOf(4u, 7u) to Rational(26803885301, 1714608), - listOf(5u, 7u) to Rational(-13767154393, 4286520), - listOf(6u, 7u) to Rational(-3875138933, 1224720), - listOf(7u, 7u) to Rational(65193755, 333396), - listOf(8u, 7u) to Rational(90974351, 2500470), - listOf(0u, 8u) to Rational(-3182197, 1260), - listOf(1u, 8u) to Rational(24899923, 8820), - listOf(2u, 8u) to Rational(-19999556, 19845), - listOf(3u, 8u) to Rational(3276587, 3969), - listOf(4u, 8u) to Rational(13719549239, 5000940), - listOf(5u, 8u) to Rational(-961839938, 1250235), - listOf(6u, 8u) to Rational(-198184871, 833490), - listOf(7u, 8u) to Rational(230659711, 5000940), - listOf(8u, 8u) to Rational(292447, 35721) - ), - NumberedPolynomialAsIs( - listOf() to Rational(9, 100), - listOf(1u) to Rational(-21, 50), - listOf(2u) to Rational(293, 700), - listOf(3u) to Rational(29, 210), - listOf(4u) to Rational(3233, 8820), - listOf(5u) to Rational(-289, 441), - listOf(6u) to Rational(-1, 9), - listOf(7u) to Rational(-20, 441), - listOf(8u) to Rational(100, 441), - listOf(0u, 1u) to Rational(-57, 80), - listOf(1u, 1u) to Rational(-121, 400), - listOf(2u, 1u) to Rational(37117, 8400), - listOf(3u, 1u) to Rational(-4853, 3150), - listOf(4u, 1u) to Rational(1166203, 132300), - listOf(5u, 1u) to Rational(-2708, 567), - listOf(6u, 1u) to Rational(-287159, 416745), - listOf(7u, 1u) to Rational(-478204, 83349), - listOf(8u, 1u) to Rational(176320, 83349), - listOf(0u, 2u) to Rational(-6239, 6400), - listOf(1u, 2u) to Rational(264211, 11200), - listOf(2u, 2u) to Rational(-1591999, 100800), - listOf(3u, 2u) to Rational(12450091, 529200), - listOf(4u, 2u) to Rational(9230759, 226800), - listOf(5u, 2u) to Rational(18995554, 2083725), - listOf(6u, 2u) to Rational(136706258, 6251175), - listOf(7u, 2u) to Rational(-120907496, 3750705), - listOf(8u, 2u) to Rational(117200176, 15752961), - listOf(0u, 3u) to Rational(5653, 320), - listOf(1u, 3u) to Rational(-130853, 8400), - listOf(2u, 3u) to Rational(-20939327, 151200), - listOf(3u, 3u) to Rational(2566691, 25200), - listOf(4u, 3u) to Rational(-68441519, 476280), - listOf(5u, 3u) to Rational(2462904247, 12502350), - listOf(6u, 3u) to Rational(353667161, 18753525), - listOf(7u, 3u) to Rational(-1689134372, 26254935), - listOf(8u, 3u) to Rational(35084104, 2250423), - listOf(0u, 4u) to Rational(-3587, 300), - listOf(1u, 4u) to Rational(-10513243, 33600), - listOf(2u, 4u) to Rational(30766733, 176400), - listOf(3u, 4u) to Rational(-65680021, 198450), - listOf(4u, 4u) to Rational(-8108910547, 20003760), - listOf(5u, 4u) to Rational(2922125159, 6251175), - listOf(6u, 4u) to Rational(-4245279943, 131274675), - listOf(7u, 4u) to Rational(-371946872, 3750705), - listOf(8u, 4u) to Rational(61286752, 2250423), - listOf(0u, 5u) to Rational(-20477, 160), - listOf(1u, 5u) to Rational(215741, 1120), - listOf(2u, 5u) to Rational(30785843, 31752), - listOf(3u, 5u) to Rational(-357495959, 317520), - listOf(4u, 5u) to Rational(-1611242993, 10001880), - listOf(5u, 5u) to Rational(345925495, 500094), - listOf(6u, 5u) to Rational(-755948411, 3750705), - listOf(7u, 5u) to Rational(-108643496, 1250235), - listOf(8u, 5u) to Rational(1122512, 35721), - listOf(0u, 6u) to Rational(358037, 2880), - listOf(1u, 6u) to Rational(3895837, 3360), - listOf(2u, 6u) to Rational(359419201, 1270080), - listOf(3u, 6u) to Rational(-158522587, 105840), - listOf(4u, 6u) to Rational(10909002599, 20003760), - listOf(5u, 6u) to Rational(76846972, 138915), - listOf(6u, 6u) to Rational(-327696553, 1250235), - listOf(7u, 6u) to Rational(-1687328, 35721), - listOf(8u, 6u) to Rational(1016836, 35721), - listOf(0u, 7u) to Rational(658, 3), - listOf(1u, 7u) to Rational(48035, 168), - listOf(2u, 7u) to Rational(-5777875, 5292), - listOf(3u, 7u) to Rational(-7893899, 10584), - listOf(4u, 7u) to Rational(10191652, 11907), - listOf(5u, 7u) to Rational(2920121, 23814), - listOf(6u, 7u) to Rational(-2699780, 11907), - listOf(7u, 7u) to Rational(4556, 441), - listOf(8u, 7u) to Rational(3440, 189), - listOf(0u, 8u) to Rational(64, 1), - listOf(1u, 8u) to Rational(-808, 7), - listOf(2u, 8u) to Rational(-360895, 1764), - listOf(3u, 8u) to Rational(257657, 882), - listOf(4u, 8u) to Rational(3779917, 15876), - listOf(5u, 8u) to Rational(-610279, 3969), - listOf(6u, 8u) to Rational(-25091, 441), - listOf(7u, 8u) to Rational(9560, 567), - listOf(8u, 8u) to Rational(400, 81) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 9), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(10, 9), - listOf(0u, 1u) to Rational(13, 3), - listOf(1u, 1u) to Rational(-12, 4), - listOf(2u, 1u) to Rational(3, 6), - listOf(0u, 2u) to Rational(2, 9), - listOf(1u, 2u) to Rational(7, 3), - listOf(2u, 2u) to Rational(16, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 2), - listOf(1u) to Rational(6, 2), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 1), - listOf(1u, 1u) to Rational(-11, 3), - listOf(2u, 1u) to Rational(7, 5), - listOf(0u, 2u) to Rational(8, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(17, 4), - ) - ) - )), - "test 3'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-66677, 3500), - listOf(1u) to Rational(-206281, 10500), - listOf(2u) to Rational(-412567, 7056), - listOf(3u) to Rational(-310081, 11025), - listOf(4u) to Rational(-575996, 15435), - listOf(0u, 1u) to Rational(-573701, 4200), - listOf(1u, 1u) to Rational(-2239001, 25200), - listOf(2u, 1u) to Rational(-8817889, 132300), - listOf(3u, 1u) to Rational(2317919, 44100), - listOf(4u, 1u) to Rational(1169471, 6615), - listOf(0u, 2u) to Rational(-4057819, 33600), - listOf(1u, 2u) to Rational(1373311, 12600), - listOf(2u, 2u) to Rational(32433493, 52920), - listOf(3u, 2u) to Rational(4998053, 33075), - listOf(4u, 2u) to Rational(-2147779, 8820), - listOf(0u, 3u) to Rational(2018481, 2240), - listOf(1u, 3u) to Rational(941713, 1440), - listOf(2u, 3u) to Rational(183749, 6615), - listOf(3u, 3u) to Rational(-4631023, 15876), - listOf(4u, 3u) to Rational(25609336, 178605), - listOf(0u, 4u) to Rational(11886431, 6720), - listOf(1u, 4u) to Rational(18433, 504), - listOf(2u, 4u) to Rational(-39613331, 45360), - listOf(3u, 4u) to Rational(681619, 5670), - listOf(4u, 4u) to Rational(-864841, 20412), - listOf(0u, 5u) to Rational(343535, 1008), - listOf(1u, 5u) to Rational(-33583, 72), - listOf(2u, 5u) to Rational(1194625, 9072), - listOf(3u, 5u) to Rational(-62917, 2268), - listOf(4u, 5u) to Rational(157645, 10206), - listOf(0u, 6u) to Rational(-1381, 3), - listOf(1u, 6u) to Rational(919, 36), - listOf(2u, 6u) to Rational(-3053, 36), - listOf(3u, 6u) to Rational(2125, 324), - listOf(4u, 6u) to Rational(-236, 243) - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(1, 4), - listOf(1u) to Rational(-5, 3), - listOf(2u) to Rational(35, 9), - listOf(3u) to Rational(-100, 27), - listOf(4u) to Rational(100, 81), - listOf(0u, 1u) to Rational(-5, 3), - listOf(1u, 1u) to Rational(14, 9), - listOf(2u, 1u) to Rational(1874, 189), - listOf(3u, 1u) to Rational(-620, 63), - listOf(4u, 1u) to Rational(40, 63), - listOf(0u, 2u) to Rational(16, 9), - listOf(1u, 2u) to Rational(365, 21), - listOf(2u, 2u) to Rational(112, 9), - listOf(3u, 2u) to Rational(-464, 63), - listOf(4u, 2u) to Rational(1996, 441), - listOf(0u, 3u) to Rational(10, 3), - listOf(1u, 3u) to Rational(118, 21), - listOf(2u, 3u) to Rational(-272, 21), - listOf(3u, 3u) to Rational(-764, 49), - listOf(4u, 3u) to Rational(8, 7), - listOf(0u, 4u) to Rational(1, 1), - listOf(1u, 4u) to Rational(-10, 7), - listOf(2u, 4u) to Rational(-171, 49), - listOf(3u, 4u) to Rational(20, 7), - listOf(4u, 4u) to Rational(4, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-66677, 3500), - listOf(1u) to Rational(-206281, 10500), - listOf(2u) to Rational(-412567, 7056), - listOf(3u) to Rational(-310081, 11025), - listOf(4u) to Rational(-575996, 15435), - listOf(0u, 1u) to Rational(-573701, 4200), - listOf(1u, 1u) to Rational(-2239001, 25200), - listOf(2u, 1u) to Rational(-8817889, 132300), - listOf(3u, 1u) to Rational(2317919, 44100), - listOf(4u, 1u) to Rational(1169471, 6615), - listOf(0u, 2u) to Rational(-4057819, 33600), - listOf(1u, 2u) to Rational(1373311, 12600), - listOf(2u, 2u) to Rational(32433493, 52920), - listOf(3u, 2u) to Rational(4998053, 33075), - listOf(4u, 2u) to Rational(-2147779, 8820), - listOf(0u, 3u) to Rational(2018481, 2240), - listOf(1u, 3u) to Rational(941713, 1440), - listOf(2u, 3u) to Rational(183749, 6615), - listOf(3u, 3u) to Rational(-4631023, 15876), - listOf(4u, 3u) to Rational(25609336, 178605), - listOf(0u, 4u) to Rational(11886431, 6720), - listOf(1u, 4u) to Rational(18433, 504), - listOf(2u, 4u) to Rational(-39613331, 45360), - listOf(3u, 4u) to Rational(681619, 5670), - listOf(4u, 4u) to Rational(-864841, 20412), - listOf(0u, 5u) to Rational(343535, 1008), - listOf(1u, 5u) to Rational(-33583, 72), - listOf(2u, 5u) to Rational(1194625, 9072), - listOf(3u, 5u) to Rational(-62917, 2268), - listOf(4u, 5u) to Rational(157645, 10206), - listOf(0u, 6u) to Rational(-1381, 3), - listOf(1u, 6u) to Rational(919, 36), - listOf(2u, 6u) to Rational(-3053, 36), - listOf(3u, 6u) to Rational(2125, 324), - listOf(4u, 6u) to Rational(-236, 243) - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(1, 4), - listOf(1u) to Rational(-5, 3), - listOf(2u) to Rational(35, 9), - listOf(3u) to Rational(-100, 27), - listOf(4u) to Rational(100, 81), - listOf(0u, 1u) to Rational(-5, 3), - listOf(1u, 1u) to Rational(14, 9), - listOf(2u, 1u) to Rational(1874, 189), - listOf(3u, 1u) to Rational(-620, 63), - listOf(4u, 1u) to Rational(40, 63), - listOf(0u, 2u) to Rational(16, 9), - listOf(1u, 2u) to Rational(365, 21), - listOf(2u, 2u) to Rational(112, 9), - listOf(3u, 2u) to Rational(-464, 63), - listOf(4u, 2u) to Rational(1996, 441), - listOf(0u, 3u) to Rational(10, 3), - listOf(1u, 3u) to Rational(118, 21), - listOf(2u, 3u) to Rational(-272, 21), - listOf(3u, 3u) to Rational(-764, 49), - listOf(4u, 3u) to Rational(8, 7), - listOf(0u, 4u) to Rational(1, 1), - listOf(1u, 4u) to Rational(-10, 7), - listOf(2u, 4u) to Rational(-171, 49), - listOf(3u, 4u) to Rational(20, 7), - listOf(4u, 4u) to Rational(4, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 9), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(10, 9), - listOf(0u, 1u) to Rational(13, 3), - listOf(1u, 1u) to Rational(-12, 4), - listOf(2u, 1u) to Rational(3, 6), - listOf(0u, 2u) to Rational(2, 9), - listOf(1u, 2u) to Rational(7, 3), - listOf(2u, 2u) to Rational(16, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 2), - listOf(1u) to Rational(6, 2), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 1), - listOf(1u, 1u) to Rational(-11, 3), - listOf(2u, 1u) to Rational(7, 5), - listOf(0u, 2u) to Rational(8, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(17, 4), - ) - ) - )), - "test 4'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(3539, 700), - listOf(1u) to Rational(-307079, 6300), - listOf(2u) to Rational(451609, 15120), - listOf(3u) to Rational(35287733, 396900), - listOf(4u) to Rational(-37242617, 396900), - listOf(5u) to Rational(382747, 19845), - listOf(6u) to Rational(-2407, 3969), - listOf(0u, 1u) to Rational(-226, 175), - listOf(1u, 1u) to Rational(-74113, 1890), - listOf(2u, 1u) to Rational(250931, 1764), - listOf(3u, 1u) to Rational(30071473, 99225), - listOf(4u, 1u) to Rational(-286466, 1323), - listOf(5u, 1u) to Rational(-2285282, 9261), - listOf(6u, 1u) to Rational(17900, 441), - listOf(0u, 2u) to Rational(3817, 3150), - listOf(1u, 2u) to Rational(577568, 11025), - listOf(2u, 2u) to Rational(9073553, 99225), - listOf(3u, 2u) to Rational(-1415849, 79380), - listOf(4u, 2u) to Rational(-124715629, 277830), - listOf(5u, 2u) to Rational(-1328953, 1890), - listOf(6u, 2u) to Rational(-297148, 1323), - listOf(0u, 3u) to Rational(6043, 945), - listOf(1u, 3u) to Rational(160381, 6615), - listOf(2u, 3u) to Rational(-673249, 13230), - listOf(3u, 3u) to Rational(-319255, 2058), - listOf(4u, 3u) to Rational(-98144, 1029), - listOf(5u, 3u) to Rational(-320239, 5145), - listOf(6u, 3u) to Rational(400, 147), - listOf(0u, 4u) to Rational(163, 63), - listOf(1u, 4u) to Rational(-25183, 4410), - listOf(2u, 4u) to Rational(-21369, 1372), - listOf(3u, 4u) to Rational(127499, 30870), - listOf(4u, 4u) to Rational(86971, 12348), - listOf(5u, 4u) to Rational(-11129, 1470), - listOf(6u, 4u) to Rational(544, 147) - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(1, 4), - listOf(1u) to Rational(-5, 3), - listOf(2u) to Rational(35, 9), - listOf(3u) to Rational(-100, 27), - listOf(4u) to Rational(100, 81), - listOf(0u, 1u) to Rational(-5, 3), - listOf(1u, 1u) to Rational(14, 9), - listOf(2u, 1u) to Rational(1874, 189), - listOf(3u, 1u) to Rational(-620, 63), - listOf(4u, 1u) to Rational(40, 63), - listOf(0u, 2u) to Rational(16, 9), - listOf(1u, 2u) to Rational(365, 21), - listOf(2u, 2u) to Rational(112, 9), - listOf(3u, 2u) to Rational(-464, 63), - listOf(4u, 2u) to Rational(1996, 441), - listOf(0u, 3u) to Rational(10, 3), - listOf(1u, 3u) to Rational(118, 21), - listOf(2u, 3u) to Rational(-272, 21), - listOf(3u, 3u) to Rational(-764, 49), - listOf(4u, 3u) to Rational(8, 7), - listOf(0u, 4u) to Rational(1, 1), - listOf(1u, 4u) to Rational(-10, 7), - listOf(2u, 4u) to Rational(-171, 49), - listOf(3u, 4u) to Rational(20, 7), - listOf(4u, 4u) to Rational(4, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(3539, 700), - listOf(1u) to Rational(-307079, 6300), - listOf(2u) to Rational(451609, 15120), - listOf(3u) to Rational(35287733, 396900), - listOf(4u) to Rational(-37242617, 396900), - listOf(5u) to Rational(382747, 19845), - listOf(6u) to Rational(-2407, 3969), - listOf(0u, 1u) to Rational(-226, 175), - listOf(1u, 1u) to Rational(-74113, 1890), - listOf(2u, 1u) to Rational(250931, 1764), - listOf(3u, 1u) to Rational(30071473, 99225), - listOf(4u, 1u) to Rational(-286466, 1323), - listOf(5u, 1u) to Rational(-2285282, 9261), - listOf(6u, 1u) to Rational(17900, 441), - listOf(0u, 2u) to Rational(3817, 3150), - listOf(1u, 2u) to Rational(577568, 11025), - listOf(2u, 2u) to Rational(9073553, 99225), - listOf(3u, 2u) to Rational(-1415849, 79380), - listOf(4u, 2u) to Rational(-124715629, 277830), - listOf(5u, 2u) to Rational(-1328953, 1890), - listOf(6u, 2u) to Rational(-297148, 1323), - listOf(0u, 3u) to Rational(6043, 945), - listOf(1u, 3u) to Rational(160381, 6615), - listOf(2u, 3u) to Rational(-673249, 13230), - listOf(3u, 3u) to Rational(-319255, 2058), - listOf(4u, 3u) to Rational(-98144, 1029), - listOf(5u, 3u) to Rational(-320239, 5145), - listOf(6u, 3u) to Rational(400, 147), - listOf(0u, 4u) to Rational(163, 63), - listOf(1u, 4u) to Rational(-25183, 4410), - listOf(2u, 4u) to Rational(-21369, 1372), - listOf(3u, 4u) to Rational(127499, 30870), - listOf(4u, 4u) to Rational(86971, 12348), - listOf(5u, 4u) to Rational(-11129, 1470), - listOf(6u, 4u) to Rational(544, 147) - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(1, 4), - listOf(1u) to Rational(-5, 3), - listOf(2u) to Rational(35, 9), - listOf(3u) to Rational(-100, 27), - listOf(4u) to Rational(100, 81), - listOf(0u, 1u) to Rational(-5, 3), - listOf(1u, 1u) to Rational(14, 9), - listOf(2u, 1u) to Rational(1874, 189), - listOf(3u, 1u) to Rational(-620, 63), - listOf(4u, 1u) to Rational(40, 63), - listOf(0u, 2u) to Rational(16, 9), - listOf(1u, 2u) to Rational(365, 21), - listOf(2u, 2u) to Rational(112, 9), - listOf(3u, 2u) to Rational(-464, 63), - listOf(4u, 2u) to Rational(1996, 441), - listOf(0u, 3u) to Rational(10, 3), - listOf(1u, 3u) to Rational(118, 21), - listOf(2u, 3u) to Rational(-272, 21), - listOf(3u, 3u) to Rational(-764, 49), - listOf(4u, 3u) to Rational(8, 7), - listOf(0u, 4u) to Rational(1, 1), - listOf(1u, 4u) to Rational(-10, 7), - listOf(2u, 4u) to Rational(-171, 49), - listOf(3u, 4u) to Rational(20, 7), - listOf(4u, 4u) to Rational(4, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 9), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(10, 9), - listOf(0u, 1u) to Rational(13, 3), - listOf(1u, 1u) to Rational(-12, 4), - listOf(2u, 1u) to Rational(3, 6), - listOf(0u, 2u) to Rational(2, 9), - listOf(1u, 2u) to Rational(7, 3), - listOf(2u, 2u) to Rational(16, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 2), - listOf(1u) to Rational(6, 2), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 1), - listOf(1u, 1u) to Rational(-11, 3), - listOf(2u, 1u) to Rational(7, 5), - listOf(0u, 2u) to Rational(8, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(17, 4), - ) - ) - )), - "test 5'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(0, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(0, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, mapOf( - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 9), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(10, 9), - listOf(0u, 1u) to Rational(13, 3), - listOf(1u, 1u) to Rational(-12, 4), - listOf(2u, 1u) to Rational(3, 6), - listOf(0u, 2u) to Rational(2, 9), - listOf(1u, 2u) to Rational(7, 3), - listOf(2u, 2u) to Rational(16, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 2), - listOf(1u) to Rational(6, 2), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 1), - listOf(1u, 1u) to Rational(-11, 3), - listOf(2u, 1u) to Rational(7, 5), - listOf(0u, 2u) to Rational(8, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(17, 4), - ) - ) - )), - "test 6'" - ) - } - @Test - fun test_RationalFunction_substitute_Double_Map() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs(emptyList() to 0.0), - NumberedPolynomialAsIs(emptyList() to 1.0), - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ), - NumberedPolynomialAsIs( - listOf() to 1.0, - ) - ).substitute(mapOf( - 0 to 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf()), - 0.001, - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 5 to 0.9211194782050933 - )), - 0.001, - "test 2'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 151.1502229133916, - listOf(0u, 1u) to -262.3790170577034, - listOf(0u, 2u) to 102.5097937392923, - ), - NumberedPolynomialAsIs( - listOf() to -367.9969733169944, - listOf(0u, 1u) to 112.4911133334554, - listOf(0u, 2u) to -469.755906895345, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 0 to -8.11707689492641, - )), - 0.001, - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 151.1502229133916, - listOf(0u, 1u) to -262.3790170577034, - listOf(0u, 2u) to 102.5097937392923, - ), - NumberedPolynomialAsIs( - listOf() to -367.9969733169944, - listOf(0u, 1u) to 112.4911133334554, - listOf(0u, 2u) to -469.755906895345, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 0 to -8.11707689492641, - 5 to 0.9211194782050933 - )), - 0.001, - "test 3'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 14.24074356896978, - listOf(1u) to -17.71987055153461, - listOf(2u) to -2.288056483312383, - ), - NumberedPolynomialAsIs( - listOf() to 7.480604285873397, - listOf(1u) to -8.43478016688617, - listOf(2u) to -9.88934943900592, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 1 to 0.795265651276015, - )), - 0.001, - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 14.24074356896978, - listOf(1u) to -17.71987055153461, - listOf(2u) to -2.288056483312383, - ), - NumberedPolynomialAsIs( - listOf() to 7.480604285873397, - listOf(1u) to -8.43478016688617, - listOf(2u) to -9.88934943900592, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 1 to 0.795265651276015, - 5 to 0.9211194782050933 - )), - 0.001, - "test 4'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 7.321261307532708, - ), - NumberedPolynomialAsIs( - listOf() to -575.6325831127576, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 0 to -8.11707689492641, - 1 to 0.795265651276015, - )), - 0.001, - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 7.321261307532708, - ), - NumberedPolynomialAsIs( - listOf() to -575.6325831127576, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(mapOf( - 0 to -8.11707689492641, - 1 to 0.795265651276015, - 5 to 0.9211194782050933 - )), - 0.001, - "test 5'" - ) - } - @Test - fun test_RationalFunction_substitute_Constant_Map() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ).substitute(RationalField, mapOf( - 0 to Rational(1) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(22047, 2450), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2204953, 147000), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 0 to Rational(7, 5), - 1 to Rational(-13, 7), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(22047, 2450), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2204953, 147000), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 0 to Rational(7, 5), - 1 to Rational(-13, 7), - 5 to Rational(-16, 4), - )), - "test 2'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(4191, 490), - listOf(1u) to Rational(14975, 1176), - listOf(2u) to Rational(-10429, 1176) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-775, 147), - listOf(1u) to Rational(-155, 49), - listOf(2u) to Rational(-757, 280) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 1 to Rational(-13, 7), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(4191, 490), - listOf(1u) to Rational(14975, 1176), - listOf(2u) to Rational(-10429, 1176) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-775, 147), - listOf(1u) to Rational(-155, 49), - listOf(2u) to Rational(-757, 280) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 1 to Rational(-13, 7), - 5 to Rational(-16, 4), - )), - "test 3'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-939, 200), - listOf(0u, 1u) to Rational(123, 50), - listOf(0u, 2u) to Rational(1059, 200) - ), - NumberedPolynomialAsIs( - listOf() to Rational(121, 25), - listOf(0u, 1u) to Rational(-949, 375), - listOf(0u, 2u) to Rational(-1423, 200) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 0 to Rational(7, 5), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-939, 200), - listOf(0u, 1u) to Rational(123, 50), - listOf(0u, 2u) to Rational(1059, 200) - ), - NumberedPolynomialAsIs( - listOf() to Rational(121, 25), - listOf(0u, 1u) to Rational(-949, 375), - listOf(0u, 2u) to Rational(-1423, 200) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 0 to Rational(7, 5), - 5 to Rational(-16, 4), - )), - "test 4'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf()), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, mapOf( - 5 to Rational(-16, 4), - )), - "test 5'" - ) - } - @Test - fun test_RationalFunction_substitute_Polynomial_Map() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(211, 4), - listOf(2u) to Rational(88, 3), - listOf(3u) to Rational(-63, 8), - listOf(4u) to Rational(441, 16), - listOf(0u, 1u) to Rational(-671, 15), - listOf(1u, 1u) to Rational(-551, 21), - listOf(2u, 1u) to Rational(279, 25), - listOf(3u, 1u) to Rational(231, 20), - listOf(0u, 2u) to Rational(-1436, 1575), - listOf(1u, 2u) to Rational(2471, 250), - listOf(2u, 2u) to Rational(-4919, 100), - listOf(0u, 3u) to Rational(-1464, 125), - listOf(1u, 3u) to Rational(-264, 25), - listOf(0u, 4u) to Rational(576, 25), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(-9, 4), - listOf(2u) to Rational(943, 8), - listOf(3u) to Rational(117, 8), - listOf(4u) to Rational(147, 16), - listOf(0u, 1u) to Rational(289, 90), - listOf(1u, 1u) to Rational(-2692, 15), - listOf(2u, 1u) to Rational(-1629, 140), - listOf(3u, 1u) to Rational(77, 20), - listOf(0u, 2u) to Rational(6187, 75), - listOf(1u, 2u) to Rational(-2879, 175), - listOf(2u, 2u) to Rational(-4919, 300), - listOf(0u, 3u) to Rational(336, 25), - listOf(1u, 3u) to Rational(-88, 25), - listOf(0u, 4u) to Rational(192, 25), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf(1u) to Rational(3, 2), - listOf(0u, 1u) to Rational(8, 5), - ), - 1 to NumberedPolynomialAsIs( - listOf(1u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-3, 1), - ) - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1202861, 210), - listOf(1u) to Rational(-215117, 45), - listOf(2u) to Rational(10889651, 19845), - listOf(3u) to Rational(-3503956, 6615), - listOf(4u) to Rational(809066, 2205), - listOf(5u) to Rational(-9056, 735), - listOf(6u) to Rational(5396, 315), - listOf(7u) to Rational(-752, 147), - listOf(8u) to Rational(16, 49), - listOf(0u, 1u) to Rational(1738469, 1470), - listOf(1u, 1u) to Rational(-926238703, 52920), - listOf(2u, 1u) to Rational(-44113982, 6615), - listOf(3u, 1u) to Rational(10423519, 5292), - listOf(4u, 1u) to Rational(3769712, 2205), - listOf(5u, 1u) to Rational(8905046, 6615), - listOf(6u, 1u) to Rational(1186972, 6615), - listOf(7u, 1u) to Rational(22124, 441), - listOf(8u, 1u) to Rational(-1504, 147), - listOf(0u, 2u) to Rational(-54723628, 2205), - listOf(1u, 2u) to Rational(70109407, 1323), - listOf(2u, 2u) to Rational(151072591, 17640), - listOf(3u, 2u) to Rational(1216428107, 52920), - listOf(4u, 2u) to Rational(2587873193, 317520), - listOf(5u, 2u) to Rational(393536369, 79380), - listOf(6u, 2u) to Rational(137614937, 79380), - listOf(7u, 2u) to Rational(566866, 1323), - listOf(8u, 2u) to Rational(41848, 441), - listOf(0u, 3u) to Rational(-19470406, 2205), - listOf(1u, 3u) to Rational(72514195, 882), - listOf(2u, 3u) to Rational(-78090707, 1764), - listOf(3u, 3u) to Rational(-1988237707, 26460), - listOf(4u, 3u) to Rational(-802137919, 17640), - listOf(5u, 3u) to Rational(-139989463, 5880), - listOf(6u, 3u) to Rational(-26066641, 3780), - listOf(7u, 3u) to Rational(-2363369, 1323), - listOf(8u, 3u) to Rational(-108280, 441), - listOf(0u, 4u) to Rational(14878516, 441), - listOf(1u, 4u) to Rational(-253416724, 2205), - listOf(2u, 4u) to Rational(16699157, 840), - listOf(3u, 4u) to Rational(-105220979, 13230), - listOf(4u, 4u) to Rational(208266383, 5880), - listOf(5u, 4u) to Rational(650135309, 26460), - listOf(6u, 4u) to Rational(123808663, 11760), - listOf(7u, 4u) to Rational(8563385, 2646), - listOf(8u, 4u) to Rational(19721, 49), - listOf(0u, 5u) to Rational(675645, 49), - listOf(1u, 5u) to Rational(-70554077, 588), - listOf(2u, 5u) to Rational(157884029, 980), - listOf(3u, 5u) to Rational(489548623, 4410), - listOf(4u, 5u) to Rational(148540519, 17640), - listOf(5u, 5u) to Rational(-5559551, 392), - listOf(6u, 5u) to Rational(-18335711, 1470), - listOf(7u, 5u) to Rational(-38437, 9), - listOf(8u, 5u) to Rational(-29620, 63), - listOf(0u, 6u) to Rational(-727625, 49), - listOf(1u, 6u) to Rational(7046685, 98), - listOf(2u, 6u) to Rational(-334814231, 7056), - listOf(3u, 6u) to Rational(-243971737, 17640), - listOf(4u, 6u) to Rational(-571116659, 35280), - listOf(5u, 6u) to Rational(567538, 315), - listOf(6u, 6u) to Rational(3199768, 315), - listOf(7u, 6u) to Rational(227744, 63), - listOf(8u, 6u) to Rational(23116, 63), - listOf(0u, 7u) to Rational(-27500, 7), - listOf(1u, 7u) to Rational(120125, 3), - listOf(2u, 7u) to Rational(-279200, 3), - listOf(3u, 7u) to Rational(-100160, 7), - listOf(4u, 7u) to Rational(920452, 21), - listOf(5u, 7u) to Rational(226481, 21), - listOf(6u, 7u) to Rational(-34428, 7), - listOf(7u, 7u) to Rational(-6232, 3), - listOf(8u, 7u) to Rational(-608, 3), - listOf(0u, 8u) to Rational(2500, 1), - listOf(1u, 8u) to Rational(-19000, 1), - listOf(2u, 8u) to Rational(37900, 1), - listOf(3u, 8u) to Rational(-1840, 1), - listOf(4u, 8u) to Rational(-17876, 1), - listOf(5u, 8u) to Rational(-1240, 1), - listOf(6u, 8u) to Rational(2788, 1), - listOf(7u, 8u) to Rational(800, 1), - listOf(8u, 8u) to Rational(64, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(162487, 63), - listOf(1u) to Rational(-92713, 54), - listOf(2u) to Rational(802436, 1323), - listOf(3u) to Rational(-55088, 441), - listOf(4u) to Rational(1404034, 9261), - listOf(5u) to Rational(-5804, 1029), - listOf(6u) to Rational(51556, 9261), - listOf(7u) to Rational(-752, 441), - listOf(8u) to Rational(16, 147), - listOf(0u, 1u) to Rational(296071, 441), - listOf(1u, 1u) to Rational(-4991281, 882), - listOf(2u, 1u) to Rational(-18702811, 9261), - listOf(3u, 1u) to Rational(40759043, 27783), - listOf(4u, 1u) to Rational(19768501, 27783), - listOf(5u, 1u) to Rational(14307337, 27783), - listOf(6u, 1u) to Rational(1655684, 27783), - listOf(7u, 1u) to Rational(22124, 1323), - listOf(8u, 1u) to Rational(-1504, 441), - listOf(0u, 2u) to Rational(-27667474, 3087), - listOf(1u, 2u) to Rational(265605901, 12348), - listOf(2u, 2u) to Rational(160360775, 98784), - listOf(3u, 2u) to Rational(1169992093, 148176), - listOf(4u, 2u) to Rational(3978014077, 1333584), - listOf(5u, 2u) to Rational(567058123, 333396), - listOf(6u, 2u) to Rational(205132579, 333396), - listOf(7u, 2u) to Rational(566866, 3969), - listOf(8u, 2u) to Rational(41848, 1323), - listOf(0u, 3u) to Rational(-2228822, 1029), - listOf(1u, 3u) to Rational(80179390, 3087), - listOf(2u, 3u) to Rational(-1378630487, 74088), - listOf(3u, 3u) to Rational(-3385811693, 111132), - listOf(4u, 3u) to Rational(-820686977, 49392), - listOf(5u, 3u) to Rational(-89101027, 10584), - listOf(6u, 3u) to Rational(-37847387, 15876), - listOf(7u, 3u) to Rational(-2363369, 3969), - listOf(8u, 3u) to Rational(-108280, 1323), - listOf(0u, 4u) to Rational(12619982, 1029), - listOf(1u, 4u) to Rational(-277723177, 6174), - listOf(2u, 4u) to Rational(649414169, 49392), - listOf(3u, 4u) to Rational(14457595, 63504), - listOf(4u, 4u) to Rational(139270339, 10584), - listOf(5u, 4u) to Rational(140367961, 15876), - listOf(6u, 4u) to Rational(25467083, 7056), - listOf(7u, 4u) to Rational(8563385, 7938), - listOf(8u, 4u) to Rational(19721, 147), - listOf(0u, 5u) to Rational(643850, 147), - listOf(1u, 5u) to Rational(-11818025, 294), - listOf(2u, 5u) to Rational(33963203, 588), - listOf(3u, 5u) to Rational(207216235, 5292), - listOf(4u, 5u) to Rational(2861021, 1512), - listOf(5u, 5u) to Rational(-6302335, 1176), - listOf(6u, 5u) to Rational(-3738587, 882), - listOf(7u, 5u) to Rational(-38437, 27), - listOf(8u, 5u) to Rational(-29620, 189), - listOf(0u, 6u) to Rational(-248725, 49), - listOf(1u, 6u) to Rational(2478535, 98), - listOf(2u, 6u) to Rational(-399721367, 21168), - listOf(3u, 6u) to Rational(-54309317, 10584), - listOf(4u, 6u) to Rational(-95398327, 21168), - listOf(5u, 6u) to Rational(173750, 189), - listOf(6u, 6u) to Rational(92216, 27), - listOf(7u, 6u) to Rational(227744, 189), - listOf(8u, 6u) to Rational(23116, 189), - listOf(0u, 7u) to Rational(-27500, 21), - listOf(1u, 7u) to Rational(120125, 9), - listOf(2u, 7u) to Rational(-279200, 9), - listOf(3u, 7u) to Rational(-100160, 21), - listOf(4u, 7u) to Rational(920452, 63), - listOf(5u, 7u) to Rational(226481, 63), - listOf(6u, 7u) to Rational(-11476, 7), - listOf(7u, 7u) to Rational(-6232, 9), - listOf(8u, 7u) to Rational(-608, 9), - listOf(0u, 8u) to Rational(2500, 3), - listOf(1u, 8u) to Rational(-19000, 3), - listOf(2u, 8u) to Rational(37900, 3), - listOf(3u, 8u) to Rational(-1840, 3), - listOf(4u, 8u) to Rational(-17876, 3), - listOf(5u, 8u) to Rational(-1240, 3), - listOf(6u, 8u) to Rational(2788, 3), - listOf(7u, 8u) to Rational(800, 3), - listOf(8u, 8u) to Rational(64, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - 1 to NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1202861, 210), - listOf(1u) to Rational(-215117, 45), - listOf(2u) to Rational(10889651, 19845), - listOf(3u) to Rational(-3503956, 6615), - listOf(4u) to Rational(809066, 2205), - listOf(5u) to Rational(-9056, 735), - listOf(6u) to Rational(5396, 315), - listOf(7u) to Rational(-752, 147), - listOf(8u) to Rational(16, 49), - listOf(0u, 1u) to Rational(1738469, 1470), - listOf(1u, 1u) to Rational(-926238703, 52920), - listOf(2u, 1u) to Rational(-44113982, 6615), - listOf(3u, 1u) to Rational(10423519, 5292), - listOf(4u, 1u) to Rational(3769712, 2205), - listOf(5u, 1u) to Rational(8905046, 6615), - listOf(6u, 1u) to Rational(1186972, 6615), - listOf(7u, 1u) to Rational(22124, 441), - listOf(8u, 1u) to Rational(-1504, 147), - listOf(0u, 2u) to Rational(-54723628, 2205), - listOf(1u, 2u) to Rational(70109407, 1323), - listOf(2u, 2u) to Rational(151072591, 17640), - listOf(3u, 2u) to Rational(1216428107, 52920), - listOf(4u, 2u) to Rational(2587873193, 317520), - listOf(5u, 2u) to Rational(393536369, 79380), - listOf(6u, 2u) to Rational(137614937, 79380), - listOf(7u, 2u) to Rational(566866, 1323), - listOf(8u, 2u) to Rational(41848, 441), - listOf(0u, 3u) to Rational(-19470406, 2205), - listOf(1u, 3u) to Rational(72514195, 882), - listOf(2u, 3u) to Rational(-78090707, 1764), - listOf(3u, 3u) to Rational(-1988237707, 26460), - listOf(4u, 3u) to Rational(-802137919, 17640), - listOf(5u, 3u) to Rational(-139989463, 5880), - listOf(6u, 3u) to Rational(-26066641, 3780), - listOf(7u, 3u) to Rational(-2363369, 1323), - listOf(8u, 3u) to Rational(-108280, 441), - listOf(0u, 4u) to Rational(14878516, 441), - listOf(1u, 4u) to Rational(-253416724, 2205), - listOf(2u, 4u) to Rational(16699157, 840), - listOf(3u, 4u) to Rational(-105220979, 13230), - listOf(4u, 4u) to Rational(208266383, 5880), - listOf(5u, 4u) to Rational(650135309, 26460), - listOf(6u, 4u) to Rational(123808663, 11760), - listOf(7u, 4u) to Rational(8563385, 2646), - listOf(8u, 4u) to Rational(19721, 49), - listOf(0u, 5u) to Rational(675645, 49), - listOf(1u, 5u) to Rational(-70554077, 588), - listOf(2u, 5u) to Rational(157884029, 980), - listOf(3u, 5u) to Rational(489548623, 4410), - listOf(4u, 5u) to Rational(148540519, 17640), - listOf(5u, 5u) to Rational(-5559551, 392), - listOf(6u, 5u) to Rational(-18335711, 1470), - listOf(7u, 5u) to Rational(-38437, 9), - listOf(8u, 5u) to Rational(-29620, 63), - listOf(0u, 6u) to Rational(-727625, 49), - listOf(1u, 6u) to Rational(7046685, 98), - listOf(2u, 6u) to Rational(-334814231, 7056), - listOf(3u, 6u) to Rational(-243971737, 17640), - listOf(4u, 6u) to Rational(-571116659, 35280), - listOf(5u, 6u) to Rational(567538, 315), - listOf(6u, 6u) to Rational(3199768, 315), - listOf(7u, 6u) to Rational(227744, 63), - listOf(8u, 6u) to Rational(23116, 63), - listOf(0u, 7u) to Rational(-27500, 7), - listOf(1u, 7u) to Rational(120125, 3), - listOf(2u, 7u) to Rational(-279200, 3), - listOf(3u, 7u) to Rational(-100160, 7), - listOf(4u, 7u) to Rational(920452, 21), - listOf(5u, 7u) to Rational(226481, 21), - listOf(6u, 7u) to Rational(-34428, 7), - listOf(7u, 7u) to Rational(-6232, 3), - listOf(8u, 7u) to Rational(-608, 3), - listOf(0u, 8u) to Rational(2500, 1), - listOf(1u, 8u) to Rational(-19000, 1), - listOf(2u, 8u) to Rational(37900, 1), - listOf(3u, 8u) to Rational(-1840, 1), - listOf(4u, 8u) to Rational(-17876, 1), - listOf(5u, 8u) to Rational(-1240, 1), - listOf(6u, 8u) to Rational(2788, 1), - listOf(7u, 8u) to Rational(800, 1), - listOf(8u, 8u) to Rational(64, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(162487, 63), - listOf(1u) to Rational(-92713, 54), - listOf(2u) to Rational(802436, 1323), - listOf(3u) to Rational(-55088, 441), - listOf(4u) to Rational(1404034, 9261), - listOf(5u) to Rational(-5804, 1029), - listOf(6u) to Rational(51556, 9261), - listOf(7u) to Rational(-752, 441), - listOf(8u) to Rational(16, 147), - listOf(0u, 1u) to Rational(296071, 441), - listOf(1u, 1u) to Rational(-4991281, 882), - listOf(2u, 1u) to Rational(-18702811, 9261), - listOf(3u, 1u) to Rational(40759043, 27783), - listOf(4u, 1u) to Rational(19768501, 27783), - listOf(5u, 1u) to Rational(14307337, 27783), - listOf(6u, 1u) to Rational(1655684, 27783), - listOf(7u, 1u) to Rational(22124, 1323), - listOf(8u, 1u) to Rational(-1504, 441), - listOf(0u, 2u) to Rational(-27667474, 3087), - listOf(1u, 2u) to Rational(265605901, 12348), - listOf(2u, 2u) to Rational(160360775, 98784), - listOf(3u, 2u) to Rational(1169992093, 148176), - listOf(4u, 2u) to Rational(3978014077, 1333584), - listOf(5u, 2u) to Rational(567058123, 333396), - listOf(6u, 2u) to Rational(205132579, 333396), - listOf(7u, 2u) to Rational(566866, 3969), - listOf(8u, 2u) to Rational(41848, 1323), - listOf(0u, 3u) to Rational(-2228822, 1029), - listOf(1u, 3u) to Rational(80179390, 3087), - listOf(2u, 3u) to Rational(-1378630487, 74088), - listOf(3u, 3u) to Rational(-3385811693, 111132), - listOf(4u, 3u) to Rational(-820686977, 49392), - listOf(5u, 3u) to Rational(-89101027, 10584), - listOf(6u, 3u) to Rational(-37847387, 15876), - listOf(7u, 3u) to Rational(-2363369, 3969), - listOf(8u, 3u) to Rational(-108280, 1323), - listOf(0u, 4u) to Rational(12619982, 1029), - listOf(1u, 4u) to Rational(-277723177, 6174), - listOf(2u, 4u) to Rational(649414169, 49392), - listOf(3u, 4u) to Rational(14457595, 63504), - listOf(4u, 4u) to Rational(139270339, 10584), - listOf(5u, 4u) to Rational(140367961, 15876), - listOf(6u, 4u) to Rational(25467083, 7056), - listOf(7u, 4u) to Rational(8563385, 7938), - listOf(8u, 4u) to Rational(19721, 147), - listOf(0u, 5u) to Rational(643850, 147), - listOf(1u, 5u) to Rational(-11818025, 294), - listOf(2u, 5u) to Rational(33963203, 588), - listOf(3u, 5u) to Rational(207216235, 5292), - listOf(4u, 5u) to Rational(2861021, 1512), - listOf(5u, 5u) to Rational(-6302335, 1176), - listOf(6u, 5u) to Rational(-3738587, 882), - listOf(7u, 5u) to Rational(-38437, 27), - listOf(8u, 5u) to Rational(-29620, 189), - listOf(0u, 6u) to Rational(-248725, 49), - listOf(1u, 6u) to Rational(2478535, 98), - listOf(2u, 6u) to Rational(-399721367, 21168), - listOf(3u, 6u) to Rational(-54309317, 10584), - listOf(4u, 6u) to Rational(-95398327, 21168), - listOf(5u, 6u) to Rational(173750, 189), - listOf(6u, 6u) to Rational(92216, 27), - listOf(7u, 6u) to Rational(227744, 189), - listOf(8u, 6u) to Rational(23116, 189), - listOf(0u, 7u) to Rational(-27500, 21), - listOf(1u, 7u) to Rational(120125, 9), - listOf(2u, 7u) to Rational(-279200, 9), - listOf(3u, 7u) to Rational(-100160, 21), - listOf(4u, 7u) to Rational(920452, 63), - listOf(5u, 7u) to Rational(226481, 63), - listOf(6u, 7u) to Rational(-11476, 7), - listOf(7u, 7u) to Rational(-6232, 9), - listOf(8u, 7u) to Rational(-608, 9), - listOf(0u, 8u) to Rational(2500, 3), - listOf(1u, 8u) to Rational(-19000, 3), - listOf(2u, 8u) to Rational(37900, 3), - listOf(3u, 8u) to Rational(-1840, 3), - listOf(4u, 8u) to Rational(-17876, 3), - listOf(5u, 8u) to Rational(-1240, 3), - listOf(6u, 8u) to Rational(2788, 3), - listOf(7u, 8u) to Rational(800, 3), - listOf(8u, 8u) to Rational(64, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - 1 to NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-6, 1), - listOf(1u) to Rational(-9, 8), - listOf(2u) to Rational(17, 5), - listOf(0u, 1u) to Rational(-2, 3), - listOf(1u, 1u) to Rational(1, 5), - listOf(2u, 1u) to Rational(-11, 7), - listOf(0u, 2u) to Rational(13, 6), - listOf(1u, 2u) to Rational(-15, 2), - listOf(2u, 2u) to Rational(-14, 4), - ) - )), - "test 3'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(493, 6), - listOf(1u) to Rational(-15991, 210), - listOf(2u) to Rational(2734, 63), - listOf(3u) to Rational(-8213, 245), - listOf(4u) to Rational(1843, 147), - listOf(5u) to Rational(-432, 245), - listOf(6u) to Rational(4, 49), - listOf(0u, 1u) to Rational(-66, 1), - listOf(1u, 1u) to Rational(-92924, 2205), - listOf(2u, 1u) to Rational(-257461, 2205), - listOf(3u, 1u) to Rational(58658, 2205), - listOf(4u, 1u) to Rational(-87884, 2205), - listOf(5u, 1u) to Rational(2726, 105), - listOf(6u, 1u) to Rational(-52, 21), - listOf(0u, 2u) to Rational(-17569, 147), - listOf(1u, 2u) to Rational(368819, 735), - listOf(2u, 2u) to Rational(-644626, 6615), - listOf(3u, 2u) to Rational(221738, 945), - listOf(4u, 2u) to Rational(-18022, 945), - listOf(5u, 2u) to Rational(-1201, 315), - listOf(6u, 2u) to Rational(1327, 63), - listOf(0u, 3u) to Rational(240, 7), - listOf(1u, 3u) to Rational(-868, 9), - listOf(2u, 3u) to Rational(-8936, 315), - listOf(3u, 3u) to Rational(-77146, 315), - listOf(4u, 3u) to Rational(-4072, 315), - listOf(5u, 3u) to Rational(-2218, 15), - listOf(6u, 3u) to Rational(-104, 3), - listOf(0u, 4u) to Rational(100, 3), - listOf(1u, 4u) to Rational(-725, 3), - listOf(2u, 4u) to Rational(459, 1), - listOf(3u, 4u) to Rational(-2071, 15), - listOf(4u, 4u) to Rational(2831, 15), - listOf(5u, 4u) to Rational(632, 5), - listOf(6u, 4u) to Rational(16, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1255, 9), - listOf(1u) to Rational(-24781, 126), - listOf(2u) to Rational(1195, 14), - listOf(3u) to Rational(-1931, 147), - listOf(4u) to Rational(439, 147), - listOf(5u) to Rational(-172, 343), - listOf(6u) to Rational(4, 147), - listOf(0u, 1u) to Rational(-183, 1), - listOf(1u, 1u) to Rational(-30988, 441), - listOf(2u, 1u) to Rational(-56137, 294), - listOf(3u, 1u) to Rational(204308, 1029), - listOf(4u, 1u) to Rational(-3263, 441), - listOf(5u, 1u) to Rational(2662, 441), - listOf(6u, 1u) to Rational(-52, 63), - listOf(0u, 2u) to Rational(-87119, 294), - listOf(1u, 2u) to Rational(1077919, 686), - listOf(2u, 2u) to Rational(-35209, 147), - listOf(3u, 2u) to Rational(15041, 147), - listOf(4u, 2u) to Rational(240889, 1323), - listOf(5u, 2u) to Rational(27778, 1323), - listOf(6u, 2u) to Rational(1327, 189), - listOf(0u, 3u) to Rational(1620, 7), - listOf(1u, 3u) to Rational(-25716, 49), - listOf(2u, 3u) to Rational(-32078, 49), - listOf(3u, 3u) to Rational(-704038, 441), - listOf(4u, 3u) to Rational(-30190, 63), - listOf(5u, 3u) to Rational(-5414, 63), - listOf(6u, 3u) to Rational(-104, 9), - listOf(0u, 4u) to Rational(225, 1), - listOf(1u, 4u) to Rational(-10560, 7), - listOf(2u, 4u) to Rational(44176, 21), - listOf(3u, 4u) to Rational(28996, 21), - listOf(4u, 4u) to Rational(2405, 7), - listOf(5u, 4u) to Rational(1240, 21), - listOf(6u, 4u) to Rational(16, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 1 to NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(493, 6), - listOf(1u) to Rational(-15991, 210), - listOf(2u) to Rational(2734, 63), - listOf(3u) to Rational(-8213, 245), - listOf(4u) to Rational(1843, 147), - listOf(5u) to Rational(-432, 245), - listOf(6u) to Rational(4, 49), - listOf(0u, 1u) to Rational(-66, 1), - listOf(1u, 1u) to Rational(-92924, 2205), - listOf(2u, 1u) to Rational(-257461, 2205), - listOf(3u, 1u) to Rational(58658, 2205), - listOf(4u, 1u) to Rational(-87884, 2205), - listOf(5u, 1u) to Rational(2726, 105), - listOf(6u, 1u) to Rational(-52, 21), - listOf(0u, 2u) to Rational(-17569, 147), - listOf(1u, 2u) to Rational(368819, 735), - listOf(2u, 2u) to Rational(-644626, 6615), - listOf(3u, 2u) to Rational(221738, 945), - listOf(4u, 2u) to Rational(-18022, 945), - listOf(5u, 2u) to Rational(-1201, 315), - listOf(6u, 2u) to Rational(1327, 63), - listOf(0u, 3u) to Rational(240, 7), - listOf(1u, 3u) to Rational(-868, 9), - listOf(2u, 3u) to Rational(-8936, 315), - listOf(3u, 3u) to Rational(-77146, 315), - listOf(4u, 3u) to Rational(-4072, 315), - listOf(5u, 3u) to Rational(-2218, 15), - listOf(6u, 3u) to Rational(-104, 3), - listOf(0u, 4u) to Rational(100, 3), - listOf(1u, 4u) to Rational(-725, 3), - listOf(2u, 4u) to Rational(459, 1), - listOf(3u, 4u) to Rational(-2071, 15), - listOf(4u, 4u) to Rational(2831, 15), - listOf(5u, 4u) to Rational(632, 5), - listOf(6u, 4u) to Rational(16, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1255, 9), - listOf(1u) to Rational(-24781, 126), - listOf(2u) to Rational(1195, 14), - listOf(3u) to Rational(-1931, 147), - listOf(4u) to Rational(439, 147), - listOf(5u) to Rational(-172, 343), - listOf(6u) to Rational(4, 147), - listOf(0u, 1u) to Rational(-183, 1), - listOf(1u, 1u) to Rational(-30988, 441), - listOf(2u, 1u) to Rational(-56137, 294), - listOf(3u, 1u) to Rational(204308, 1029), - listOf(4u, 1u) to Rational(-3263, 441), - listOf(5u, 1u) to Rational(2662, 441), - listOf(6u, 1u) to Rational(-52, 63), - listOf(0u, 2u) to Rational(-87119, 294), - listOf(1u, 2u) to Rational(1077919, 686), - listOf(2u, 2u) to Rational(-35209, 147), - listOf(3u, 2u) to Rational(15041, 147), - listOf(4u, 2u) to Rational(240889, 1323), - listOf(5u, 2u) to Rational(27778, 1323), - listOf(6u, 2u) to Rational(1327, 189), - listOf(0u, 3u) to Rational(1620, 7), - listOf(1u, 3u) to Rational(-25716, 49), - listOf(2u, 3u) to Rational(-32078, 49), - listOf(3u, 3u) to Rational(-704038, 441), - listOf(4u, 3u) to Rational(-30190, 63), - listOf(5u, 3u) to Rational(-5414, 63), - listOf(6u, 3u) to Rational(-104, 9), - listOf(0u, 4u) to Rational(225, 1), - listOf(1u, 4u) to Rational(-10560, 7), - listOf(2u, 4u) to Rational(44176, 21), - listOf(3u, 4u) to Rational(28996, 21), - listOf(4u, 4u) to Rational(2405, 7), - listOf(5u, 4u) to Rational(1240, 21), - listOf(6u, 4u) to Rational(16, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 1 to NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-6, 1), - listOf(1u) to Rational(-9, 8), - listOf(2u) to Rational(17, 5), - listOf(0u, 1u) to Rational(-2, 3), - listOf(1u, 1u) to Rational(1, 5), - listOf(2u, 1u) to Rational(-11, 7), - listOf(0u, 2u) to Rational(13, 6), - listOf(1u, 2u) to Rational(-15, 2), - listOf(2u, 2u) to Rational(-14, 4), - ) - )), - "test 4'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-409, 6), - listOf(1u) to Rational(-376, 9), - listOf(2u) to Rational(-1781, 81), - listOf(3u) to Rational(-128, 27), - listOf(4u) to Rational(-8, 9), - listOf(0u, 1u) to Rational(18701, 210), - listOf(1u, 1u) to Rational(614183, 7560), - listOf(2u, 1u) to Rational(90941, 1890), - listOf(3u, 1u) to Rational(1802, 135), - listOf(4u, 1u) to Rational(112, 45), - listOf(0u, 2u) to Rational(181421, 315), - listOf(1u, 2u) to Rational(77813, 378), - listOf(2u, 2u) to Rational(598583, 7560), - listOf(3u, 2u) to Rational(85, 27), - listOf(4u, 2u) to Rational(2, 5), - listOf(0u, 3u) to Rational(130997, 315), - listOf(1u, 3u) to Rational(1093, 420), - listOf(2u, 3u) to Rational(9551, 2520), - listOf(3u, 3u) to Rational(-14, 45), - listOf(4u, 3u) to Rational(22, 45), - listOf(0u, 4u) to Rational(-2801, 9), - listOf(1u, 4u) to Rational(4033, 90), - listOf(2u, 4u) to Rational(6429, 80), - listOf(3u, 4u) to Rational(2851, 90), - listOf(4u, 4u) to Rational(293, 45), - listOf(0u, 5u) to Rational(-220, 1), - listOf(1u, 5u) to Rational(127, 1), - listOf(2u, 5u) to Rational(202, 5), - listOf(3u, 5u) to Rational(-63, 5), - listOf(4u, 5u) to Rational(-12, 5), - listOf(0u, 6u) to Rational(100, 1), - listOf(1u, 6u) to Rational(-80, 1), - listOf(2u, 6u) to Rational(-24, 1), - listOf(3u, 6u) to Rational(16, 1), - listOf(4u, 6u) to Rational(4, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(5407, 9), - listOf(1u) to Rational(9568, 27), - listOf(2u) to Rational(4996, 27), - listOf(3u) to Rational(352, 9), - listOf(4u) to Rational(22, 3), - listOf(0u, 1u) to Rational(104411, 126), - listOf(1u, 1u) to Rational(6001, 126), - listOf(2u, 1u) to Rational(-796, 21), - listOf(3u, 1u) to Rational(-5389, 126), - listOf(4u, 1u) to Rational(-166, 21), - listOf(0u, 2u) to Rational(-35327, 126), - listOf(1u, 2u) to Rational(53, 252), - listOf(2u, 2u) to Rational(849197, 6048), - listOf(3u, 2u) to Rational(22361, 252), - listOf(4u, 2u) to Rational(773, 42), - listOf(0u, 3u) to Rational(-6067, 21), - listOf(1u, 3u) to Rational(39049, 126), - listOf(2u, 3u) to Rational(80303, 1008), - listOf(3u, 3u) to Rational(-3035, 63), - listOf(4u, 3u) to Rational(-209, 21), - listOf(0u, 4u) to Rational(3113, 21), - listOf(1u, 4u) to Rational(-22345, 126), - listOf(2u, 4u) to Rational(-30931, 1008), - listOf(3u, 4u) to Rational(5837, 126), - listOf(4u, 4u) to Rational(229, 21), - listOf(0u, 5u) to Rational(-2120, 21), - listOf(1u, 5u) to Rational(451, 7), - listOf(2u, 5u) to Rational(422, 21), - listOf(3u, 5u) to Rational(-181, 21), - listOf(4u, 5u) to Rational(-40, 21), - listOf(0u, 6u) to Rational(100, 3), - listOf(1u, 6u) to Rational(-80, 3), - listOf(2u, 6u) to Rational(-8, 1), - listOf(3u, 6u) to Rational(16, 3), - listOf(4u, 6u) to Rational(4, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-409, 6), - listOf(1u) to Rational(-376, 9), - listOf(2u) to Rational(-1781, 81), - listOf(3u) to Rational(-128, 27), - listOf(4u) to Rational(-8, 9), - listOf(0u, 1u) to Rational(18701, 210), - listOf(1u, 1u) to Rational(614183, 7560), - listOf(2u, 1u) to Rational(90941, 1890), - listOf(3u, 1u) to Rational(1802, 135), - listOf(4u, 1u) to Rational(112, 45), - listOf(0u, 2u) to Rational(181421, 315), - listOf(1u, 2u) to Rational(77813, 378), - listOf(2u, 2u) to Rational(598583, 7560), - listOf(3u, 2u) to Rational(85, 27), - listOf(4u, 2u) to Rational(2, 5), - listOf(0u, 3u) to Rational(130997, 315), - listOf(1u, 3u) to Rational(1093, 420), - listOf(2u, 3u) to Rational(9551, 2520), - listOf(3u, 3u) to Rational(-14, 45), - listOf(4u, 3u) to Rational(22, 45), - listOf(0u, 4u) to Rational(-2801, 9), - listOf(1u, 4u) to Rational(4033, 90), - listOf(2u, 4u) to Rational(6429, 80), - listOf(3u, 4u) to Rational(2851, 90), - listOf(4u, 4u) to Rational(293, 45), - listOf(0u, 5u) to Rational(-220, 1), - listOf(1u, 5u) to Rational(127, 1), - listOf(2u, 5u) to Rational(202, 5), - listOf(3u, 5u) to Rational(-63, 5), - listOf(4u, 5u) to Rational(-12, 5), - listOf(0u, 6u) to Rational(100, 1), - listOf(1u, 6u) to Rational(-80, 1), - listOf(2u, 6u) to Rational(-24, 1), - listOf(3u, 6u) to Rational(16, 1), - listOf(4u, 6u) to Rational(4, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(5407, 9), - listOf(1u) to Rational(9568, 27), - listOf(2u) to Rational(4996, 27), - listOf(3u) to Rational(352, 9), - listOf(4u) to Rational(22, 3), - listOf(0u, 1u) to Rational(104411, 126), - listOf(1u, 1u) to Rational(6001, 126), - listOf(2u, 1u) to Rational(-796, 21), - listOf(3u, 1u) to Rational(-5389, 126), - listOf(4u, 1u) to Rational(-166, 21), - listOf(0u, 2u) to Rational(-35327, 126), - listOf(1u, 2u) to Rational(53, 252), - listOf(2u, 2u) to Rational(849197, 6048), - listOf(3u, 2u) to Rational(22361, 252), - listOf(4u, 2u) to Rational(773, 42), - listOf(0u, 3u) to Rational(-6067, 21), - listOf(1u, 3u) to Rational(39049, 126), - listOf(2u, 3u) to Rational(80303, 1008), - listOf(3u, 3u) to Rational(-3035, 63), - listOf(4u, 3u) to Rational(-209, 21), - listOf(0u, 4u) to Rational(3113, 21), - listOf(1u, 4u) to Rational(-22345, 126), - listOf(2u, 4u) to Rational(-30931, 1008), - listOf(3u, 4u) to Rational(5837, 126), - listOf(4u, 4u) to Rational(229, 21), - listOf(0u, 5u) to Rational(-2120, 21), - listOf(1u, 5u) to Rational(451, 7), - listOf(2u, 5u) to Rational(422, 21), - listOf(3u, 5u) to Rational(-181, 21), - listOf(4u, 5u) to Rational(-40, 21), - listOf(0u, 6u) to Rational(100, 3), - listOf(1u, 6u) to Rational(-80, 3), - listOf(2u, 6u) to Rational(-8, 1), - listOf(3u, 6u) to Rational(16, 3), - listOf(4u, 6u) to Rational(4, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-6, 1), - listOf(1u) to Rational(-9, 8), - listOf(2u) to Rational(17, 5), - listOf(0u, 1u) to Rational(-2, 3), - listOf(1u, 1u) to Rational(1, 5), - listOf(2u, 1u) to Rational(-11, 7), - listOf(0u, 2u) to Rational(13, 6), - listOf(1u, 2u) to Rational(-15, 2), - listOf(2u, 2u) to Rational(-14, 4), - ) - )), - "test 5'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, mapOf( - 5 to NumberedPolynomialAsIs( - listOf() to Rational(-6, 1), - listOf(1u) to Rational(-9, 8), - listOf(2u) to Rational(17, 5), - listOf(0u, 1u) to Rational(-2, 3), - listOf(1u, 1u) to Rational(1, 5), - listOf(2u, 1u) to Rational(-11, 7), - listOf(0u, 2u) to Rational(13, 6), - listOf(1u, 2u) to Rational(-15, 2), - listOf(2u, 2u) to Rational(-14, 4), - ) - )), - "test 6'" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_RationalFunction_substitute_RationalFunction_Map() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(4u) to Rational(-17166109, 793800), - listOf(3u, 1u) to Rational(-930960143, 5556600), - listOf(2u, 2u) to Rational(-144665109691, 350065800), - listOf(1u, 3u) to Rational(-17232577, 52920), - listOf(0u, 4u) to Rational(-68141, 1323), - ), - NumberedPolynomialAsIs( - listOf(4u) to Rational(-57522533, 14288400), - listOf(3u, 1u) to Rational(-13085162953, 300056400), - listOf(2u, 2u) to Rational(-92093367341, 525098700), - listOf(1u, 3u) to Rational(-1979342797, 6667920), - listOf(0u, 4u) to Rational(-3082727, 21168), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(11, 5), - listOf(0u, 1u) to Rational(8, 4), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(1, 9), - listOf(0u, 1u) to Rational(11, 7), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(-4, 3), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(3, 6), - listOf(0u, 1u) to Rational(12, 8), - ) - ), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-130778291, 76800), - listOf(1u) to Rational(-445270919, 230400), - listOf(2u) to Rational(44578444937, 14515200), - listOf(3u) to Rational(17329402153, 1555200), - listOf(4u) to Rational(89239926809, 2332800), - listOf(5u) to Rational(2808812267, 145152), - listOf(6u) to Rational(-21362661007, 725760), - listOf(7u) to Rational(-258455443, 2016), - listOf(8u) to Rational(-21454693, 96), - listOf(0u, 1u) to Rational(-1002137, 15360), - listOf(1u, 1u) to Rational(-1704849697, 430080), - listOf(2u, 1u) to Rational(-57657676789, 4838400), - listOf(3u, 1u) to Rational(-101331731, 89600), - listOf(4u, 1u) to Rational(5362280079329, 130636800), - listOf(5u, 1u) to Rational(4069896167053, 130636800), - listOf(6u, 1u) to Rational(12011514569, 544320), - listOf(7u, 1u) to Rational(138293195623, 725760), - listOf(8u, 1u) to Rational(6228779419, 48384), - listOf(0u, 2u) to Rational(-32395872823, 8064000), - listOf(1u, 2u) to Rational(-7398505523, 2304000), - listOf(2u, 2u) to Rational(95217051699521, 3048192000), - listOf(3u, 2u) to Rational(198026968812079, 3657830400), - listOf(4u, 2u) to Rational(4291645618499, 228614400), - listOf(5u, 2u) to Rational(-33211690942439, 914457600), - listOf(6u, 2u) to Rational(-637385538163153, 1371686400), - listOf(7u, 2u) to Rational(-138671528276273, 182891520), - listOf(8u, 2u) to Rational(-14566368751, 217728), - listOf(0u, 3u) to Rational(-10538718719, 2016000), - listOf(1u, 3u) to Rational(-1844485375199, 84672000), - listOf(2u, 3u) to Rational(103968665891, 12096000), - listOf(3u, 3u) to Rational(175402107278351, 1828915200), - listOf(4u, 3u) to Rational(8020699588879, 114307200), - listOf(5u, 3u) to Rational(3414841894991, 38102400), - listOf(6u, 3u) to Rational(1848405591611, 4665600), - listOf(7u, 3u) to Rational(39486708738989, 137168640), - listOf(8u, 3u) to Rational(255926289517, 9144576), - listOf(0u, 4u) to Rational(-655379564629, 105840000), - listOf(1u, 4u) to Rational(-208336039441, 127008000), - listOf(2u, 4u) to Rational(40173146771411, 1143072000), - listOf(3u, 4u) to Rational(150473493581239, 2667168000), - listOf(4u, 4u) to Rational(38833783990483, 1143072000), - listOf(5u, 4u) to Rational(-1963676248203053, 4800902400), - listOf(6u, 4u) to Rational(-2598759412825747, 3200601600), - listOf(7u, 4u) to Rational(-192895352019667, 1280240640), - listOf(8u, 4u) to Rational(3737382679, 6858432), - listOf(0u, 5u) to Rational(-16959378721, 1890000), - listOf(1u, 5u) to Rational(-1864802244743, 79380000), - listOf(2u, 5u) to Rational(13449261536489, 666792000), - listOf(3u, 5u) to Rational(215272234137329, 2667168000), - listOf(4u, 5u) to Rational(6040691379277, 83349000), - listOf(5u, 5u) to Rational(153687143525887, 800150400), - listOf(6u, 5u) to Rational(475602854903563, 2400451200), - listOf(7u, 5u) to Rational(27315599358749, 640120320), - listOf(8u, 5u) to Rational(-2630413357, 10668672), - listOf(0u, 6u) to Rational(-6654999511, 2646000), - listOf(1u, 6u) to Rational(-67885252327, 15876000), - listOf(2u, 6u) to Rational(5786776220983, 2667168000), - listOf(3u, 6u) to Rational(60615922629083, 1143072000), - listOf(4u, 6u) to Rational(-34703539637627407, 672126336000), - listOf(5u, 6u) to Rational(-744694192134101, 2240421120), - listOf(6u, 6u) to Rational(-1782470617231, 14817600), - listOf(7u, 6u) to Rational(59123208433, 8890560), - listOf(8u, 6u) to Rational(-141653, 5292), - listOf(0u, 7u) to Rational(-338051969, 441000), - listOf(1u, 7u) to Rational(468850013, 1764000), - listOf(2u, 7u) to Rational(2102343426101, 222264000), - listOf(3u, 7u) to Rational(7836130602007, 1333584000), - listOf(4u, 7u) to Rational(16239111865997, 746807040), - listOf(5u, 7u) to Rational(3824649185383, 88905600), - listOf(6u, 7u) to Rational(56058614459, 3457440), - listOf(7u, 7u) to Rational(-396766339, 493920), - listOf(8u, 7u) to Rational(-165147, 2744), - listOf(0u, 8u) to Rational(-3088619, 58800), - listOf(1u, 8u) to Rational(155343347, 88200), - listOf(2u, 8u) to Rational(100098736469, 7408800), - listOf(3u, 8u) to Rational(109725511381, 7408800), - listOf(4u, 8u) to Rational(-2431199641013, 59270400), - listOf(5u, 8u) to Rational(-102872383249, 3457440), - listOf(6u, 8u) to Rational(1449461309, 576240), - listOf(7u, 8u) to Rational(812775, 1372), - listOf(8u, 8u) to Rational(-16461, 343) - ), - NumberedPolynomialAsIs( - listOf() to Rational(164202773, 230400), - listOf(1u) to Rational(-70345303, 518400), - listOf(2u) to Rational(-4229702731, 4665600), - listOf(3u) to Rational(3262171027, 6998400), - listOf(4u) to Rational(-25423104169, 13996800), - listOf(5u) to Rational(64061869, 349920), - listOf(6u) to Rational(-1655878091, 116640), - listOf(7u) to Rational(-7991441, 648), - listOf(8u) to Rational(-502591, 18), - listOf(0u, 1u) to Rational(-8780429, 3840), - listOf(1u, 1u) to Rational(434272361, 115200), - listOf(2u, 1u) to Rational(429825727, 41472), - listOf(3u, 1u) to Rational(-10066790339, 6998400), - listOf(4u, 1u) to Rational(70022035471, 20995200), - listOf(5u, 1u) to Rational(-32070283493, 1399680), - listOf(6u, 1u) to Rational(-22051101001, 1399680), - listOf(7u, 1u) to Rational(-126493427, 12960), - listOf(8u, 1u) to Rational(3050245, 864), - listOf(0u, 2u) to Rational(-1194654631, 345600), - listOf(1u, 2u) to Rational(-542961452671, 31104000), - listOf(2u, 2u) to Rational(-234000873607, 48988800), - listOf(3u, 2u) to Rational(140520538087, 3628800), - listOf(4u, 2u) to Rational(9215088876563, 130636800), - listOf(5u, 2u) to Rational(27590569647253, 293932800), - listOf(6u, 2u) to Rational(5129057792891, 97977600), - listOf(7u, 2u) to Rational(-106334191, 5103), - listOf(8u, 2u) to Rational(-1024113911, 435456), - listOf(0u, 3u) to Rational(76223843, 6000), - listOf(1u, 3u) to Rational(57425857357, 2592000), - listOf(2u, 3u) to Rational(-2044736497573, 46656000), - listOf(3u, 3u) to Rational(-26155810120031, 293932800), - listOf(4u, 3u) to Rational(-1064419459813, 6998400), - listOf(5u, 3u) to Rational(-753782018389, 4082400), - listOf(6u, 3u) to Rational(-291973360873, 2799360), - listOf(7u, 3u) to Rational(-46372122599, 816480), - listOf(8u, 3u) to Rational(3579859657, 653184), - listOf(0u, 4u) to Rational(-13374241901, 4320000), - listOf(1u, 4u) to Rational(306606499811, 54432000), - listOf(2u, 4u) to Rational(964267124745437, 13716864000), - listOf(3u, 4u) to Rational(21603809415373, 182891520), - listOf(4u, 4u) to Rational(1097860214654027, 6858432000), - listOf(5u, 4u) to Rational(161615254570669, 914457600), - listOf(6u, 4u) to Rational(758415239461, 22861440), - listOf(7u, 4u) to Rational(2585568355471, 274337280), - listOf(8u, 4u) to Rational(-70433747863, 9144576), - listOf(0u, 5u) to Rational(-9582586217, 2520000), - listOf(1u, 5u) to Rational(-19093471394171, 635040000), - listOf(2u, 5u) to Rational(-13010261944411, 381024000), - listOf(3u, 5u) to Rational(-259039825301861, 4572288000), - listOf(4u, 5u) to Rational(-305081119071079, 2286144000), - listOf(5u, 5u) to Rational(-1923114383311, 19595520), - listOf(6u, 5u) to Rational(-14181787253231, 228614400), - listOf(7u, 5u) to Rational(-3959584789, 4354560), - listOf(8u, 5u) to Rational(4691742523, 762048), - listOf(0u, 6u) to Rational(-588323437, 180000), - listOf(1u, 6u) to Rational(5952234691, 52920000), - listOf(2u, 6u) to Rational(21001851056959, 1088640000), - listOf(3u, 6u) to Rational(84668034357563, 2133734400), - listOf(4u, 6u) to Rational(2029754605811557, 25604812800), - listOf(5u, 6u) to Rational(11721216739823, 426746880), - listOf(6u, 6u) to Rational(-8275903187003, 2133734400), - listOf(7u, 6u) to Rational(-4730447299, 2540160), - listOf(8u, 6u) to Rational(-46069985, 21168), - listOf(0u, 7u) to Rational(-75711301, 117600), - listOf(1u, 7u) to Rational(32430417413, 7056000), - listOf(2u, 7u) to Rational(677988533153, 98784000), - listOf(3u, 7u) to Rational(-948417645827, 71124480), - listOf(4u, 7u) to Rational(-11320265215207, 711244800), - listOf(5u, 7u) to Rational(-676438627783, 50803200), - listOf(6u, 7u) to Rational(-7382274253, 1975680), - listOf(7u, 7u) to Rational(6505733, 2205), - listOf(8u, 7u) to Rational(450137, 882), - listOf(0u, 8u) to Rational(-8368253, 78400), - listOf(1u, 8u) to Rational(6833783, 117600), - listOf(2u, 8u) to Rational(4528971133, 5927040), - listOf(3u, 8u) to Rational(146252636617, 29635200), - listOf(4u, 8u) to Rational(8321882556889, 1659571200), - listOf(5u, 8u) to Rational(-4686033011, 1975680), - listOf(6u, 8u) to Rational(-1074445963, 987840), - listOf(7u, 8u) to Rational(-142313, 588), - listOf(8u, 8u) to Rational(-4281, 49) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-130778291, 76800), - listOf(1u) to Rational(-445270919, 230400), - listOf(2u) to Rational(44578444937, 14515200), - listOf(3u) to Rational(17329402153, 1555200), - listOf(4u) to Rational(89239926809, 2332800), - listOf(5u) to Rational(2808812267, 145152), - listOf(6u) to Rational(-21362661007, 725760), - listOf(7u) to Rational(-258455443, 2016), - listOf(8u) to Rational(-21454693, 96), - listOf(0u, 1u) to Rational(-1002137, 15360), - listOf(1u, 1u) to Rational(-1704849697, 430080), - listOf(2u, 1u) to Rational(-57657676789, 4838400), - listOf(3u, 1u) to Rational(-101331731, 89600), - listOf(4u, 1u) to Rational(5362280079329, 130636800), - listOf(5u, 1u) to Rational(4069896167053, 130636800), - listOf(6u, 1u) to Rational(12011514569, 544320), - listOf(7u, 1u) to Rational(138293195623, 725760), - listOf(8u, 1u) to Rational(6228779419, 48384), - listOf(0u, 2u) to Rational(-32395872823, 8064000), - listOf(1u, 2u) to Rational(-7398505523, 2304000), - listOf(2u, 2u) to Rational(95217051699521, 3048192000), - listOf(3u, 2u) to Rational(198026968812079, 3657830400), - listOf(4u, 2u) to Rational(4291645618499, 228614400), - listOf(5u, 2u) to Rational(-33211690942439, 914457600), - listOf(6u, 2u) to Rational(-637385538163153, 1371686400), - listOf(7u, 2u) to Rational(-138671528276273, 182891520), - listOf(8u, 2u) to Rational(-14566368751, 217728), - listOf(0u, 3u) to Rational(-10538718719, 2016000), - listOf(1u, 3u) to Rational(-1844485375199, 84672000), - listOf(2u, 3u) to Rational(103968665891, 12096000), - listOf(3u, 3u) to Rational(175402107278351, 1828915200), - listOf(4u, 3u) to Rational(8020699588879, 114307200), - listOf(5u, 3u) to Rational(3414841894991, 38102400), - listOf(6u, 3u) to Rational(1848405591611, 4665600), - listOf(7u, 3u) to Rational(39486708738989, 137168640), - listOf(8u, 3u) to Rational(255926289517, 9144576), - listOf(0u, 4u) to Rational(-655379564629, 105840000), - listOf(1u, 4u) to Rational(-208336039441, 127008000), - listOf(2u, 4u) to Rational(40173146771411, 1143072000), - listOf(3u, 4u) to Rational(150473493581239, 2667168000), - listOf(4u, 4u) to Rational(38833783990483, 1143072000), - listOf(5u, 4u) to Rational(-1963676248203053, 4800902400), - listOf(6u, 4u) to Rational(-2598759412825747, 3200601600), - listOf(7u, 4u) to Rational(-192895352019667, 1280240640), - listOf(8u, 4u) to Rational(3737382679, 6858432), - listOf(0u, 5u) to Rational(-16959378721, 1890000), - listOf(1u, 5u) to Rational(-1864802244743, 79380000), - listOf(2u, 5u) to Rational(13449261536489, 666792000), - listOf(3u, 5u) to Rational(215272234137329, 2667168000), - listOf(4u, 5u) to Rational(6040691379277, 83349000), - listOf(5u, 5u) to Rational(153687143525887, 800150400), - listOf(6u, 5u) to Rational(475602854903563, 2400451200), - listOf(7u, 5u) to Rational(27315599358749, 640120320), - listOf(8u, 5u) to Rational(-2630413357, 10668672), - listOf(0u, 6u) to Rational(-6654999511, 2646000), - listOf(1u, 6u) to Rational(-67885252327, 15876000), - listOf(2u, 6u) to Rational(5786776220983, 2667168000), - listOf(3u, 6u) to Rational(60615922629083, 1143072000), - listOf(4u, 6u) to Rational(-34703539637627407, 672126336000), - listOf(5u, 6u) to Rational(-744694192134101, 2240421120), - listOf(6u, 6u) to Rational(-1782470617231, 14817600), - listOf(7u, 6u) to Rational(59123208433, 8890560), - listOf(8u, 6u) to Rational(-141653, 5292), - listOf(0u, 7u) to Rational(-338051969, 441000), - listOf(1u, 7u) to Rational(468850013, 1764000), - listOf(2u, 7u) to Rational(2102343426101, 222264000), - listOf(3u, 7u) to Rational(7836130602007, 1333584000), - listOf(4u, 7u) to Rational(16239111865997, 746807040), - listOf(5u, 7u) to Rational(3824649185383, 88905600), - listOf(6u, 7u) to Rational(56058614459, 3457440), - listOf(7u, 7u) to Rational(-396766339, 493920), - listOf(8u, 7u) to Rational(-165147, 2744), - listOf(0u, 8u) to Rational(-3088619, 58800), - listOf(1u, 8u) to Rational(155343347, 88200), - listOf(2u, 8u) to Rational(100098736469, 7408800), - listOf(3u, 8u) to Rational(109725511381, 7408800), - listOf(4u, 8u) to Rational(-2431199641013, 59270400), - listOf(5u, 8u) to Rational(-102872383249, 3457440), - listOf(6u, 8u) to Rational(1449461309, 576240), - listOf(7u, 8u) to Rational(812775, 1372), - listOf(8u, 8u) to Rational(-16461, 343) - ), - NumberedPolynomialAsIs( - listOf() to Rational(164202773, 230400), - listOf(1u) to Rational(-70345303, 518400), - listOf(2u) to Rational(-4229702731, 4665600), - listOf(3u) to Rational(3262171027, 6998400), - listOf(4u) to Rational(-25423104169, 13996800), - listOf(5u) to Rational(64061869, 349920), - listOf(6u) to Rational(-1655878091, 116640), - listOf(7u) to Rational(-7991441, 648), - listOf(8u) to Rational(-502591, 18), - listOf(0u, 1u) to Rational(-8780429, 3840), - listOf(1u, 1u) to Rational(434272361, 115200), - listOf(2u, 1u) to Rational(429825727, 41472), - listOf(3u, 1u) to Rational(-10066790339, 6998400), - listOf(4u, 1u) to Rational(70022035471, 20995200), - listOf(5u, 1u) to Rational(-32070283493, 1399680), - listOf(6u, 1u) to Rational(-22051101001, 1399680), - listOf(7u, 1u) to Rational(-126493427, 12960), - listOf(8u, 1u) to Rational(3050245, 864), - listOf(0u, 2u) to Rational(-1194654631, 345600), - listOf(1u, 2u) to Rational(-542961452671, 31104000), - listOf(2u, 2u) to Rational(-234000873607, 48988800), - listOf(3u, 2u) to Rational(140520538087, 3628800), - listOf(4u, 2u) to Rational(9215088876563, 130636800), - listOf(5u, 2u) to Rational(27590569647253, 293932800), - listOf(6u, 2u) to Rational(5129057792891, 97977600), - listOf(7u, 2u) to Rational(-106334191, 5103), - listOf(8u, 2u) to Rational(-1024113911, 435456), - listOf(0u, 3u) to Rational(76223843, 6000), - listOf(1u, 3u) to Rational(57425857357, 2592000), - listOf(2u, 3u) to Rational(-2044736497573, 46656000), - listOf(3u, 3u) to Rational(-26155810120031, 293932800), - listOf(4u, 3u) to Rational(-1064419459813, 6998400), - listOf(5u, 3u) to Rational(-753782018389, 4082400), - listOf(6u, 3u) to Rational(-291973360873, 2799360), - listOf(7u, 3u) to Rational(-46372122599, 816480), - listOf(8u, 3u) to Rational(3579859657, 653184), - listOf(0u, 4u) to Rational(-13374241901, 4320000), - listOf(1u, 4u) to Rational(306606499811, 54432000), - listOf(2u, 4u) to Rational(964267124745437, 13716864000), - listOf(3u, 4u) to Rational(21603809415373, 182891520), - listOf(4u, 4u) to Rational(1097860214654027, 6858432000), - listOf(5u, 4u) to Rational(161615254570669, 914457600), - listOf(6u, 4u) to Rational(758415239461, 22861440), - listOf(7u, 4u) to Rational(2585568355471, 274337280), - listOf(8u, 4u) to Rational(-70433747863, 9144576), - listOf(0u, 5u) to Rational(-9582586217, 2520000), - listOf(1u, 5u) to Rational(-19093471394171, 635040000), - listOf(2u, 5u) to Rational(-13010261944411, 381024000), - listOf(3u, 5u) to Rational(-259039825301861, 4572288000), - listOf(4u, 5u) to Rational(-305081119071079, 2286144000), - listOf(5u, 5u) to Rational(-1923114383311, 19595520), - listOf(6u, 5u) to Rational(-14181787253231, 228614400), - listOf(7u, 5u) to Rational(-3959584789, 4354560), - listOf(8u, 5u) to Rational(4691742523, 762048), - listOf(0u, 6u) to Rational(-588323437, 180000), - listOf(1u, 6u) to Rational(5952234691, 52920000), - listOf(2u, 6u) to Rational(21001851056959, 1088640000), - listOf(3u, 6u) to Rational(84668034357563, 2133734400), - listOf(4u, 6u) to Rational(2029754605811557, 25604812800), - listOf(5u, 6u) to Rational(11721216739823, 426746880), - listOf(6u, 6u) to Rational(-8275903187003, 2133734400), - listOf(7u, 6u) to Rational(-4730447299, 2540160), - listOf(8u, 6u) to Rational(-46069985, 21168), - listOf(0u, 7u) to Rational(-75711301, 117600), - listOf(1u, 7u) to Rational(32430417413, 7056000), - listOf(2u, 7u) to Rational(677988533153, 98784000), - listOf(3u, 7u) to Rational(-948417645827, 71124480), - listOf(4u, 7u) to Rational(-11320265215207, 711244800), - listOf(5u, 7u) to Rational(-676438627783, 50803200), - listOf(6u, 7u) to Rational(-7382274253, 1975680), - listOf(7u, 7u) to Rational(6505733, 2205), - listOf(8u, 7u) to Rational(450137, 882), - listOf(0u, 8u) to Rational(-8368253, 78400), - listOf(1u, 8u) to Rational(6833783, 117600), - listOf(2u, 8u) to Rational(4528971133, 5927040), - listOf(3u, 8u) to Rational(146252636617, 29635200), - listOf(4u, 8u) to Rational(8321882556889, 1659571200), - listOf(5u, 8u) to Rational(-4686033011, 1975680), - listOf(6u, 8u) to Rational(-1074445963, 987840), - listOf(7u, 8u) to Rational(-142313, 588), - listOf(8u, 8u) to Rational(-4281, 49) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 8), - listOf(1u) to Rational(-12, 6), - listOf(2u) to Rational(7, 6), - listOf(0u, 1u) to Rational(-10, 4), - listOf(1u, 1u) to Rational(-7, 6), - listOf(2u, 1u) to Rational(8, 9), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-13, 4), - listOf(2u, 2u) to Rational(5, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(10, 6), - listOf(1u) to Rational(-18, 6), - listOf(2u) to Rational(5, 1), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(8, 4), - listOf(2u, 1u) to Rational(-4, 9), - listOf(0u, 2u) to Rational(-6, 5), - listOf(1u, 2u) to Rational(-15, 8), - listOf(2u, 2u) to Rational(-18, 5), - ) - ), - )), - "test 3'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(2303, 64), - listOf(1u) to Rational(31843, 192), - listOf(2u) to Rational(118891, 576), - listOf(3u) to Rational(94453, 168), - listOf(4u) to Rational(-179203, 1512), - listOf(5u) to Rational(-16979, 126), - listOf(6u) to Rational(-13499, 12), - listOf(0u, 1u) to Rational(-4767, 64), - listOf(1u, 1u) to Rational(-58689, 256), - listOf(2u, 1u) to Rational(-757333, 4032), - listOf(3u, 1u) to Rational(-4921205, 4032), - listOf(4u, 1u) to Rational(-2930815, 4032), - listOf(5u, 1u) to Rational(-398803, 1512), - listOf(6u, 1u) to Rational(18835, 36), - listOf(0u, 2u) to Rational(224101, 960), - listOf(1u, 2u) to Rational(9139699, 40320), - listOf(2u, 2u) to Rational(3848803, 5760), - listOf(3u, 2u) to Rational(93102371, 241920), - listOf(4u, 2u) to Rational(-65821229, 141120), - listOf(5u, 2u) to Rational(-15675899, 7056), - listOf(6u, 2u) to Rational(10459, 189), - listOf(0u, 3u) to Rational(2411, 16), - listOf(1u, 3u) to Rational(1294543, 10080), - listOf(2u, 3u) to Rational(-1740199, 1440), - listOf(3u, 3u) to Rational(-266994841, 282240), - listOf(4u, 3u) to Rational(-41261893, 211680), - listOf(5u, 3u) to Rational(1717357, 3528), - listOf(6u, 3u) to Rational(69, 14), - listOf(0u, 4u) to Rational(13231, 360), - listOf(1u, 4u) to Rational(4858831, 25200), - listOf(2u, 4u) to Rational(15565759, 75600), - listOf(3u, 4u) to Rational(-15583391, 35280), - listOf(4u, 4u) to Rational(-13345747, 11760), - listOf(5u, 4u) to Rational(140103, 686), - listOf(6u, 4u) to Rational(-765, 49) - ), - NumberedPolynomialAsIs( - listOf() to Rational(31409, 576), - listOf(1u) to Rational(-337099, 1728), - listOf(2u) to Rational(-211429, 1728), - listOf(3u) to Rational(-259241, 432), - listOf(4u) to Rational(-13777, 36), - listOf(5u) to Rational(-41389, 72), - listOf(6u) to Rational(-7679, 48), - listOf(0u, 1u) to Rational(-3269, 12), - listOf(1u, 1u) to Rational(629569, 864), - listOf(2u, 1u) to Rational(53867, 324), - listOf(3u, 1u) to Rational(2290577, 1728), - listOf(4u, 1u) to Rational(101507, 216), - listOf(5u, 1u) to Rational(213109, 288), - listOf(6u, 1u) to Rational(17927, 144), - listOf(0u, 2u) to Rational(314587, 1080), - listOf(1u, 2u) to Rational(-109771, 144), - listOf(2u, 2u) to Rational(-6469, 16), - listOf(3u, 2u) to Rational(-298291681, 181440), - listOf(4u, 2u) to Rational(-59147357, 48384), - listOf(5u, 2u) to Rational(-4982365, 6048), - listOf(6u, 2u) to Rational(-18727, 576), - listOf(0u, 3u) to Rational(12379, 90), - listOf(1u, 3u) to Rational(-542911, 1620), - listOf(2u, 3u) to Rational(143123, 1260), - listOf(3u, 3u) to Rational(9859177, 30240), - listOf(4u, 3u) to Rational(9312529, 20160), - listOf(5u, 3u) to Rational(207001, 672), - listOf(6u, 3u) to Rational(203, 24), - listOf(0u, 4u) to Rational(9442, 675), - listOf(1u, 4u) to Rational(-13729, 300), - listOf(2u, 4u) to Rational(-3490471, 25200), - listOf(3u, 4u) to Rational(-333031, 840), - listOf(4u, 4u) to Rational(-7572211, 47040), - listOf(5u, 4u) to Rational(-1189, 56), - listOf(6u, 4u) to Rational(-405, 196) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(2303, 64), - listOf(1u) to Rational(31843, 192), - listOf(2u) to Rational(118891, 576), - listOf(3u) to Rational(94453, 168), - listOf(4u) to Rational(-179203, 1512), - listOf(5u) to Rational(-16979, 126), - listOf(6u) to Rational(-13499, 12), - listOf(0u, 1u) to Rational(-4767, 64), - listOf(1u, 1u) to Rational(-58689, 256), - listOf(2u, 1u) to Rational(-757333, 4032), - listOf(3u, 1u) to Rational(-4921205, 4032), - listOf(4u, 1u) to Rational(-2930815, 4032), - listOf(5u, 1u) to Rational(-398803, 1512), - listOf(6u, 1u) to Rational(18835, 36), - listOf(0u, 2u) to Rational(224101, 960), - listOf(1u, 2u) to Rational(9139699, 40320), - listOf(2u, 2u) to Rational(3848803, 5760), - listOf(3u, 2u) to Rational(93102371, 241920), - listOf(4u, 2u) to Rational(-65821229, 141120), - listOf(5u, 2u) to Rational(-15675899, 7056), - listOf(6u, 2u) to Rational(10459, 189), - listOf(0u, 3u) to Rational(2411, 16), - listOf(1u, 3u) to Rational(1294543, 10080), - listOf(2u, 3u) to Rational(-1740199, 1440), - listOf(3u, 3u) to Rational(-266994841, 282240), - listOf(4u, 3u) to Rational(-41261893, 211680), - listOf(5u, 3u) to Rational(1717357, 3528), - listOf(6u, 3u) to Rational(69, 14), - listOf(0u, 4u) to Rational(13231, 360), - listOf(1u, 4u) to Rational(4858831, 25200), - listOf(2u, 4u) to Rational(15565759, 75600), - listOf(3u, 4u) to Rational(-15583391, 35280), - listOf(4u, 4u) to Rational(-13345747, 11760), - listOf(5u, 4u) to Rational(140103, 686), - listOf(6u, 4u) to Rational(-765, 49) - ), - NumberedPolynomialAsIs( - listOf() to Rational(31409, 576), - listOf(1u) to Rational(-337099, 1728), - listOf(2u) to Rational(-211429, 1728), - listOf(3u) to Rational(-259241, 432), - listOf(4u) to Rational(-13777, 36), - listOf(5u) to Rational(-41389, 72), - listOf(6u) to Rational(-7679, 48), - listOf(0u, 1u) to Rational(-3269, 12), - listOf(1u, 1u) to Rational(629569, 864), - listOf(2u, 1u) to Rational(53867, 324), - listOf(3u, 1u) to Rational(2290577, 1728), - listOf(4u, 1u) to Rational(101507, 216), - listOf(5u, 1u) to Rational(213109, 288), - listOf(6u, 1u) to Rational(17927, 144), - listOf(0u, 2u) to Rational(314587, 1080), - listOf(1u, 2u) to Rational(-109771, 144), - listOf(2u, 2u) to Rational(-6469, 16), - listOf(3u, 2u) to Rational(-298291681, 181440), - listOf(4u, 2u) to Rational(-59147357, 48384), - listOf(5u, 2u) to Rational(-4982365, 6048), - listOf(6u, 2u) to Rational(-18727, 576), - listOf(0u, 3u) to Rational(12379, 90), - listOf(1u, 3u) to Rational(-542911, 1620), - listOf(2u, 3u) to Rational(143123, 1260), - listOf(3u, 3u) to Rational(9859177, 30240), - listOf(4u, 3u) to Rational(9312529, 20160), - listOf(5u, 3u) to Rational(207001, 672), - listOf(6u, 3u) to Rational(203, 24), - listOf(0u, 4u) to Rational(9442, 675), - listOf(1u, 4u) to Rational(-13729, 300), - listOf(2u, 4u) to Rational(-3490471, 25200), - listOf(3u, 4u) to Rational(-333031, 840), - listOf(4u, 4u) to Rational(-7572211, 47040), - listOf(5u, 4u) to Rational(-1189, 56), - listOf(6u, 4u) to Rational(-405, 196) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 1 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 8), - listOf(1u) to Rational(-12, 6), - listOf(2u) to Rational(7, 6), - listOf(0u, 1u) to Rational(-10, 4), - listOf(1u, 1u) to Rational(-7, 6), - listOf(2u, 1u) to Rational(8, 9), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-13, 4), - listOf(2u, 2u) to Rational(5, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(10, 6), - listOf(1u) to Rational(-18, 6), - listOf(2u) to Rational(5, 1), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(8, 4), - listOf(2u, 1u) to Rational(-4, 9), - listOf(0u, 2u) to Rational(-6, 5), - listOf(1u, 2u) to Rational(-15, 8), - listOf(2u, 2u) to Rational(-18, 5), - ) - ), - )), - "test 4'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-506213, 2800), - listOf(1u) to Rational(9859, 315), - listOf(2u) to Rational(17384377, 11340), - listOf(3u) to Rational(-9662, 63), - listOf(4u) to Rational(-12563, 4), - listOf(0u, 1u) to Rational(-486293, 22400), - listOf(1u, 1u) to Rational(-6530947, 25200), - listOf(2u, 1u) to Rational(866125, 18144), - listOf(3u, 1u) to Rational(2948747, 2520), - listOf(4u, 1u) to Rational(1196611, 2016), - listOf(0u, 2u) to Rational(-20266021, 117600), - listOf(1u, 2u) to Rational(26656339, 44100), - listOf(2u, 2u) to Rational(19499183, 18144), - listOf(3u, 2u) to Rational(-19801849, 7560), - listOf(4u, 2u) to Rational(-2639635, 1296), - listOf(0u, 3u) to Rational(-5017697, 29400), - listOf(1u, 3u) to Rational(-606007, 1575), - listOf(2u, 3u) to Rational(127494487, 132300), - listOf(3u, 3u) to Rational(166567, 105), - listOf(4u, 3u) to Rational(486403, 18144), - listOf(0u, 4u) to Rational(-32182, 735), - listOf(1u, 4u) to Rational(2420671, 8820), - listOf(2u, 4u) to Rational(-12619193, 26460), - listOf(3u, 4u) to Rational(-6823067, 5670), - listOf(4u, 4u) to Rational(-2311693, 13608), - listOf(0u, 5u) to Rational(-13324, 245), - listOf(1u, 5u) to Rational(1966, 35), - listOf(2u, 5u) to Rational(1052719, 2520), - listOf(3u, 5u) to Rational(19153, 270), - listOf(4u, 5u) to Rational(701, 54), - listOf(0u, 6u) to Rational(4647, 196), - listOf(1u, 6u) to Rational(2197, 28), - listOf(2u, 6u) to Rational(-43853, 336), - listOf(3u, 6u) to Rational(-301, 3), - listOf(4u, 6u) to Rational(34, 3) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2843, 1600), - listOf(1u) to Rational(-1483, 240), - listOf(2u) to Rational(110623, 1296), - listOf(3u) to Rational(1265, 72), - listOf(4u) to Rational(-5011, 16), - listOf(0u, 1u) to Rational(47743, 1800), - listOf(1u, 1u) to Rational(619229, 32400), - listOf(2u, 1u) to Rational(-5978369, 58320), - listOf(3u, 1u) to Rational(-86081, 1620), - listOf(4u, 1u) to Rational(6325, 72), - listOf(0u, 2u) to Rational(110951, 3360), - listOf(1u, 2u) to Rational(-9550649, 302400), - listOf(2u, 2u) to Rational(6542933, 85050), - listOf(3u, 2u) to Rational(4708291, 38880), - listOf(4u, 2u) to Rational(-433327, 1296), - listOf(0u, 3u) to Rational(56143, 600), - listOf(1u, 3u) to Rational(94243, 720), - listOf(2u, 3u) to Rational(-46779139, 226800), - listOf(3u, 3u) to Rational(-6948253, 12960), - listOf(4u, 3u) to Rational(-260261, 486), - listOf(0u, 4u) to Rational(-3205317, 19600), - listOf(1u, 4u) to Rational(-201253, 1050), - listOf(2u, 4u) to Rational(332192677, 302400), - listOf(3u, 4u) to Rational(351511, 360), - listOf(4u, 4u) to Rational(-40547, 81), - listOf(0u, 5u) to Rational(-65421, 1960), - listOf(1u, 5u) to Rational(-10118, 35), - listOf(2u, 5u) to Rational(-4341709, 10080), - listOf(3u, 5u) to Rational(-91703, 360), - listOf(4u, 5u) to Rational(-85, 9), - listOf(0u, 6u) to Rational(-25965, 784), - listOf(1u, 6u) to Rational(3351, 16), - listOf(2u, 6u) to Rational(595159, 1344), - listOf(3u, 6u) to Rational(-1381, 12), - listOf(4u, 6u) to Rational(-155, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-506213, 2800), - listOf(1u) to Rational(9859, 315), - listOf(2u) to Rational(17384377, 11340), - listOf(3u) to Rational(-9662, 63), - listOf(4u) to Rational(-12563, 4), - listOf(0u, 1u) to Rational(-486293, 22400), - listOf(1u, 1u) to Rational(-6530947, 25200), - listOf(2u, 1u) to Rational(866125, 18144), - listOf(3u, 1u) to Rational(2948747, 2520), - listOf(4u, 1u) to Rational(1196611, 2016), - listOf(0u, 2u) to Rational(-20266021, 117600), - listOf(1u, 2u) to Rational(26656339, 44100), - listOf(2u, 2u) to Rational(19499183, 18144), - listOf(3u, 2u) to Rational(-19801849, 7560), - listOf(4u, 2u) to Rational(-2639635, 1296), - listOf(0u, 3u) to Rational(-5017697, 29400), - listOf(1u, 3u) to Rational(-606007, 1575), - listOf(2u, 3u) to Rational(127494487, 132300), - listOf(3u, 3u) to Rational(166567, 105), - listOf(4u, 3u) to Rational(486403, 18144), - listOf(0u, 4u) to Rational(-32182, 735), - listOf(1u, 4u) to Rational(2420671, 8820), - listOf(2u, 4u) to Rational(-12619193, 26460), - listOf(3u, 4u) to Rational(-6823067, 5670), - listOf(4u, 4u) to Rational(-2311693, 13608), - listOf(0u, 5u) to Rational(-13324, 245), - listOf(1u, 5u) to Rational(1966, 35), - listOf(2u, 5u) to Rational(1052719, 2520), - listOf(3u, 5u) to Rational(19153, 270), - listOf(4u, 5u) to Rational(701, 54), - listOf(0u, 6u) to Rational(4647, 196), - listOf(1u, 6u) to Rational(2197, 28), - listOf(2u, 6u) to Rational(-43853, 336), - listOf(3u, 6u) to Rational(-301, 3), - listOf(4u, 6u) to Rational(34, 3) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2843, 1600), - listOf(1u) to Rational(-1483, 240), - listOf(2u) to Rational(110623, 1296), - listOf(3u) to Rational(1265, 72), - listOf(4u) to Rational(-5011, 16), - listOf(0u, 1u) to Rational(47743, 1800), - listOf(1u, 1u) to Rational(619229, 32400), - listOf(2u, 1u) to Rational(-5978369, 58320), - listOf(3u, 1u) to Rational(-86081, 1620), - listOf(4u, 1u) to Rational(6325, 72), - listOf(0u, 2u) to Rational(110951, 3360), - listOf(1u, 2u) to Rational(-9550649, 302400), - listOf(2u, 2u) to Rational(6542933, 85050), - listOf(3u, 2u) to Rational(4708291, 38880), - listOf(4u, 2u) to Rational(-433327, 1296), - listOf(0u, 3u) to Rational(56143, 600), - listOf(1u, 3u) to Rational(94243, 720), - listOf(2u, 3u) to Rational(-46779139, 226800), - listOf(3u, 3u) to Rational(-6948253, 12960), - listOf(4u, 3u) to Rational(-260261, 486), - listOf(0u, 4u) to Rational(-3205317, 19600), - listOf(1u, 4u) to Rational(-201253, 1050), - listOf(2u, 4u) to Rational(332192677, 302400), - listOf(3u, 4u) to Rational(351511, 360), - listOf(4u, 4u) to Rational(-40547, 81), - listOf(0u, 5u) to Rational(-65421, 1960), - listOf(1u, 5u) to Rational(-10118, 35), - listOf(2u, 5u) to Rational(-4341709, 10080), - listOf(3u, 5u) to Rational(-91703, 360), - listOf(4u, 5u) to Rational(-85, 9), - listOf(0u, 6u) to Rational(-25965, 784), - listOf(1u, 6u) to Rational(3351, 16), - listOf(2u, 6u) to Rational(595159, 1344), - listOf(3u, 6u) to Rational(-1381, 12), - listOf(4u, 6u) to Rational(-155, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 0 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 8), - listOf(1u) to Rational(-12, 6), - listOf(2u) to Rational(7, 6), - listOf(0u, 1u) to Rational(-10, 4), - listOf(1u, 1u) to Rational(-7, 6), - listOf(2u, 1u) to Rational(8, 9), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-13, 4), - listOf(2u, 2u) to Rational(5, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(10, 6), - listOf(1u) to Rational(-18, 6), - listOf(2u) to Rational(5, 1), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(8, 4), - listOf(2u, 1u) to Rational(-4, 9), - listOf(0u, 2u) to Rational(-6, 5), - listOf(1u, 2u) to Rational(-15, 8), - listOf(2u, 2u) to Rational(-18, 5), - ) - ), - )), - "test 5'" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf>()), - "test 6" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, mapOf( - 5 to NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 8), - listOf(1u) to Rational(-12, 6), - listOf(2u) to Rational(7, 6), - listOf(0u, 1u) to Rational(-10, 4), - listOf(1u, 1u) to Rational(-7, 6), - listOf(2u, 1u) to Rational(8, 9), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-13, 4), - listOf(2u, 2u) to Rational(5, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(10, 6), - listOf(1u) to Rational(-18, 6), - listOf(2u) to Rational(5, 1), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(8, 4), - listOf(2u, 1u) to Rational(-4, 9), - listOf(0u, 2u) to Rational(-6, 5), - listOf(1u, 2u) to Rational(-15, 8), - listOf(2u, 2u) to Rational(-18, 5), - ) - ), - )), - "test 6'" - ) - } - @Test - fun test_Polynomial_substitute_Double_Buffer() { - assertEquals( - NumberedPolynomialAsIs(emptyList() to 0.0), - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ).substitute(bufferOf( - 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf()), - 0.001, - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(0u, 1u) to 0.4561746111587508, - listOf(0u, 2u) to 0.2700930201481795, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf( - 0.0, - )), - 0.001, - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.047895694399743, - listOf(0u, 1u) to 0.859913883275481, - listOf(0u, 2u) to 0.2327806735363575, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf( - 0.4846192734143442, - )), - 0.001, - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.934530767358133, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - )), - 0.001, - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.934530767358133, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - 0.9211194782050933 - )), - 0.001, - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to 1.934530767358133, - ), - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substitute(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - 0.9211194782050933, - 0.4752854632152105 - )), - 0.001, - "test 7" - ) - } - @Test - fun test_Polynomial_substitute_Constant_Buffer() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, bufferOf( - Rational(1) - )), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf()), - "test 2" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-83, 50), - listOf(0u, 1u) to Rational(29, 25), - listOf(0u, 2u) to Rational(3, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - Rational(-2, 5), - )), - "test 3" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5%2C+y+%3D+12%2F9 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(143, 150) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - )), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(143, 150) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - Rational(57, 179), - )), - "test 5" - ) - // https://www.wolframalpha.com/input?i=%28%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2%29+p%5E8+where+x+%3D+q%2Fp%2C+y+%3D+x%5E3%2C+p+%3D+-2%2F5%2C+q+%3D+12%2F9 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(47639065216, 2562890625) - ), - NumberedPolynomialAsIs( - listOf(8u) to Rational(-3, 2), - listOf(7u, 1u) to Rational(8, 6), - listOf(6u, 2u) to Rational(14, 6), - listOf(5u, 3u) to Rational(-3, 1), - listOf(4u, 4u) to Rational(-19, 2), - listOf(3u, 5u) to Rational(9, 4), - listOf(2u, 6u) to Rational(5, 5), - listOf(1u, 7u) to Rational(18, 9), - listOf(0u, 8u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - )), - "test 6" - ) - } - @Test - fun test_Polynomial_substitute_Polynomial_Buffer() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - )), - "test 1" - ) - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-5%2F1+s+%2B+2%2F8+t%2C+y+%3D+11%2F7+t - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(0u, 1u) to Rational(-92, 21), - listOf(0u, 2u) to Rational(-2627, 2352), - listOf(0u, 3u) to Rational(4565, 3136), - listOf(0u, 4u) to Rational(605, 1568), - listOf(1u) to Rational(-20, 3), - listOf(1u, 1u) to Rational(1445, 21), - listOf(1u, 2u) to Rational(-13145, 392), - listOf(1u, 3u) to Rational(-3025, 196), - listOf(2u) to Rational(175, 3), - listOf(2u, 1u) to Rational(2475, 28), - listOf(2u, 2u) to Rational(15125, 98), - listOf(3u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf(1u) to Rational(-5, 1), - listOf(0u, 1u) to Rational(2, 8), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(0, 5), - listOf(0u, 1u) to Rational(11, 7), - ), - )), - "test 2" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = (-9/2 + 2/7 s + 9/1 s^2) + (13/1 + -1/8 s + 2/8 s^2) t + (19/4 + 15/7 s + -19/4 s^2) t^2 - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(48583, 336), - listOf(2u) to Rational(-913477, 1568), - listOf(3u) to Rational(-967567, 672), - listOf(4u) to Rational(4722043, 1344), - listOf(5u) to Rational(8855, 2), - listOf(6u) to Rational(-311971, 32), - listOf(7u) to Rational(-17325, 4), - listOf(8u) to Rational(19845, 2), - listOf(0u, 1u) to Rational(-827, 4), - listOf(1u, 1u) to Rational(191927, 840), - listOf(2u, 1u) to Rational(9592627, 2352), - listOf(3u, 1u) to Rational(-105400711, 53760), - listOf(4u, 1u) to Rational(-10054101459, 439040), - listOf(5u, 1u) to Rational(2127351, 128), - listOf(6u, 1u) to Rational(116680973, 3136), - listOf(7u, 1u) to Rational(-220445, 7), - listOf(8u, 1u) to Rational(-2655, 4), - listOf(0u, 2u) to Rational(30567, 100), - listOf(1u, 2u) to Rational(-156284953, 39200), - listOf(2u, 2u) to Rational(-57661541711, 6585600), - listOf(3u, 2u) to Rational(131931579, 3136), - listOf(4u, 2u) to Rational(98818124791, 3512320), - listOf(5u, 2u) to Rational(-94458855053, 878080), - listOf(6u, 2u) to Rational(13937705305, 1229312), - listOf(7u, 2u) to Rational(335706887, 21952), - listOf(8u, 2u) to Rational(23549165, 1568), - listOf(0u, 3u) to Rational(111367, 1400), - listOf(1u, 3u) to Rational(4937369, 700), - listOf(2u, 3u) to Rational(-4449423711, 274400), - listOf(3u, 3u) to Rational(-351873325703, 4390400), - listOf(4u, 3u) to Rational(23495875029, 307328), - listOf(5u, 3u) to Rational(17576300919, 878080), - listOf(6u, 3u) to Rational(230316993, 12544), - listOf(7u, 3u) to Rational(-191130515, 21952), - listOf(8u, 3u) to Rational(332435, 392), - listOf(0u, 4u) to Rational(-275084, 1225), - listOf(1u, 4u) to Rational(-266774603, 137200), - listOf(2u, 4u) to Rational(2176279167121, 30732800), - listOf(3u, 4u) to Rational(10904913303, 2195200), - listOf(4u, 4u) to Rational(-10769286147, 2195200), - listOf(5u, 4u) to Rational(-26277119793, 439040), - listOf(6u, 4u) to Rational(25859735869, 6146560), - listOf(7u, 4u) to Rational(38906289, 2744), - listOf(8u, 4u) to Rational(-3072025, 392), - listOf(0u, 5u) to Rational(9573, 98), - listOf(1u, 5u) to Rational(-4154651399, 548800), - listOf(2u, 5u) to Rational(3446069019, 548800), - listOf(3u, 5u) to Rational(-7851500623, 137200), - listOf(4u, 5u) to Rational(-53205142903, 1920800), - listOf(5u, 5u) to Rational(-31953611, 3430), - listOf(6u, 5u) to Rational(1447380313, 109760), - listOf(7u, 5u) to Rational(764158625, 21952), - listOf(8u, 5u) to Rational(1153515, 784), - listOf(0u, 6u) to Rational(1722351, 7840), - listOf(1u, 6u) to Rational(-164554821, 109760), - listOf(2u, 6u) to Rational(-79096147243, 7683200), - listOf(3u, 6u) to Rational(-624721089, 15680), - listOf(4u, 6u) to Rational(11147305567, 548800), - listOf(5u, 6u) to Rational(8318333679, 109760), - listOf(6u, 6u) to Rational(32981871553, 1536640), - listOf(7u, 6u) to Rational(-225359619, 21952), - listOf(8u, 6u) to Rational(-3973995, 392), - listOf(0u, 7u) to Rational(67203, 784), - listOf(1u, 7u) to Rational(39281469, 54880), - listOf(2u, 7u) to Rational(70162551, 27440), - listOf(3u, 7u) to Rational(413630709, 54880), - listOf(4u, 7u) to Rational(4640410269, 192080), - listOf(5u, 7u) to Rational(802712247, 54880), - listOf(6u, 7u) to Rational(-473517603, 27440), - listOf(7u, 7u) to Rational(-17055459, 1568), - listOf(8u, 7u) to Rational(-12825, 14), - listOf(0u, 8u) to Rational(16245, 1568), - listOf(1u, 8u) to Rational(503253, 2744), - listOf(2u, 8u) to Rational(125292591, 96040), - listOf(3u, 8u) to Rational(12033171, 2744), - listOf(4u, 8u) to Rational(154352673, 27440), - listOf(5u, 8u) to Rational(-1302291, 392), - listOf(6u, 8u) to Rational(-20265741, 1960), - listOf(7u, 8u) to Rational(-26163, 56), - listOf(8u, 8u) to Rational(146205, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 3), - listOf(1u) to Rational(5, 2), - listOf(2u) to Rational(13, 7), - listOf(0u, 1u) to Rational(16, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(6, 1), - listOf(0u, 2u) to Rational(-14, 3), - listOf(1u, 2u) to Rational(-2, 7), - listOf(2u, 2u) to Rational(-10, 8), - ) - )), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(129, 4), - listOf(1u) to Rational(48583, 336), - listOf(2u) to Rational(-913477, 1568), - listOf(3u) to Rational(-967567, 672), - listOf(4u) to Rational(4722043, 1344), - listOf(5u) to Rational(8855, 2), - listOf(6u) to Rational(-311971, 32), - listOf(7u) to Rational(-17325, 4), - listOf(8u) to Rational(19845, 2), - listOf(0u, 1u) to Rational(-827, 4), - listOf(1u, 1u) to Rational(191927, 840), - listOf(2u, 1u) to Rational(9592627, 2352), - listOf(3u, 1u) to Rational(-105400711, 53760), - listOf(4u, 1u) to Rational(-10054101459, 439040), - listOf(5u, 1u) to Rational(2127351, 128), - listOf(6u, 1u) to Rational(116680973, 3136), - listOf(7u, 1u) to Rational(-220445, 7), - listOf(8u, 1u) to Rational(-2655, 4), - listOf(0u, 2u) to Rational(30567, 100), - listOf(1u, 2u) to Rational(-156284953, 39200), - listOf(2u, 2u) to Rational(-57661541711, 6585600), - listOf(3u, 2u) to Rational(131931579, 3136), - listOf(4u, 2u) to Rational(98818124791, 3512320), - listOf(5u, 2u) to Rational(-94458855053, 878080), - listOf(6u, 2u) to Rational(13937705305, 1229312), - listOf(7u, 2u) to Rational(335706887, 21952), - listOf(8u, 2u) to Rational(23549165, 1568), - listOf(0u, 3u) to Rational(111367, 1400), - listOf(1u, 3u) to Rational(4937369, 700), - listOf(2u, 3u) to Rational(-4449423711, 274400), - listOf(3u, 3u) to Rational(-351873325703, 4390400), - listOf(4u, 3u) to Rational(23495875029, 307328), - listOf(5u, 3u) to Rational(17576300919, 878080), - listOf(6u, 3u) to Rational(230316993, 12544), - listOf(7u, 3u) to Rational(-191130515, 21952), - listOf(8u, 3u) to Rational(332435, 392), - listOf(0u, 4u) to Rational(-275084, 1225), - listOf(1u, 4u) to Rational(-266774603, 137200), - listOf(2u, 4u) to Rational(2176279167121, 30732800), - listOf(3u, 4u) to Rational(10904913303, 2195200), - listOf(4u, 4u) to Rational(-10769286147, 2195200), - listOf(5u, 4u) to Rational(-26277119793, 439040), - listOf(6u, 4u) to Rational(25859735869, 6146560), - listOf(7u, 4u) to Rational(38906289, 2744), - listOf(8u, 4u) to Rational(-3072025, 392), - listOf(0u, 5u) to Rational(9573, 98), - listOf(1u, 5u) to Rational(-4154651399, 548800), - listOf(2u, 5u) to Rational(3446069019, 548800), - listOf(3u, 5u) to Rational(-7851500623, 137200), - listOf(4u, 5u) to Rational(-53205142903, 1920800), - listOf(5u, 5u) to Rational(-31953611, 3430), - listOf(6u, 5u) to Rational(1447380313, 109760), - listOf(7u, 5u) to Rational(764158625, 21952), - listOf(8u, 5u) to Rational(1153515, 784), - listOf(0u, 6u) to Rational(1722351, 7840), - listOf(1u, 6u) to Rational(-164554821, 109760), - listOf(2u, 6u) to Rational(-79096147243, 7683200), - listOf(3u, 6u) to Rational(-624721089, 15680), - listOf(4u, 6u) to Rational(11147305567, 548800), - listOf(5u, 6u) to Rational(8318333679, 109760), - listOf(6u, 6u) to Rational(32981871553, 1536640), - listOf(7u, 6u) to Rational(-225359619, 21952), - listOf(8u, 6u) to Rational(-3973995, 392), - listOf(0u, 7u) to Rational(67203, 784), - listOf(1u, 7u) to Rational(39281469, 54880), - listOf(2u, 7u) to Rational(70162551, 27440), - listOf(3u, 7u) to Rational(413630709, 54880), - listOf(4u, 7u) to Rational(4640410269, 192080), - listOf(5u, 7u) to Rational(802712247, 54880), - listOf(6u, 7u) to Rational(-473517603, 27440), - listOf(7u, 7u) to Rational(-17055459, 1568), - listOf(8u, 7u) to Rational(-12825, 14), - listOf(0u, 8u) to Rational(16245, 1568), - listOf(1u, 8u) to Rational(503253, 2744), - listOf(2u, 8u) to Rational(125292591, 96040), - listOf(3u, 8u) to Rational(12033171, 2744), - listOf(4u, 8u) to Rational(154352673, 27440), - listOf(5u, 8u) to Rational(-1302291, 392), - listOf(6u, 8u) to Rational(-20265741, 1960), - listOf(7u, 8u) to Rational(-26163, 56), - listOf(8u, 8u) to Rational(146205, 32), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-9, 2), - listOf(1u) to Rational(2, 7), - listOf(2u) to Rational(9, 1), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-1, 8), - listOf(2u, 1u) to Rational(2, 8), - listOf(0u, 2u) to Rational(19, 4), - listOf(1u, 2u) to Rational(15, 7), - listOf(2u, 2u) to Rational(-19, 4), - ), - )), - "test 4" - ) - // (-3/2 + 8/6 x + 14/6 x^2) + (-3/1 + -19/2 x + 9/4 x^2) y + (5/5 + 18/9 x + 5/2 x^2) y^2 where x = (0/6 + 14/8 s + -14/2 s^2) + (-3/5 + 11/1 s + 3/7 s^2) t + (-3/7 + -18/5 s + -9/1 s^2) t^2, y = t - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(7, 3), - listOf(2u) to Rational(-35, 16), - listOf(3u) to Rational(-343, 6), - listOf(4u) to Rational(343, 3), - listOf(0u, 1u) to Rational(-19, 5), - listOf(1u, 1u) to Rational(-823, 120), - listOf(2u, 1u) to Rational(1232417, 6720), - listOf(3u, 1u) to Rational(-9863, 24), - listOf(4u, 1u) to Rational(385, 4), - listOf(0u, 2u) to Rational(2439, 350), - listOf(1u, 2u) to Rational(-5793, 40), - listOf(2u, 2u) to Rational(1172113, 3360), - listOf(3u, 2u) to Rational(-13531, 40), - listOf(4u, 2u) to Rational(2824, 7), - listOf(0u, 3u) to Rational(3417, 700), - listOf(1u, 3u) to Rational(1191, 200), - listOf(2u, 3u) to Rational(8383, 28), - listOf(3u, 3u) to Rational(-220279, 280), - listOf(4u, 3u) to Rational(49179, 196), - listOf(0u, 4u) to Rational(57, 35), - listOf(1u, 4u) to Rational(-33771, 700), - listOf(2u, 4u) to Rational(196279, 1225), - listOf(3u, 4u) to Rational(-32259, 140), - listOf(4u, 4u) to Rational(23868, 49), - listOf(0u, 5u) to Rational(333, 196), - listOf(1u, 5u) to Rational(-204, 35), - listOf(2u, 5u) to Rational(-307233, 2450), - listOf(3u, 5u) to Rational(-12492, 35), - listOf(4u, 5u) to Rational(4563, 28), - listOf(0u, 6u) to Rational(45, 98), - listOf(1u, 6u) to Rational(54, 7), - listOf(2u, 6u) to Rational(1809, 35), - listOf(3u, 6u) to Rational(162), - listOf(4u, 6u) to Rational(405, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(0, 6), - listOf(1u) to Rational(14, 8), - listOf(2u) to Rational(-14, 2), - listOf(0u, 1u) to Rational(-3, 5), - listOf(1u, 1u) to Rational(11, 1), - listOf(2u, 1u) to Rational(3, 7), - listOf(0u, 2u) to Rational(-3, 7), - listOf(1u, 2u) to Rational(-18, 5), - listOf(2u, 2u) to Rational(-9, 1), - ), - )), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substitute(RationalField, bufferOf>()), - "test 6" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_Polynomial_substitute_RationalFunction_Buffer() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(4u) to Rational(-194071, 4900), - listOf(3u, 1u) to Rational(394811, 225), - listOf(2u, 2u) to Rational(-444183161, 66150), - listOf(1u, 3u) to Rational(70537618, 59535), - listOf(0u, 4u) to Rational(9655504, 2835), - ), - NumberedPolynomialAsIs( - listOf(4u) to Rational(9, 1), - listOf(3u, 1u) to Rational(61, 1), - listOf(2u, 2u) to Rational(2137, 36), - listOf(1u, 3u) to Rational(-1342, 9), - listOf(0u, 4u) to Rational(484, 9), - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(17, 7), - listOf(0u, 1u) to Rational(-13, 1), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(-18, 6), - listOf(0u, 1u) to Rational(11, 6), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(18, 5), - listOf(0u, 1u) to Rational(-16, 3), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(-4, 1), - ) - ), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-6443599, 10000), - listOf(1u) to Rational(166251223, 210000), - listOf(2u) to Rational(-4606805099, 3528000), - listOf(3u) to Rational(51204379, 19600), - listOf(4u) to Rational(-529045460659, 277830000), - listOf(5u) to Rational(2630836709, 1488375), - listOf(6u) to Rational(-42675691369, 25004700), - listOf(7u) to Rational(495825223, 1250235), - listOf(8u) to Rational(-22531756, 1750329), - listOf(0u, 1u) to Rational(-2526552797, 420000), - listOf(1u, 1u) to Rational(31108840471, 2520000), - listOf(2u, 1u) to Rational(-4789740847, 1102500), - listOf(3u, 1u) to Rational(186594307807, 11340000), - listOf(4u, 1u) to Rational(-11677815943, 1488375), - listOf(5u, 1u) to Rational(-181118486447, 27783000), - listOf(6u, 1u) to Rational(-16123292162, 14586075), - listOf(7u, 1u) to Rational(-140339343808, 26254935), - listOf(8u, 1u) to Rational(4570171616, 5250987), - listOf(0u, 2u) to Rational(-181436530573, 10080000), - listOf(1u, 2u) to Rational(6700437957491, 105840000), - listOf(2u, 2u) to Rational(-3527267461, 1417500), - listOf(3u, 2u) to Rational(-38084563451, 5556600), - listOf(4u, 2u) to Rational(-565662040631, 13891500), - listOf(5u, 2u) to Rational(-35479071126397, 583443000), - listOf(6u, 2u) to Rational(-11717559078469, 525098700), - listOf(7u, 2u) to Rational(-2043385293517, 225042300), - listOf(8u, 2u) to Rational(-3644439630451, 551353635), - listOf(0u, 3u) to Rational(-1760423269, 126000), - listOf(1u, 3u) to Rational(310176758299, 2352000), - listOf(2u, 3u) to Rational(-907229584837, 21168000), - listOf(3u, 3u) to Rational(-16717135885963, 95256000), - listOf(4u, 3u) to Rational(-43762928025353, 333396000), - listOf(5u, 3u) to Rational(-328427480571607, 3000564000), - listOf(6u, 3u) to Rational(-7722675917197, 210039480), - listOf(7u, 3u) to Rational(1713350137019, 1225230300), - listOf(8u, 3u) to Rational(156695935643, 31505922), - listOf(0u, 4u) to Rational(18362364269, 1008000), - listOf(1u, 4u) to Rational(955674858553, 10584000), - listOf(2u, 4u) to Rational(-71937470607371, 444528000), - listOf(3u, 4u) to Rational(-34097985615163, 95256000), - listOf(4u, 4u) to Rational(-340736178775883, 2000376000), - listOf(5u, 4u) to Rational(-511324523441897, 10501974000), - listOf(6u, 4u) to Rational(-125375649409151, 8821658160), - listOf(7u, 4u) to Rational(-2813518533421, 1575296100), - listOf(8u, 4u) to Rational(-17044089109, 5250987), - listOf(0u, 5u) to Rational(600086461, 20160), - listOf(1u, 5u) to Rational(-18959931367, 423360), - listOf(2u, 5u) to Rational(-9178804929607, 44452800), - listOf(3u, 5u) to Rational(-1460114275979, 5334336), - listOf(4u, 5u) to Rational(-342533479090169, 4200789600), - listOf(5u, 5u) to Rational(20335453022963, 4200789600), - listOf(6u, 5u) to Rational(-21649775090197, 6301184400), - listOf(7u, 5u) to Rational(-197301716069, 131274675), - listOf(8u, 5u) to Rational(18711357470, 15752961), - listOf(0u, 6u) to Rational(621417991, 100800), - listOf(1u, 6u) to Rational(-159236792977, 2116800), - listOf(2u, 6u) to Rational(-6602528890883, 66679200), - listOf(3u, 6u) to Rational(-1086091664047, 19051200), - listOf(4u, 6u) to Rational(3769375009003, 1680315840), - listOf(5u, 6u) to Rational(-12920385574769, 1050197400), - listOf(6u, 6u) to Rational(-90219591809287, 6301184400), - listOf(7u, 6u) to Rational(656361553391, 1575296100), - listOf(8u, 6u) to Rational(757900793, 2250423), - listOf(0u, 7u) to Rational(-100770017, 15120), - listOf(1u, 7u) to Rational(-316364851, 17640), - listOf(2u, 7u) to Rational(-85118560057, 6667920), - listOf(3u, 7u) to Rational(6286563719, 416745), - listOf(4u, 7u) to Rational(26803885301, 1714608), - listOf(5u, 7u) to Rational(-13767154393, 4286520), - listOf(6u, 7u) to Rational(-3875138933, 1224720), - listOf(7u, 7u) to Rational(65193755, 333396), - listOf(8u, 7u) to Rational(90974351, 2500470), - listOf(0u, 8u) to Rational(-3182197, 1260), - listOf(1u, 8u) to Rational(24899923, 8820), - listOf(2u, 8u) to Rational(-19999556, 19845), - listOf(3u, 8u) to Rational(3276587, 3969), - listOf(4u, 8u) to Rational(13719549239, 5000940), - listOf(5u, 8u) to Rational(-961839938, 1250235), - listOf(6u, 8u) to Rational(-198184871, 833490), - listOf(7u, 8u) to Rational(230659711, 5000940), - listOf(8u, 8u) to Rational(292447, 35721) - ), - NumberedPolynomialAsIs( - listOf() to Rational(9, 100), - listOf(1u) to Rational(-21, 50), - listOf(2u) to Rational(293, 700), - listOf(3u) to Rational(29, 210), - listOf(4u) to Rational(3233, 8820), - listOf(5u) to Rational(-289, 441), - listOf(6u) to Rational(-1, 9), - listOf(7u) to Rational(-20, 441), - listOf(8u) to Rational(100, 441), - listOf(0u, 1u) to Rational(-57, 80), - listOf(1u, 1u) to Rational(-121, 400), - listOf(2u, 1u) to Rational(37117, 8400), - listOf(3u, 1u) to Rational(-4853, 3150), - listOf(4u, 1u) to Rational(1166203, 132300), - listOf(5u, 1u) to Rational(-2708, 567), - listOf(6u, 1u) to Rational(-287159, 416745), - listOf(7u, 1u) to Rational(-478204, 83349), - listOf(8u, 1u) to Rational(176320, 83349), - listOf(0u, 2u) to Rational(-6239, 6400), - listOf(1u, 2u) to Rational(264211, 11200), - listOf(2u, 2u) to Rational(-1591999, 100800), - listOf(3u, 2u) to Rational(12450091, 529200), - listOf(4u, 2u) to Rational(9230759, 226800), - listOf(5u, 2u) to Rational(18995554, 2083725), - listOf(6u, 2u) to Rational(136706258, 6251175), - listOf(7u, 2u) to Rational(-120907496, 3750705), - listOf(8u, 2u) to Rational(117200176, 15752961), - listOf(0u, 3u) to Rational(5653, 320), - listOf(1u, 3u) to Rational(-130853, 8400), - listOf(2u, 3u) to Rational(-20939327, 151200), - listOf(3u, 3u) to Rational(2566691, 25200), - listOf(4u, 3u) to Rational(-68441519, 476280), - listOf(5u, 3u) to Rational(2462904247, 12502350), - listOf(6u, 3u) to Rational(353667161, 18753525), - listOf(7u, 3u) to Rational(-1689134372, 26254935), - listOf(8u, 3u) to Rational(35084104, 2250423), - listOf(0u, 4u) to Rational(-3587, 300), - listOf(1u, 4u) to Rational(-10513243, 33600), - listOf(2u, 4u) to Rational(30766733, 176400), - listOf(3u, 4u) to Rational(-65680021, 198450), - listOf(4u, 4u) to Rational(-8108910547, 20003760), - listOf(5u, 4u) to Rational(2922125159, 6251175), - listOf(6u, 4u) to Rational(-4245279943, 131274675), - listOf(7u, 4u) to Rational(-371946872, 3750705), - listOf(8u, 4u) to Rational(61286752, 2250423), - listOf(0u, 5u) to Rational(-20477, 160), - listOf(1u, 5u) to Rational(215741, 1120), - listOf(2u, 5u) to Rational(30785843, 31752), - listOf(3u, 5u) to Rational(-357495959, 317520), - listOf(4u, 5u) to Rational(-1611242993, 10001880), - listOf(5u, 5u) to Rational(345925495, 500094), - listOf(6u, 5u) to Rational(-755948411, 3750705), - listOf(7u, 5u) to Rational(-108643496, 1250235), - listOf(8u, 5u) to Rational(1122512, 35721), - listOf(0u, 6u) to Rational(358037, 2880), - listOf(1u, 6u) to Rational(3895837, 3360), - listOf(2u, 6u) to Rational(359419201, 1270080), - listOf(3u, 6u) to Rational(-158522587, 105840), - listOf(4u, 6u) to Rational(10909002599, 20003760), - listOf(5u, 6u) to Rational(76846972, 138915), - listOf(6u, 6u) to Rational(-327696553, 1250235), - listOf(7u, 6u) to Rational(-1687328, 35721), - listOf(8u, 6u) to Rational(1016836, 35721), - listOf(0u, 7u) to Rational(658, 3), - listOf(1u, 7u) to Rational(48035, 168), - listOf(2u, 7u) to Rational(-5777875, 5292), - listOf(3u, 7u) to Rational(-7893899, 10584), - listOf(4u, 7u) to Rational(10191652, 11907), - listOf(5u, 7u) to Rational(2920121, 23814), - listOf(6u, 7u) to Rational(-2699780, 11907), - listOf(7u, 7u) to Rational(4556, 441), - listOf(8u, 7u) to Rational(3440, 189), - listOf(0u, 8u) to Rational(64, 1), - listOf(1u, 8u) to Rational(-808, 7), - listOf(2u, 8u) to Rational(-360895, 1764), - listOf(3u, 8u) to Rational(257657, 882), - listOf(4u, 8u) to Rational(3779917, 15876), - listOf(5u, 8u) to Rational(-610279, 3969), - listOf(6u, 8u) to Rational(-25091, 441), - listOf(7u, 8u) to Rational(9560, 567), - listOf(8u, 8u) to Rational(400, 81) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 9), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(10, 9), - listOf(0u, 1u) to Rational(13, 3), - listOf(1u, 1u) to Rational(-12, 4), - listOf(2u, 1u) to Rational(3, 6), - listOf(0u, 2u) to Rational(2, 9), - listOf(1u, 2u) to Rational(7, 3), - listOf(2u, 2u) to Rational(16, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 2), - listOf(1u) to Rational(6, 2), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 1), - listOf(1u, 1u) to Rational(-11, 3), - listOf(2u, 1u) to Rational(7, 5), - listOf(0u, 2u) to Rational(8, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(17, 4), - ) - ) - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-6443599, 10000), - listOf(1u) to Rational(166251223, 210000), - listOf(2u) to Rational(-4606805099, 3528000), - listOf(3u) to Rational(51204379, 19600), - listOf(4u) to Rational(-529045460659, 277830000), - listOf(5u) to Rational(2630836709, 1488375), - listOf(6u) to Rational(-42675691369, 25004700), - listOf(7u) to Rational(495825223, 1250235), - listOf(8u) to Rational(-22531756, 1750329), - listOf(0u, 1u) to Rational(-2526552797, 420000), - listOf(1u, 1u) to Rational(31108840471, 2520000), - listOf(2u, 1u) to Rational(-4789740847, 1102500), - listOf(3u, 1u) to Rational(186594307807, 11340000), - listOf(4u, 1u) to Rational(-11677815943, 1488375), - listOf(5u, 1u) to Rational(-181118486447, 27783000), - listOf(6u, 1u) to Rational(-16123292162, 14586075), - listOf(7u, 1u) to Rational(-140339343808, 26254935), - listOf(8u, 1u) to Rational(4570171616, 5250987), - listOf(0u, 2u) to Rational(-181436530573, 10080000), - listOf(1u, 2u) to Rational(6700437957491, 105840000), - listOf(2u, 2u) to Rational(-3527267461, 1417500), - listOf(3u, 2u) to Rational(-38084563451, 5556600), - listOf(4u, 2u) to Rational(-565662040631, 13891500), - listOf(5u, 2u) to Rational(-35479071126397, 583443000), - listOf(6u, 2u) to Rational(-11717559078469, 525098700), - listOf(7u, 2u) to Rational(-2043385293517, 225042300), - listOf(8u, 2u) to Rational(-3644439630451, 551353635), - listOf(0u, 3u) to Rational(-1760423269, 126000), - listOf(1u, 3u) to Rational(310176758299, 2352000), - listOf(2u, 3u) to Rational(-907229584837, 21168000), - listOf(3u, 3u) to Rational(-16717135885963, 95256000), - listOf(4u, 3u) to Rational(-43762928025353, 333396000), - listOf(5u, 3u) to Rational(-328427480571607, 3000564000), - listOf(6u, 3u) to Rational(-7722675917197, 210039480), - listOf(7u, 3u) to Rational(1713350137019, 1225230300), - listOf(8u, 3u) to Rational(156695935643, 31505922), - listOf(0u, 4u) to Rational(18362364269, 1008000), - listOf(1u, 4u) to Rational(955674858553, 10584000), - listOf(2u, 4u) to Rational(-71937470607371, 444528000), - listOf(3u, 4u) to Rational(-34097985615163, 95256000), - listOf(4u, 4u) to Rational(-340736178775883, 2000376000), - listOf(5u, 4u) to Rational(-511324523441897, 10501974000), - listOf(6u, 4u) to Rational(-125375649409151, 8821658160), - listOf(7u, 4u) to Rational(-2813518533421, 1575296100), - listOf(8u, 4u) to Rational(-17044089109, 5250987), - listOf(0u, 5u) to Rational(600086461, 20160), - listOf(1u, 5u) to Rational(-18959931367, 423360), - listOf(2u, 5u) to Rational(-9178804929607, 44452800), - listOf(3u, 5u) to Rational(-1460114275979, 5334336), - listOf(4u, 5u) to Rational(-342533479090169, 4200789600), - listOf(5u, 5u) to Rational(20335453022963, 4200789600), - listOf(6u, 5u) to Rational(-21649775090197, 6301184400), - listOf(7u, 5u) to Rational(-197301716069, 131274675), - listOf(8u, 5u) to Rational(18711357470, 15752961), - listOf(0u, 6u) to Rational(621417991, 100800), - listOf(1u, 6u) to Rational(-159236792977, 2116800), - listOf(2u, 6u) to Rational(-6602528890883, 66679200), - listOf(3u, 6u) to Rational(-1086091664047, 19051200), - listOf(4u, 6u) to Rational(3769375009003, 1680315840), - listOf(5u, 6u) to Rational(-12920385574769, 1050197400), - listOf(6u, 6u) to Rational(-90219591809287, 6301184400), - listOf(7u, 6u) to Rational(656361553391, 1575296100), - listOf(8u, 6u) to Rational(757900793, 2250423), - listOf(0u, 7u) to Rational(-100770017, 15120), - listOf(1u, 7u) to Rational(-316364851, 17640), - listOf(2u, 7u) to Rational(-85118560057, 6667920), - listOf(3u, 7u) to Rational(6286563719, 416745), - listOf(4u, 7u) to Rational(26803885301, 1714608), - listOf(5u, 7u) to Rational(-13767154393, 4286520), - listOf(6u, 7u) to Rational(-3875138933, 1224720), - listOf(7u, 7u) to Rational(65193755, 333396), - listOf(8u, 7u) to Rational(90974351, 2500470), - listOf(0u, 8u) to Rational(-3182197, 1260), - listOf(1u, 8u) to Rational(24899923, 8820), - listOf(2u, 8u) to Rational(-19999556, 19845), - listOf(3u, 8u) to Rational(3276587, 3969), - listOf(4u, 8u) to Rational(13719549239, 5000940), - listOf(5u, 8u) to Rational(-961839938, 1250235), - listOf(6u, 8u) to Rational(-198184871, 833490), - listOf(7u, 8u) to Rational(230659711, 5000940), - listOf(8u, 8u) to Rational(292447, 35721) - ), - NumberedPolynomialAsIs( - listOf() to Rational(9, 100), - listOf(1u) to Rational(-21, 50), - listOf(2u) to Rational(293, 700), - listOf(3u) to Rational(29, 210), - listOf(4u) to Rational(3233, 8820), - listOf(5u) to Rational(-289, 441), - listOf(6u) to Rational(-1, 9), - listOf(7u) to Rational(-20, 441), - listOf(8u) to Rational(100, 441), - listOf(0u, 1u) to Rational(-57, 80), - listOf(1u, 1u) to Rational(-121, 400), - listOf(2u, 1u) to Rational(37117, 8400), - listOf(3u, 1u) to Rational(-4853, 3150), - listOf(4u, 1u) to Rational(1166203, 132300), - listOf(5u, 1u) to Rational(-2708, 567), - listOf(6u, 1u) to Rational(-287159, 416745), - listOf(7u, 1u) to Rational(-478204, 83349), - listOf(8u, 1u) to Rational(176320, 83349), - listOf(0u, 2u) to Rational(-6239, 6400), - listOf(1u, 2u) to Rational(264211, 11200), - listOf(2u, 2u) to Rational(-1591999, 100800), - listOf(3u, 2u) to Rational(12450091, 529200), - listOf(4u, 2u) to Rational(9230759, 226800), - listOf(5u, 2u) to Rational(18995554, 2083725), - listOf(6u, 2u) to Rational(136706258, 6251175), - listOf(7u, 2u) to Rational(-120907496, 3750705), - listOf(8u, 2u) to Rational(117200176, 15752961), - listOf(0u, 3u) to Rational(5653, 320), - listOf(1u, 3u) to Rational(-130853, 8400), - listOf(2u, 3u) to Rational(-20939327, 151200), - listOf(3u, 3u) to Rational(2566691, 25200), - listOf(4u, 3u) to Rational(-68441519, 476280), - listOf(5u, 3u) to Rational(2462904247, 12502350), - listOf(6u, 3u) to Rational(353667161, 18753525), - listOf(7u, 3u) to Rational(-1689134372, 26254935), - listOf(8u, 3u) to Rational(35084104, 2250423), - listOf(0u, 4u) to Rational(-3587, 300), - listOf(1u, 4u) to Rational(-10513243, 33600), - listOf(2u, 4u) to Rational(30766733, 176400), - listOf(3u, 4u) to Rational(-65680021, 198450), - listOf(4u, 4u) to Rational(-8108910547, 20003760), - listOf(5u, 4u) to Rational(2922125159, 6251175), - listOf(6u, 4u) to Rational(-4245279943, 131274675), - listOf(7u, 4u) to Rational(-371946872, 3750705), - listOf(8u, 4u) to Rational(61286752, 2250423), - listOf(0u, 5u) to Rational(-20477, 160), - listOf(1u, 5u) to Rational(215741, 1120), - listOf(2u, 5u) to Rational(30785843, 31752), - listOf(3u, 5u) to Rational(-357495959, 317520), - listOf(4u, 5u) to Rational(-1611242993, 10001880), - listOf(5u, 5u) to Rational(345925495, 500094), - listOf(6u, 5u) to Rational(-755948411, 3750705), - listOf(7u, 5u) to Rational(-108643496, 1250235), - listOf(8u, 5u) to Rational(1122512, 35721), - listOf(0u, 6u) to Rational(358037, 2880), - listOf(1u, 6u) to Rational(3895837, 3360), - listOf(2u, 6u) to Rational(359419201, 1270080), - listOf(3u, 6u) to Rational(-158522587, 105840), - listOf(4u, 6u) to Rational(10909002599, 20003760), - listOf(5u, 6u) to Rational(76846972, 138915), - listOf(6u, 6u) to Rational(-327696553, 1250235), - listOf(7u, 6u) to Rational(-1687328, 35721), - listOf(8u, 6u) to Rational(1016836, 35721), - listOf(0u, 7u) to Rational(658, 3), - listOf(1u, 7u) to Rational(48035, 168), - listOf(2u, 7u) to Rational(-5777875, 5292), - listOf(3u, 7u) to Rational(-7893899, 10584), - listOf(4u, 7u) to Rational(10191652, 11907), - listOf(5u, 7u) to Rational(2920121, 23814), - listOf(6u, 7u) to Rational(-2699780, 11907), - listOf(7u, 7u) to Rational(4556, 441), - listOf(8u, 7u) to Rational(3440, 189), - listOf(0u, 8u) to Rational(64, 1), - listOf(1u, 8u) to Rational(-808, 7), - listOf(2u, 8u) to Rational(-360895, 1764), - listOf(3u, 8u) to Rational(257657, 882), - listOf(4u, 8u) to Rational(3779917, 15876), - listOf(5u, 8u) to Rational(-610279, 3969), - listOf(6u, 8u) to Rational(-25091, 441), - listOf(7u, 8u) to Rational(9560, 567), - listOf(8u, 8u) to Rational(400, 81) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(18, 5), - listOf(1u) to Rational(-17, 5), - listOf(2u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(-5, 1), - listOf(2u, 1u) to Rational(-9, 1), - listOf(0u, 2u) to Rational(-8, 8), - listOf(1u, 2u) to Rational(2, 7), - listOf(2u, 2u) to Rational(-13, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-4, 8), - listOf(1u) to Rational(15, 9), - listOf(2u) to Rational(-10, 9), - listOf(0u, 1u) to Rational(5, 3), - listOf(1u, 1u) to Rational(4, 1), - listOf(2u, 1u) to Rational(-2, 7), - listOf(0u, 2u) to Rational(2, 2), - listOf(1u, 2u) to Rational(-5, 7), - listOf(2u, 2u) to Rational(-18, 9), - ) - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-66677, 3500), - listOf(1u) to Rational(-206281, 10500), - listOf(2u) to Rational(-412567, 7056), - listOf(3u) to Rational(-310081, 11025), - listOf(4u) to Rational(-575996, 15435), - listOf(0u, 1u) to Rational(-573701, 4200), - listOf(1u, 1u) to Rational(-2239001, 25200), - listOf(2u, 1u) to Rational(-8817889, 132300), - listOf(3u, 1u) to Rational(2317919, 44100), - listOf(4u, 1u) to Rational(1169471, 6615), - listOf(0u, 2u) to Rational(-4057819, 33600), - listOf(1u, 2u) to Rational(1373311, 12600), - listOf(2u, 2u) to Rational(32433493, 52920), - listOf(3u, 2u) to Rational(4998053, 33075), - listOf(4u, 2u) to Rational(-2147779, 8820), - listOf(0u, 3u) to Rational(2018481, 2240), - listOf(1u, 3u) to Rational(941713, 1440), - listOf(2u, 3u) to Rational(183749, 6615), - listOf(3u, 3u) to Rational(-4631023, 15876), - listOf(4u, 3u) to Rational(25609336, 178605), - listOf(0u, 4u) to Rational(11886431, 6720), - listOf(1u, 4u) to Rational(18433, 504), - listOf(2u, 4u) to Rational(-39613331, 45360), - listOf(3u, 4u) to Rational(681619, 5670), - listOf(4u, 4u) to Rational(-864841, 20412), - listOf(0u, 5u) to Rational(343535, 1008), - listOf(1u, 5u) to Rational(-33583, 72), - listOf(2u, 5u) to Rational(1194625, 9072), - listOf(3u, 5u) to Rational(-62917, 2268), - listOf(4u, 5u) to Rational(157645, 10206), - listOf(0u, 6u) to Rational(-1381, 3), - listOf(1u, 6u) to Rational(919, 36), - listOf(2u, 6u) to Rational(-3053, 36), - listOf(3u, 6u) to Rational(2125, 324), - listOf(4u, 6u) to Rational(-236, 243) - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(1, 4), - listOf(1u) to Rational(-5, 3), - listOf(2u) to Rational(35, 9), - listOf(3u) to Rational(-100, 27), - listOf(4u) to Rational(100, 81), - listOf(0u, 1u) to Rational(-5, 3), - listOf(1u, 1u) to Rational(14, 9), - listOf(2u, 1u) to Rational(1874, 189), - listOf(3u, 1u) to Rational(-620, 63), - listOf(4u, 1u) to Rational(40, 63), - listOf(0u, 2u) to Rational(16, 9), - listOf(1u, 2u) to Rational(365, 21), - listOf(2u, 2u) to Rational(112, 9), - listOf(3u, 2u) to Rational(-464, 63), - listOf(4u, 2u) to Rational(1996, 441), - listOf(0u, 3u) to Rational(10, 3), - listOf(1u, 3u) to Rational(118, 21), - listOf(2u, 3u) to Rational(-272, 21), - listOf(3u, 3u) to Rational(-764, 49), - listOf(4u, 3u) to Rational(8, 7), - listOf(0u, 4u) to Rational(1, 1), - listOf(1u, 4u) to Rational(-10, 7), - listOf(2u, 4u) to Rational(-171, 49), - listOf(3u, 4u) to Rational(20, 7), - listOf(4u, 4u) to Rational(4, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(17, 5), - listOf(1u) to Rational(11, 6), - listOf(2u) to Rational(14, 3), - listOf(0u, 1u) to Rational(17, 1), - listOf(1u, 1u) to Rational(12, 3), - listOf(2u, 1u) to Rational(-6, 2), - listOf(0u, 2u) to Rational(17, 1), - listOf(1u, 2u) to Rational(-4, 3), - listOf(2u, 2u) to Rational(2, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(3, 5), - listOf(1u) to Rational(3, 5), - listOf(2u) to Rational(3, 7), - listOf(0u, 1u) to Rational(-3, 8), - listOf(1u, 1u) to Rational(-1, 1), - listOf(2u, 1u) to Rational(17, 9), - listOf(0u, 2u) to Rational(-8, 1), - listOf(1u, 2u) to Rational(6, 4), - listOf(2u, 2u) to Rational(10, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ), - NumberedPolynomialAsIs(listOf() to Rational(0, 1), - listOf() to Rational(0, 1) - ) - ), - NumberedPolynomialAsIs( - listOf() to Rational(15, 7), - listOf(1u) to Rational(1, 5), - listOf(2u) to Rational(-7, 4), - listOf(0u, 1u) to Rational(-1, 9), - listOf(1u, 1u) to Rational(-2, 7), - listOf(2u, 1u) to Rational(17, 3), - listOf(0u, 2u) to Rational(2, 6), - listOf(1u, 2u) to Rational(-17, 6), - listOf(2u, 2u) to Rational(-6, 2), - ).substitute(RationalField, bufferOf>()), - "test 6" - ) - } - @Test - fun test_RationalFunction_substitute_Double_Buffer() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs(emptyList() to 0.0), - NumberedPolynomialAsIs(emptyList() to 1.0), - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ), - NumberedPolynomialAsIs( - listOf() to 1.0, - ) - ).substitute(bufferOf( - 1.0 - )), - 0.001, - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(bufferOf()), - 0.001, - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 151.1502229133916, - listOf(0u, 1u) to -262.3790170577034, - listOf(0u, 2u) to 102.5097937392923, - ), - NumberedPolynomialAsIs( - listOf() to -367.9969733169944, - listOf(0u, 1u) to 112.4911133334554, - listOf(0u, 2u) to -469.755906895345, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(bufferOf( - -8.11707689492641, - )), - 0.001, - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 7.321261307532708, - ), - NumberedPolynomialAsIs( - listOf() to -575.6325831127576, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(bufferOf( - -8.11707689492641, - 0.795265651276015, - )), - 0.001, - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 7.321261307532708, - ), - NumberedPolynomialAsIs( - listOf() to -575.6325831127576, - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substitute(bufferOf( - -8.11707689492641, - 0.795265651276015, - 0.9211194782050933 - )), - 0.001, - "test 5" - ) - } - @Test - fun test_RationalFunction_substitute_Constant_Buffer() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ).substitute(RationalField, bufferOf( - Rational(1) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(22047, 2450), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2204953, 147000), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, bufferOf( - Rational(7, 5), - Rational(-13, 7), - Rational(-16, 4), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(22047, 2450), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2204953, 147000), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, bufferOf( - Rational(7, 5), - Rational(-13, 7), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-939, 200), - listOf(0u, 1u) to Rational(123, 50), - listOf(0u, 2u) to Rational(1059, 200) - ), - NumberedPolynomialAsIs( - listOf() to Rational(121, 25), - listOf(0u, 1u) to Rational(-949, 375), - listOf(0u, 2u) to Rational(-1423, 200) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, bufferOf( - Rational(7, 5), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substitute(RationalField, bufferOf()), - "test 5" - ) - } - @Test - fun test_RationalFunction_substitute_Polynomial_Buffer() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(211, 4), - listOf(2u) to Rational(88, 3), - listOf(3u) to Rational(-63, 8), - listOf(4u) to Rational(441, 16), - listOf(0u, 1u) to Rational(-671, 15), - listOf(1u, 1u) to Rational(-551, 21), - listOf(2u, 1u) to Rational(279, 25), - listOf(3u, 1u) to Rational(231, 20), - listOf(0u, 2u) to Rational(-1436, 1575), - listOf(1u, 2u) to Rational(2471, 250), - listOf(2u, 2u) to Rational(-4919, 100), - listOf(0u, 3u) to Rational(-1464, 125), - listOf(1u, 3u) to Rational(-264, 25), - listOf(0u, 4u) to Rational(576, 25), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(-9, 4), - listOf(2u) to Rational(943, 8), - listOf(3u) to Rational(117, 8), - listOf(4u) to Rational(147, 16), - listOf(0u, 1u) to Rational(289, 90), - listOf(1u, 1u) to Rational(-2692, 15), - listOf(2u, 1u) to Rational(-1629, 140), - listOf(3u, 1u) to Rational(77, 20), - listOf(0u, 2u) to Rational(6187, 75), - listOf(1u, 2u) to Rational(-2879, 175), - listOf(2u, 2u) to Rational(-4919, 300), - listOf(0u, 3u) to Rational(336, 25), - listOf(1u, 3u) to Rational(-88, 25), - listOf(0u, 4u) to Rational(192, 25), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf(1u) to Rational(3, 2), - listOf(0u, 1u) to Rational(8, 5), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-3, 1), - ) - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1202861, 210), - listOf(1u) to Rational(-215117, 45), - listOf(2u) to Rational(10889651, 19845), - listOf(3u) to Rational(-3503956, 6615), - listOf(4u) to Rational(809066, 2205), - listOf(5u) to Rational(-9056, 735), - listOf(6u) to Rational(5396, 315), - listOf(7u) to Rational(-752, 147), - listOf(8u) to Rational(16, 49), - listOf(0u, 1u) to Rational(1738469, 1470), - listOf(1u, 1u) to Rational(-926238703, 52920), - listOf(2u, 1u) to Rational(-44113982, 6615), - listOf(3u, 1u) to Rational(10423519, 5292), - listOf(4u, 1u) to Rational(3769712, 2205), - listOf(5u, 1u) to Rational(8905046, 6615), - listOf(6u, 1u) to Rational(1186972, 6615), - listOf(7u, 1u) to Rational(22124, 441), - listOf(8u, 1u) to Rational(-1504, 147), - listOf(0u, 2u) to Rational(-54723628, 2205), - listOf(1u, 2u) to Rational(70109407, 1323), - listOf(2u, 2u) to Rational(151072591, 17640), - listOf(3u, 2u) to Rational(1216428107, 52920), - listOf(4u, 2u) to Rational(2587873193, 317520), - listOf(5u, 2u) to Rational(393536369, 79380), - listOf(6u, 2u) to Rational(137614937, 79380), - listOf(7u, 2u) to Rational(566866, 1323), - listOf(8u, 2u) to Rational(41848, 441), - listOf(0u, 3u) to Rational(-19470406, 2205), - listOf(1u, 3u) to Rational(72514195, 882), - listOf(2u, 3u) to Rational(-78090707, 1764), - listOf(3u, 3u) to Rational(-1988237707, 26460), - listOf(4u, 3u) to Rational(-802137919, 17640), - listOf(5u, 3u) to Rational(-139989463, 5880), - listOf(6u, 3u) to Rational(-26066641, 3780), - listOf(7u, 3u) to Rational(-2363369, 1323), - listOf(8u, 3u) to Rational(-108280, 441), - listOf(0u, 4u) to Rational(14878516, 441), - listOf(1u, 4u) to Rational(-253416724, 2205), - listOf(2u, 4u) to Rational(16699157, 840), - listOf(3u, 4u) to Rational(-105220979, 13230), - listOf(4u, 4u) to Rational(208266383, 5880), - listOf(5u, 4u) to Rational(650135309, 26460), - listOf(6u, 4u) to Rational(123808663, 11760), - listOf(7u, 4u) to Rational(8563385, 2646), - listOf(8u, 4u) to Rational(19721, 49), - listOf(0u, 5u) to Rational(675645, 49), - listOf(1u, 5u) to Rational(-70554077, 588), - listOf(2u, 5u) to Rational(157884029, 980), - listOf(3u, 5u) to Rational(489548623, 4410), - listOf(4u, 5u) to Rational(148540519, 17640), - listOf(5u, 5u) to Rational(-5559551, 392), - listOf(6u, 5u) to Rational(-18335711, 1470), - listOf(7u, 5u) to Rational(-38437, 9), - listOf(8u, 5u) to Rational(-29620, 63), - listOf(0u, 6u) to Rational(-727625, 49), - listOf(1u, 6u) to Rational(7046685, 98), - listOf(2u, 6u) to Rational(-334814231, 7056), - listOf(3u, 6u) to Rational(-243971737, 17640), - listOf(4u, 6u) to Rational(-571116659, 35280), - listOf(5u, 6u) to Rational(567538, 315), - listOf(6u, 6u) to Rational(3199768, 315), - listOf(7u, 6u) to Rational(227744, 63), - listOf(8u, 6u) to Rational(23116, 63), - listOf(0u, 7u) to Rational(-27500, 7), - listOf(1u, 7u) to Rational(120125, 3), - listOf(2u, 7u) to Rational(-279200, 3), - listOf(3u, 7u) to Rational(-100160, 7), - listOf(4u, 7u) to Rational(920452, 21), - listOf(5u, 7u) to Rational(226481, 21), - listOf(6u, 7u) to Rational(-34428, 7), - listOf(7u, 7u) to Rational(-6232, 3), - listOf(8u, 7u) to Rational(-608, 3), - listOf(0u, 8u) to Rational(2500, 1), - listOf(1u, 8u) to Rational(-19000, 1), - listOf(2u, 8u) to Rational(37900, 1), - listOf(3u, 8u) to Rational(-1840, 1), - listOf(4u, 8u) to Rational(-17876, 1), - listOf(5u, 8u) to Rational(-1240, 1), - listOf(6u, 8u) to Rational(2788, 1), - listOf(7u, 8u) to Rational(800, 1), - listOf(8u, 8u) to Rational(64, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(162487, 63), - listOf(1u) to Rational(-92713, 54), - listOf(2u) to Rational(802436, 1323), - listOf(3u) to Rational(-55088, 441), - listOf(4u) to Rational(1404034, 9261), - listOf(5u) to Rational(-5804, 1029), - listOf(6u) to Rational(51556, 9261), - listOf(7u) to Rational(-752, 441), - listOf(8u) to Rational(16, 147), - listOf(0u, 1u) to Rational(296071, 441), - listOf(1u, 1u) to Rational(-4991281, 882), - listOf(2u, 1u) to Rational(-18702811, 9261), - listOf(3u, 1u) to Rational(40759043, 27783), - listOf(4u, 1u) to Rational(19768501, 27783), - listOf(5u, 1u) to Rational(14307337, 27783), - listOf(6u, 1u) to Rational(1655684, 27783), - listOf(7u, 1u) to Rational(22124, 1323), - listOf(8u, 1u) to Rational(-1504, 441), - listOf(0u, 2u) to Rational(-27667474, 3087), - listOf(1u, 2u) to Rational(265605901, 12348), - listOf(2u, 2u) to Rational(160360775, 98784), - listOf(3u, 2u) to Rational(1169992093, 148176), - listOf(4u, 2u) to Rational(3978014077, 1333584), - listOf(5u, 2u) to Rational(567058123, 333396), - listOf(6u, 2u) to Rational(205132579, 333396), - listOf(7u, 2u) to Rational(566866, 3969), - listOf(8u, 2u) to Rational(41848, 1323), - listOf(0u, 3u) to Rational(-2228822, 1029), - listOf(1u, 3u) to Rational(80179390, 3087), - listOf(2u, 3u) to Rational(-1378630487, 74088), - listOf(3u, 3u) to Rational(-3385811693, 111132), - listOf(4u, 3u) to Rational(-820686977, 49392), - listOf(5u, 3u) to Rational(-89101027, 10584), - listOf(6u, 3u) to Rational(-37847387, 15876), - listOf(7u, 3u) to Rational(-2363369, 3969), - listOf(8u, 3u) to Rational(-108280, 1323), - listOf(0u, 4u) to Rational(12619982, 1029), - listOf(1u, 4u) to Rational(-277723177, 6174), - listOf(2u, 4u) to Rational(649414169, 49392), - listOf(3u, 4u) to Rational(14457595, 63504), - listOf(4u, 4u) to Rational(139270339, 10584), - listOf(5u, 4u) to Rational(140367961, 15876), - listOf(6u, 4u) to Rational(25467083, 7056), - listOf(7u, 4u) to Rational(8563385, 7938), - listOf(8u, 4u) to Rational(19721, 147), - listOf(0u, 5u) to Rational(643850, 147), - listOf(1u, 5u) to Rational(-11818025, 294), - listOf(2u, 5u) to Rational(33963203, 588), - listOf(3u, 5u) to Rational(207216235, 5292), - listOf(4u, 5u) to Rational(2861021, 1512), - listOf(5u, 5u) to Rational(-6302335, 1176), - listOf(6u, 5u) to Rational(-3738587, 882), - listOf(7u, 5u) to Rational(-38437, 27), - listOf(8u, 5u) to Rational(-29620, 189), - listOf(0u, 6u) to Rational(-248725, 49), - listOf(1u, 6u) to Rational(2478535, 98), - listOf(2u, 6u) to Rational(-399721367, 21168), - listOf(3u, 6u) to Rational(-54309317, 10584), - listOf(4u, 6u) to Rational(-95398327, 21168), - listOf(5u, 6u) to Rational(173750, 189), - listOf(6u, 6u) to Rational(92216, 27), - listOf(7u, 6u) to Rational(227744, 189), - listOf(8u, 6u) to Rational(23116, 189), - listOf(0u, 7u) to Rational(-27500, 21), - listOf(1u, 7u) to Rational(120125, 9), - listOf(2u, 7u) to Rational(-279200, 9), - listOf(3u, 7u) to Rational(-100160, 21), - listOf(4u, 7u) to Rational(920452, 63), - listOf(5u, 7u) to Rational(226481, 63), - listOf(6u, 7u) to Rational(-11476, 7), - listOf(7u, 7u) to Rational(-6232, 9), - listOf(8u, 7u) to Rational(-608, 9), - listOf(0u, 8u) to Rational(2500, 3), - listOf(1u, 8u) to Rational(-19000, 3), - listOf(2u, 8u) to Rational(37900, 3), - listOf(3u, 8u) to Rational(-1840, 3), - listOf(4u, 8u) to Rational(-17876, 3), - listOf(5u, 8u) to Rational(-1240, 3), - listOf(6u, 8u) to Rational(2788, 3), - listOf(7u, 8u) to Rational(800, 3), - listOf(8u, 8u) to Rational(64, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 1), - listOf(1u) to Rational(-9, 8), - listOf(2u) to Rational(17, 5), - listOf(0u, 1u) to Rational(-2, 3), - listOf(1u, 1u) to Rational(1, 5), - listOf(2u, 1u) to Rational(-11, 7), - listOf(0u, 2u) to Rational(13, 6), - listOf(1u, 2u) to Rational(-15, 2), - listOf(2u, 2u) to Rational(-14, 4), - ) - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1202861, 210), - listOf(1u) to Rational(-215117, 45), - listOf(2u) to Rational(10889651, 19845), - listOf(3u) to Rational(-3503956, 6615), - listOf(4u) to Rational(809066, 2205), - listOf(5u) to Rational(-9056, 735), - listOf(6u) to Rational(5396, 315), - listOf(7u) to Rational(-752, 147), - listOf(8u) to Rational(16, 49), - listOf(0u, 1u) to Rational(1738469, 1470), - listOf(1u, 1u) to Rational(-926238703, 52920), - listOf(2u, 1u) to Rational(-44113982, 6615), - listOf(3u, 1u) to Rational(10423519, 5292), - listOf(4u, 1u) to Rational(3769712, 2205), - listOf(5u, 1u) to Rational(8905046, 6615), - listOf(6u, 1u) to Rational(1186972, 6615), - listOf(7u, 1u) to Rational(22124, 441), - listOf(8u, 1u) to Rational(-1504, 147), - listOf(0u, 2u) to Rational(-54723628, 2205), - listOf(1u, 2u) to Rational(70109407, 1323), - listOf(2u, 2u) to Rational(151072591, 17640), - listOf(3u, 2u) to Rational(1216428107, 52920), - listOf(4u, 2u) to Rational(2587873193, 317520), - listOf(5u, 2u) to Rational(393536369, 79380), - listOf(6u, 2u) to Rational(137614937, 79380), - listOf(7u, 2u) to Rational(566866, 1323), - listOf(8u, 2u) to Rational(41848, 441), - listOf(0u, 3u) to Rational(-19470406, 2205), - listOf(1u, 3u) to Rational(72514195, 882), - listOf(2u, 3u) to Rational(-78090707, 1764), - listOf(3u, 3u) to Rational(-1988237707, 26460), - listOf(4u, 3u) to Rational(-802137919, 17640), - listOf(5u, 3u) to Rational(-139989463, 5880), - listOf(6u, 3u) to Rational(-26066641, 3780), - listOf(7u, 3u) to Rational(-2363369, 1323), - listOf(8u, 3u) to Rational(-108280, 441), - listOf(0u, 4u) to Rational(14878516, 441), - listOf(1u, 4u) to Rational(-253416724, 2205), - listOf(2u, 4u) to Rational(16699157, 840), - listOf(3u, 4u) to Rational(-105220979, 13230), - listOf(4u, 4u) to Rational(208266383, 5880), - listOf(5u, 4u) to Rational(650135309, 26460), - listOf(6u, 4u) to Rational(123808663, 11760), - listOf(7u, 4u) to Rational(8563385, 2646), - listOf(8u, 4u) to Rational(19721, 49), - listOf(0u, 5u) to Rational(675645, 49), - listOf(1u, 5u) to Rational(-70554077, 588), - listOf(2u, 5u) to Rational(157884029, 980), - listOf(3u, 5u) to Rational(489548623, 4410), - listOf(4u, 5u) to Rational(148540519, 17640), - listOf(5u, 5u) to Rational(-5559551, 392), - listOf(6u, 5u) to Rational(-18335711, 1470), - listOf(7u, 5u) to Rational(-38437, 9), - listOf(8u, 5u) to Rational(-29620, 63), - listOf(0u, 6u) to Rational(-727625, 49), - listOf(1u, 6u) to Rational(7046685, 98), - listOf(2u, 6u) to Rational(-334814231, 7056), - listOf(3u, 6u) to Rational(-243971737, 17640), - listOf(4u, 6u) to Rational(-571116659, 35280), - listOf(5u, 6u) to Rational(567538, 315), - listOf(6u, 6u) to Rational(3199768, 315), - listOf(7u, 6u) to Rational(227744, 63), - listOf(8u, 6u) to Rational(23116, 63), - listOf(0u, 7u) to Rational(-27500, 7), - listOf(1u, 7u) to Rational(120125, 3), - listOf(2u, 7u) to Rational(-279200, 3), - listOf(3u, 7u) to Rational(-100160, 7), - listOf(4u, 7u) to Rational(920452, 21), - listOf(5u, 7u) to Rational(226481, 21), - listOf(6u, 7u) to Rational(-34428, 7), - listOf(7u, 7u) to Rational(-6232, 3), - listOf(8u, 7u) to Rational(-608, 3), - listOf(0u, 8u) to Rational(2500, 1), - listOf(1u, 8u) to Rational(-19000, 1), - listOf(2u, 8u) to Rational(37900, 1), - listOf(3u, 8u) to Rational(-1840, 1), - listOf(4u, 8u) to Rational(-17876, 1), - listOf(5u, 8u) to Rational(-1240, 1), - listOf(6u, 8u) to Rational(2788, 1), - listOf(7u, 8u) to Rational(800, 1), - listOf(8u, 8u) to Rational(64, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(162487, 63), - listOf(1u) to Rational(-92713, 54), - listOf(2u) to Rational(802436, 1323), - listOf(3u) to Rational(-55088, 441), - listOf(4u) to Rational(1404034, 9261), - listOf(5u) to Rational(-5804, 1029), - listOf(6u) to Rational(51556, 9261), - listOf(7u) to Rational(-752, 441), - listOf(8u) to Rational(16, 147), - listOf(0u, 1u) to Rational(296071, 441), - listOf(1u, 1u) to Rational(-4991281, 882), - listOf(2u, 1u) to Rational(-18702811, 9261), - listOf(3u, 1u) to Rational(40759043, 27783), - listOf(4u, 1u) to Rational(19768501, 27783), - listOf(5u, 1u) to Rational(14307337, 27783), - listOf(6u, 1u) to Rational(1655684, 27783), - listOf(7u, 1u) to Rational(22124, 1323), - listOf(8u, 1u) to Rational(-1504, 441), - listOf(0u, 2u) to Rational(-27667474, 3087), - listOf(1u, 2u) to Rational(265605901, 12348), - listOf(2u, 2u) to Rational(160360775, 98784), - listOf(3u, 2u) to Rational(1169992093, 148176), - listOf(4u, 2u) to Rational(3978014077, 1333584), - listOf(5u, 2u) to Rational(567058123, 333396), - listOf(6u, 2u) to Rational(205132579, 333396), - listOf(7u, 2u) to Rational(566866, 3969), - listOf(8u, 2u) to Rational(41848, 1323), - listOf(0u, 3u) to Rational(-2228822, 1029), - listOf(1u, 3u) to Rational(80179390, 3087), - listOf(2u, 3u) to Rational(-1378630487, 74088), - listOf(3u, 3u) to Rational(-3385811693, 111132), - listOf(4u, 3u) to Rational(-820686977, 49392), - listOf(5u, 3u) to Rational(-89101027, 10584), - listOf(6u, 3u) to Rational(-37847387, 15876), - listOf(7u, 3u) to Rational(-2363369, 3969), - listOf(8u, 3u) to Rational(-108280, 1323), - listOf(0u, 4u) to Rational(12619982, 1029), - listOf(1u, 4u) to Rational(-277723177, 6174), - listOf(2u, 4u) to Rational(649414169, 49392), - listOf(3u, 4u) to Rational(14457595, 63504), - listOf(4u, 4u) to Rational(139270339, 10584), - listOf(5u, 4u) to Rational(140367961, 15876), - listOf(6u, 4u) to Rational(25467083, 7056), - listOf(7u, 4u) to Rational(8563385, 7938), - listOf(8u, 4u) to Rational(19721, 147), - listOf(0u, 5u) to Rational(643850, 147), - listOf(1u, 5u) to Rational(-11818025, 294), - listOf(2u, 5u) to Rational(33963203, 588), - listOf(3u, 5u) to Rational(207216235, 5292), - listOf(4u, 5u) to Rational(2861021, 1512), - listOf(5u, 5u) to Rational(-6302335, 1176), - listOf(6u, 5u) to Rational(-3738587, 882), - listOf(7u, 5u) to Rational(-38437, 27), - listOf(8u, 5u) to Rational(-29620, 189), - listOf(0u, 6u) to Rational(-248725, 49), - listOf(1u, 6u) to Rational(2478535, 98), - listOf(2u, 6u) to Rational(-399721367, 21168), - listOf(3u, 6u) to Rational(-54309317, 10584), - listOf(4u, 6u) to Rational(-95398327, 21168), - listOf(5u, 6u) to Rational(173750, 189), - listOf(6u, 6u) to Rational(92216, 27), - listOf(7u, 6u) to Rational(227744, 189), - listOf(8u, 6u) to Rational(23116, 189), - listOf(0u, 7u) to Rational(-27500, 21), - listOf(1u, 7u) to Rational(120125, 9), - listOf(2u, 7u) to Rational(-279200, 9), - listOf(3u, 7u) to Rational(-100160, 21), - listOf(4u, 7u) to Rational(920452, 63), - listOf(5u, 7u) to Rational(226481, 63), - listOf(6u, 7u) to Rational(-11476, 7), - listOf(7u, 7u) to Rational(-6232, 9), - listOf(8u, 7u) to Rational(-608, 9), - listOf(0u, 8u) to Rational(2500, 3), - listOf(1u, 8u) to Rational(-19000, 3), - listOf(2u, 8u) to Rational(37900, 3), - listOf(3u, 8u) to Rational(-1840, 3), - listOf(4u, 8u) to Rational(-17876, 3), - listOf(5u, 8u) to Rational(-1240, 3), - listOf(6u, 8u) to Rational(2788, 3), - listOf(7u, 8u) to Rational(800, 3), - listOf(8u, 8u) to Rational(64, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(8, 2), - listOf(1u) to Rational(-15, 5), - listOf(2u) to Rational(2, 7), - listOf(0u, 1u) to Rational(-18, 7), - listOf(1u, 1u) to Rational(-16, 6), - listOf(2u, 1u) to Rational(-13, 3), - listOf(0u, 2u) to Rational(-5, 1), - listOf(1u, 2u) to Rational(17, 1), - listOf(2u, 2u) to Rational(8, 2), - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-409, 6), - listOf(1u) to Rational(-376, 9), - listOf(2u) to Rational(-1781, 81), - listOf(3u) to Rational(-128, 27), - listOf(4u) to Rational(-8, 9), - listOf(0u, 1u) to Rational(18701, 210), - listOf(1u, 1u) to Rational(614183, 7560), - listOf(2u, 1u) to Rational(90941, 1890), - listOf(3u, 1u) to Rational(1802, 135), - listOf(4u, 1u) to Rational(112, 45), - listOf(0u, 2u) to Rational(181421, 315), - listOf(1u, 2u) to Rational(77813, 378), - listOf(2u, 2u) to Rational(598583, 7560), - listOf(3u, 2u) to Rational(85, 27), - listOf(4u, 2u) to Rational(2, 5), - listOf(0u, 3u) to Rational(130997, 315), - listOf(1u, 3u) to Rational(1093, 420), - listOf(2u, 3u) to Rational(9551, 2520), - listOf(3u, 3u) to Rational(-14, 45), - listOf(4u, 3u) to Rational(22, 45), - listOf(0u, 4u) to Rational(-2801, 9), - listOf(1u, 4u) to Rational(4033, 90), - listOf(2u, 4u) to Rational(6429, 80), - listOf(3u, 4u) to Rational(2851, 90), - listOf(4u, 4u) to Rational(293, 45), - listOf(0u, 5u) to Rational(-220, 1), - listOf(1u, 5u) to Rational(127, 1), - listOf(2u, 5u) to Rational(202, 5), - listOf(3u, 5u) to Rational(-63, 5), - listOf(4u, 5u) to Rational(-12, 5), - listOf(0u, 6u) to Rational(100, 1), - listOf(1u, 6u) to Rational(-80, 1), - listOf(2u, 6u) to Rational(-24, 1), - listOf(3u, 6u) to Rational(16, 1), - listOf(4u, 6u) to Rational(4, 1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(5407, 9), - listOf(1u) to Rational(9568, 27), - listOf(2u) to Rational(4996, 27), - listOf(3u) to Rational(352, 9), - listOf(4u) to Rational(22, 3), - listOf(0u, 1u) to Rational(104411, 126), - listOf(1u, 1u) to Rational(6001, 126), - listOf(2u, 1u) to Rational(-796, 21), - listOf(3u, 1u) to Rational(-5389, 126), - listOf(4u, 1u) to Rational(-166, 21), - listOf(0u, 2u) to Rational(-35327, 126), - listOf(1u, 2u) to Rational(53, 252), - listOf(2u, 2u) to Rational(849197, 6048), - listOf(3u, 2u) to Rational(22361, 252), - listOf(4u, 2u) to Rational(773, 42), - listOf(0u, 3u) to Rational(-6067, 21), - listOf(1u, 3u) to Rational(39049, 126), - listOf(2u, 3u) to Rational(80303, 1008), - listOf(3u, 3u) to Rational(-3035, 63), - listOf(4u, 3u) to Rational(-209, 21), - listOf(0u, 4u) to Rational(3113, 21), - listOf(1u, 4u) to Rational(-22345, 126), - listOf(2u, 4u) to Rational(-30931, 1008), - listOf(3u, 4u) to Rational(5837, 126), - listOf(4u, 4u) to Rational(229, 21), - listOf(0u, 5u) to Rational(-2120, 21), - listOf(1u, 5u) to Rational(451, 7), - listOf(2u, 5u) to Rational(422, 21), - listOf(3u, 5u) to Rational(-181, 21), - listOf(4u, 5u) to Rational(-40, 21), - listOf(0u, 6u) to Rational(100, 3), - listOf(1u, 6u) to Rational(-80, 3), - listOf(2u, 6u) to Rational(-8, 1), - listOf(3u, 6u) to Rational(16, 3), - listOf(4u, 6u) to Rational(4, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, bufferOf( - NumberedPolynomialAsIs( - listOf() to Rational(18, 1), - listOf(1u) to Rational(16, 3), - listOf(2u) to Rational(12, 6), - listOf(0u, 1u) to Rational(13, 1), - listOf(1u, 1u) to Rational(-11, 4), - listOf(2u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(-10, 1), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(2, 1), - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 6), - listOf(1u) to Rational(1, 6), - listOf(2u) to Rational(-2, 9), - listOf(0u, 1u) to Rational(15, 1), - listOf(1u, 1u) to Rational(18, 7), - listOf(2u, 1u) to Rational(2, 5), - listOf(0u, 2u) to Rational(12, 9), - listOf(1u, 2u) to Rational(-3, 5), - listOf(2u, 2u) to Rational(4, 4), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-11, 9), - listOf(1u) to Rational(4, 9), - listOf(2u) to Rational(11, 6), - listOf(0u, 1u) to Rational(-5, 6), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(-1, 7), - listOf(0u, 2u) to Rational(9, 1), - listOf(1u, 2u) to Rational(6, 7), - listOf(2u, 2u) to Rational(1, 3), - ) - ).substitute(RationalField, bufferOf>()), - "test 6" - ) - } - @Test - @Ignore // FIXME: This tests work only for sane realisations of the substitutions. Currently, it is not. - // Sane algorithm for substitution p(q/r) (p, q, and r are polynomials) should return denominator r^deg(p), - // not r^(deg(p)(deg(p)+1)/2) as it is now. - fun test_RationalFunction_substitute_RationalFunction_Buffer() { - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(0) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ) - )), - "test 1" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(4u) to Rational(-17166109, 793800), - listOf(3u, 1u) to Rational(-930960143, 5556600), - listOf(2u, 2u) to Rational(-144665109691, 350065800), - listOf(1u, 3u) to Rational(-17232577, 52920), - listOf(0u, 4u) to Rational(-68141, 1323), - ), - NumberedPolynomialAsIs( - listOf(4u) to Rational(-57522533, 14288400), - listOf(3u, 1u) to Rational(-13085162953, 300056400), - listOf(2u, 2u) to Rational(-92093367341, 525098700), - listOf(1u, 3u) to Rational(-1979342797, 6667920), - listOf(0u, 4u) to Rational(-3082727, 21168), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(11, 5), - listOf(0u, 1u) to Rational(8, 4), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(1, 9), - listOf(0u, 1u) to Rational(11, 7), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf(1u) to Rational(-2, 7), - listOf(0u, 1u) to Rational(-4, 3), - ), - NumberedPolynomialAsIs( - listOf(1u) to Rational(3, 6), - listOf(0u, 1u) to Rational(12, 8), - ) - ), - )), - "test 2" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-130778291, 76800), - listOf(1u) to Rational(-445270919, 230400), - listOf(2u) to Rational(44578444937, 14515200), - listOf(3u) to Rational(17329402153, 1555200), - listOf(4u) to Rational(89239926809, 2332800), - listOf(5u) to Rational(2808812267, 145152), - listOf(6u) to Rational(-21362661007, 725760), - listOf(7u) to Rational(-258455443, 2016), - listOf(8u) to Rational(-21454693, 96), - listOf(0u, 1u) to Rational(-1002137, 15360), - listOf(1u, 1u) to Rational(-1704849697, 430080), - listOf(2u, 1u) to Rational(-57657676789, 4838400), - listOf(3u, 1u) to Rational(-101331731, 89600), - listOf(4u, 1u) to Rational(5362280079329, 130636800), - listOf(5u, 1u) to Rational(4069896167053, 130636800), - listOf(6u, 1u) to Rational(12011514569, 544320), - listOf(7u, 1u) to Rational(138293195623, 725760), - listOf(8u, 1u) to Rational(6228779419, 48384), - listOf(0u, 2u) to Rational(-32395872823, 8064000), - listOf(1u, 2u) to Rational(-7398505523, 2304000), - listOf(2u, 2u) to Rational(95217051699521, 3048192000), - listOf(3u, 2u) to Rational(198026968812079, 3657830400), - listOf(4u, 2u) to Rational(4291645618499, 228614400), - listOf(5u, 2u) to Rational(-33211690942439, 914457600), - listOf(6u, 2u) to Rational(-637385538163153, 1371686400), - listOf(7u, 2u) to Rational(-138671528276273, 182891520), - listOf(8u, 2u) to Rational(-14566368751, 217728), - listOf(0u, 3u) to Rational(-10538718719, 2016000), - listOf(1u, 3u) to Rational(-1844485375199, 84672000), - listOf(2u, 3u) to Rational(103968665891, 12096000), - listOf(3u, 3u) to Rational(175402107278351, 1828915200), - listOf(4u, 3u) to Rational(8020699588879, 114307200), - listOf(5u, 3u) to Rational(3414841894991, 38102400), - listOf(6u, 3u) to Rational(1848405591611, 4665600), - listOf(7u, 3u) to Rational(39486708738989, 137168640), - listOf(8u, 3u) to Rational(255926289517, 9144576), - listOf(0u, 4u) to Rational(-655379564629, 105840000), - listOf(1u, 4u) to Rational(-208336039441, 127008000), - listOf(2u, 4u) to Rational(40173146771411, 1143072000), - listOf(3u, 4u) to Rational(150473493581239, 2667168000), - listOf(4u, 4u) to Rational(38833783990483, 1143072000), - listOf(5u, 4u) to Rational(-1963676248203053, 4800902400), - listOf(6u, 4u) to Rational(-2598759412825747, 3200601600), - listOf(7u, 4u) to Rational(-192895352019667, 1280240640), - listOf(8u, 4u) to Rational(3737382679, 6858432), - listOf(0u, 5u) to Rational(-16959378721, 1890000), - listOf(1u, 5u) to Rational(-1864802244743, 79380000), - listOf(2u, 5u) to Rational(13449261536489, 666792000), - listOf(3u, 5u) to Rational(215272234137329, 2667168000), - listOf(4u, 5u) to Rational(6040691379277, 83349000), - listOf(5u, 5u) to Rational(153687143525887, 800150400), - listOf(6u, 5u) to Rational(475602854903563, 2400451200), - listOf(7u, 5u) to Rational(27315599358749, 640120320), - listOf(8u, 5u) to Rational(-2630413357, 10668672), - listOf(0u, 6u) to Rational(-6654999511, 2646000), - listOf(1u, 6u) to Rational(-67885252327, 15876000), - listOf(2u, 6u) to Rational(5786776220983, 2667168000), - listOf(3u, 6u) to Rational(60615922629083, 1143072000), - listOf(4u, 6u) to Rational(-34703539637627407, 672126336000), - listOf(5u, 6u) to Rational(-744694192134101, 2240421120), - listOf(6u, 6u) to Rational(-1782470617231, 14817600), - listOf(7u, 6u) to Rational(59123208433, 8890560), - listOf(8u, 6u) to Rational(-141653, 5292), - listOf(0u, 7u) to Rational(-338051969, 441000), - listOf(1u, 7u) to Rational(468850013, 1764000), - listOf(2u, 7u) to Rational(2102343426101, 222264000), - listOf(3u, 7u) to Rational(7836130602007, 1333584000), - listOf(4u, 7u) to Rational(16239111865997, 746807040), - listOf(5u, 7u) to Rational(3824649185383, 88905600), - listOf(6u, 7u) to Rational(56058614459, 3457440), - listOf(7u, 7u) to Rational(-396766339, 493920), - listOf(8u, 7u) to Rational(-165147, 2744), - listOf(0u, 8u) to Rational(-3088619, 58800), - listOf(1u, 8u) to Rational(155343347, 88200), - listOf(2u, 8u) to Rational(100098736469, 7408800), - listOf(3u, 8u) to Rational(109725511381, 7408800), - listOf(4u, 8u) to Rational(-2431199641013, 59270400), - listOf(5u, 8u) to Rational(-102872383249, 3457440), - listOf(6u, 8u) to Rational(1449461309, 576240), - listOf(7u, 8u) to Rational(812775, 1372), - listOf(8u, 8u) to Rational(-16461, 343) - ), - NumberedPolynomialAsIs( - listOf() to Rational(164202773, 230400), - listOf(1u) to Rational(-70345303, 518400), - listOf(2u) to Rational(-4229702731, 4665600), - listOf(3u) to Rational(3262171027, 6998400), - listOf(4u) to Rational(-25423104169, 13996800), - listOf(5u) to Rational(64061869, 349920), - listOf(6u) to Rational(-1655878091, 116640), - listOf(7u) to Rational(-7991441, 648), - listOf(8u) to Rational(-502591, 18), - listOf(0u, 1u) to Rational(-8780429, 3840), - listOf(1u, 1u) to Rational(434272361, 115200), - listOf(2u, 1u) to Rational(429825727, 41472), - listOf(3u, 1u) to Rational(-10066790339, 6998400), - listOf(4u, 1u) to Rational(70022035471, 20995200), - listOf(5u, 1u) to Rational(-32070283493, 1399680), - listOf(6u, 1u) to Rational(-22051101001, 1399680), - listOf(7u, 1u) to Rational(-126493427, 12960), - listOf(8u, 1u) to Rational(3050245, 864), - listOf(0u, 2u) to Rational(-1194654631, 345600), - listOf(1u, 2u) to Rational(-542961452671, 31104000), - listOf(2u, 2u) to Rational(-234000873607, 48988800), - listOf(3u, 2u) to Rational(140520538087, 3628800), - listOf(4u, 2u) to Rational(9215088876563, 130636800), - listOf(5u, 2u) to Rational(27590569647253, 293932800), - listOf(6u, 2u) to Rational(5129057792891, 97977600), - listOf(7u, 2u) to Rational(-106334191, 5103), - listOf(8u, 2u) to Rational(-1024113911, 435456), - listOf(0u, 3u) to Rational(76223843, 6000), - listOf(1u, 3u) to Rational(57425857357, 2592000), - listOf(2u, 3u) to Rational(-2044736497573, 46656000), - listOf(3u, 3u) to Rational(-26155810120031, 293932800), - listOf(4u, 3u) to Rational(-1064419459813, 6998400), - listOf(5u, 3u) to Rational(-753782018389, 4082400), - listOf(6u, 3u) to Rational(-291973360873, 2799360), - listOf(7u, 3u) to Rational(-46372122599, 816480), - listOf(8u, 3u) to Rational(3579859657, 653184), - listOf(0u, 4u) to Rational(-13374241901, 4320000), - listOf(1u, 4u) to Rational(306606499811, 54432000), - listOf(2u, 4u) to Rational(964267124745437, 13716864000), - listOf(3u, 4u) to Rational(21603809415373, 182891520), - listOf(4u, 4u) to Rational(1097860214654027, 6858432000), - listOf(5u, 4u) to Rational(161615254570669, 914457600), - listOf(6u, 4u) to Rational(758415239461, 22861440), - listOf(7u, 4u) to Rational(2585568355471, 274337280), - listOf(8u, 4u) to Rational(-70433747863, 9144576), - listOf(0u, 5u) to Rational(-9582586217, 2520000), - listOf(1u, 5u) to Rational(-19093471394171, 635040000), - listOf(2u, 5u) to Rational(-13010261944411, 381024000), - listOf(3u, 5u) to Rational(-259039825301861, 4572288000), - listOf(4u, 5u) to Rational(-305081119071079, 2286144000), - listOf(5u, 5u) to Rational(-1923114383311, 19595520), - listOf(6u, 5u) to Rational(-14181787253231, 228614400), - listOf(7u, 5u) to Rational(-3959584789, 4354560), - listOf(8u, 5u) to Rational(4691742523, 762048), - listOf(0u, 6u) to Rational(-588323437, 180000), - listOf(1u, 6u) to Rational(5952234691, 52920000), - listOf(2u, 6u) to Rational(21001851056959, 1088640000), - listOf(3u, 6u) to Rational(84668034357563, 2133734400), - listOf(4u, 6u) to Rational(2029754605811557, 25604812800), - listOf(5u, 6u) to Rational(11721216739823, 426746880), - listOf(6u, 6u) to Rational(-8275903187003, 2133734400), - listOf(7u, 6u) to Rational(-4730447299, 2540160), - listOf(8u, 6u) to Rational(-46069985, 21168), - listOf(0u, 7u) to Rational(-75711301, 117600), - listOf(1u, 7u) to Rational(32430417413, 7056000), - listOf(2u, 7u) to Rational(677988533153, 98784000), - listOf(3u, 7u) to Rational(-948417645827, 71124480), - listOf(4u, 7u) to Rational(-11320265215207, 711244800), - listOf(5u, 7u) to Rational(-676438627783, 50803200), - listOf(6u, 7u) to Rational(-7382274253, 1975680), - listOf(7u, 7u) to Rational(6505733, 2205), - listOf(8u, 7u) to Rational(450137, 882), - listOf(0u, 8u) to Rational(-8368253, 78400), - listOf(1u, 8u) to Rational(6833783, 117600), - listOf(2u, 8u) to Rational(4528971133, 5927040), - listOf(3u, 8u) to Rational(146252636617, 29635200), - listOf(4u, 8u) to Rational(8321882556889, 1659571200), - listOf(5u, 8u) to Rational(-4686033011, 1975680), - listOf(6u, 8u) to Rational(-1074445963, 987840), - listOf(7u, 8u) to Rational(-142313, 588), - listOf(8u, 8u) to Rational(-4281, 49) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(5, 8), - listOf(1u) to Rational(-12, 6), - listOf(2u) to Rational(7, 6), - listOf(0u, 1u) to Rational(-10, 4), - listOf(1u, 1u) to Rational(-7, 6), - listOf(2u, 1u) to Rational(8, 9), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-13, 4), - listOf(2u, 2u) to Rational(5, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(10, 6), - listOf(1u) to Rational(-18, 6), - listOf(2u) to Rational(5, 1), - listOf(0u, 1u) to Rational(17, 7), - listOf(1u, 1u) to Rational(8, 4), - listOf(2u, 1u) to Rational(-4, 9), - listOf(0u, 2u) to Rational(-6, 5), - listOf(1u, 2u) to Rational(-15, 8), - listOf(2u, 2u) to Rational(-18, 5), - ) - ), - )), - "test 3" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-130778291, 76800), - listOf(1u) to Rational(-445270919, 230400), - listOf(2u) to Rational(44578444937, 14515200), - listOf(3u) to Rational(17329402153, 1555200), - listOf(4u) to Rational(89239926809, 2332800), - listOf(5u) to Rational(2808812267, 145152), - listOf(6u) to Rational(-21362661007, 725760), - listOf(7u) to Rational(-258455443, 2016), - listOf(8u) to Rational(-21454693, 96), - listOf(0u, 1u) to Rational(-1002137, 15360), - listOf(1u, 1u) to Rational(-1704849697, 430080), - listOf(2u, 1u) to Rational(-57657676789, 4838400), - listOf(3u, 1u) to Rational(-101331731, 89600), - listOf(4u, 1u) to Rational(5362280079329, 130636800), - listOf(5u, 1u) to Rational(4069896167053, 130636800), - listOf(6u, 1u) to Rational(12011514569, 544320), - listOf(7u, 1u) to Rational(138293195623, 725760), - listOf(8u, 1u) to Rational(6228779419, 48384), - listOf(0u, 2u) to Rational(-32395872823, 8064000), - listOf(1u, 2u) to Rational(-7398505523, 2304000), - listOf(2u, 2u) to Rational(95217051699521, 3048192000), - listOf(3u, 2u) to Rational(198026968812079, 3657830400), - listOf(4u, 2u) to Rational(4291645618499, 228614400), - listOf(5u, 2u) to Rational(-33211690942439, 914457600), - listOf(6u, 2u) to Rational(-637385538163153, 1371686400), - listOf(7u, 2u) to Rational(-138671528276273, 182891520), - listOf(8u, 2u) to Rational(-14566368751, 217728), - listOf(0u, 3u) to Rational(-10538718719, 2016000), - listOf(1u, 3u) to Rational(-1844485375199, 84672000), - listOf(2u, 3u) to Rational(103968665891, 12096000), - listOf(3u, 3u) to Rational(175402107278351, 1828915200), - listOf(4u, 3u) to Rational(8020699588879, 114307200), - listOf(5u, 3u) to Rational(3414841894991, 38102400), - listOf(6u, 3u) to Rational(1848405591611, 4665600), - listOf(7u, 3u) to Rational(39486708738989, 137168640), - listOf(8u, 3u) to Rational(255926289517, 9144576), - listOf(0u, 4u) to Rational(-655379564629, 105840000), - listOf(1u, 4u) to Rational(-208336039441, 127008000), - listOf(2u, 4u) to Rational(40173146771411, 1143072000), - listOf(3u, 4u) to Rational(150473493581239, 2667168000), - listOf(4u, 4u) to Rational(38833783990483, 1143072000), - listOf(5u, 4u) to Rational(-1963676248203053, 4800902400), - listOf(6u, 4u) to Rational(-2598759412825747, 3200601600), - listOf(7u, 4u) to Rational(-192895352019667, 1280240640), - listOf(8u, 4u) to Rational(3737382679, 6858432), - listOf(0u, 5u) to Rational(-16959378721, 1890000), - listOf(1u, 5u) to Rational(-1864802244743, 79380000), - listOf(2u, 5u) to Rational(13449261536489, 666792000), - listOf(3u, 5u) to Rational(215272234137329, 2667168000), - listOf(4u, 5u) to Rational(6040691379277, 83349000), - listOf(5u, 5u) to Rational(153687143525887, 800150400), - listOf(6u, 5u) to Rational(475602854903563, 2400451200), - listOf(7u, 5u) to Rational(27315599358749, 640120320), - listOf(8u, 5u) to Rational(-2630413357, 10668672), - listOf(0u, 6u) to Rational(-6654999511, 2646000), - listOf(1u, 6u) to Rational(-67885252327, 15876000), - listOf(2u, 6u) to Rational(5786776220983, 2667168000), - listOf(3u, 6u) to Rational(60615922629083, 1143072000), - listOf(4u, 6u) to Rational(-34703539637627407, 672126336000), - listOf(5u, 6u) to Rational(-744694192134101, 2240421120), - listOf(6u, 6u) to Rational(-1782470617231, 14817600), - listOf(7u, 6u) to Rational(59123208433, 8890560), - listOf(8u, 6u) to Rational(-141653, 5292), - listOf(0u, 7u) to Rational(-338051969, 441000), - listOf(1u, 7u) to Rational(468850013, 1764000), - listOf(2u, 7u) to Rational(2102343426101, 222264000), - listOf(3u, 7u) to Rational(7836130602007, 1333584000), - listOf(4u, 7u) to Rational(16239111865997, 746807040), - listOf(5u, 7u) to Rational(3824649185383, 88905600), - listOf(6u, 7u) to Rational(56058614459, 3457440), - listOf(7u, 7u) to Rational(-396766339, 493920), - listOf(8u, 7u) to Rational(-165147, 2744), - listOf(0u, 8u) to Rational(-3088619, 58800), - listOf(1u, 8u) to Rational(155343347, 88200), - listOf(2u, 8u) to Rational(100098736469, 7408800), - listOf(3u, 8u) to Rational(109725511381, 7408800), - listOf(4u, 8u) to Rational(-2431199641013, 59270400), - listOf(5u, 8u) to Rational(-102872383249, 3457440), - listOf(6u, 8u) to Rational(1449461309, 576240), - listOf(7u, 8u) to Rational(812775, 1372), - listOf(8u, 8u) to Rational(-16461, 343) - ), - NumberedPolynomialAsIs( - listOf() to Rational(164202773, 230400), - listOf(1u) to Rational(-70345303, 518400), - listOf(2u) to Rational(-4229702731, 4665600), - listOf(3u) to Rational(3262171027, 6998400), - listOf(4u) to Rational(-25423104169, 13996800), - listOf(5u) to Rational(64061869, 349920), - listOf(6u) to Rational(-1655878091, 116640), - listOf(7u) to Rational(-7991441, 648), - listOf(8u) to Rational(-502591, 18), - listOf(0u, 1u) to Rational(-8780429, 3840), - listOf(1u, 1u) to Rational(434272361, 115200), - listOf(2u, 1u) to Rational(429825727, 41472), - listOf(3u, 1u) to Rational(-10066790339, 6998400), - listOf(4u, 1u) to Rational(70022035471, 20995200), - listOf(5u, 1u) to Rational(-32070283493, 1399680), - listOf(6u, 1u) to Rational(-22051101001, 1399680), - listOf(7u, 1u) to Rational(-126493427, 12960), - listOf(8u, 1u) to Rational(3050245, 864), - listOf(0u, 2u) to Rational(-1194654631, 345600), - listOf(1u, 2u) to Rational(-542961452671, 31104000), - listOf(2u, 2u) to Rational(-234000873607, 48988800), - listOf(3u, 2u) to Rational(140520538087, 3628800), - listOf(4u, 2u) to Rational(9215088876563, 130636800), - listOf(5u, 2u) to Rational(27590569647253, 293932800), - listOf(6u, 2u) to Rational(5129057792891, 97977600), - listOf(7u, 2u) to Rational(-106334191, 5103), - listOf(8u, 2u) to Rational(-1024113911, 435456), - listOf(0u, 3u) to Rational(76223843, 6000), - listOf(1u, 3u) to Rational(57425857357, 2592000), - listOf(2u, 3u) to Rational(-2044736497573, 46656000), - listOf(3u, 3u) to Rational(-26155810120031, 293932800), - listOf(4u, 3u) to Rational(-1064419459813, 6998400), - listOf(5u, 3u) to Rational(-753782018389, 4082400), - listOf(6u, 3u) to Rational(-291973360873, 2799360), - listOf(7u, 3u) to Rational(-46372122599, 816480), - listOf(8u, 3u) to Rational(3579859657, 653184), - listOf(0u, 4u) to Rational(-13374241901, 4320000), - listOf(1u, 4u) to Rational(306606499811, 54432000), - listOf(2u, 4u) to Rational(964267124745437, 13716864000), - listOf(3u, 4u) to Rational(21603809415373, 182891520), - listOf(4u, 4u) to Rational(1097860214654027, 6858432000), - listOf(5u, 4u) to Rational(161615254570669, 914457600), - listOf(6u, 4u) to Rational(758415239461, 22861440), - listOf(7u, 4u) to Rational(2585568355471, 274337280), - listOf(8u, 4u) to Rational(-70433747863, 9144576), - listOf(0u, 5u) to Rational(-9582586217, 2520000), - listOf(1u, 5u) to Rational(-19093471394171, 635040000), - listOf(2u, 5u) to Rational(-13010261944411, 381024000), - listOf(3u, 5u) to Rational(-259039825301861, 4572288000), - listOf(4u, 5u) to Rational(-305081119071079, 2286144000), - listOf(5u, 5u) to Rational(-1923114383311, 19595520), - listOf(6u, 5u) to Rational(-14181787253231, 228614400), - listOf(7u, 5u) to Rational(-3959584789, 4354560), - listOf(8u, 5u) to Rational(4691742523, 762048), - listOf(0u, 6u) to Rational(-588323437, 180000), - listOf(1u, 6u) to Rational(5952234691, 52920000), - listOf(2u, 6u) to Rational(21001851056959, 1088640000), - listOf(3u, 6u) to Rational(84668034357563, 2133734400), - listOf(4u, 6u) to Rational(2029754605811557, 25604812800), - listOf(5u, 6u) to Rational(11721216739823, 426746880), - listOf(6u, 6u) to Rational(-8275903187003, 2133734400), - listOf(7u, 6u) to Rational(-4730447299, 2540160), - listOf(8u, 6u) to Rational(-46069985, 21168), - listOf(0u, 7u) to Rational(-75711301, 117600), - listOf(1u, 7u) to Rational(32430417413, 7056000), - listOf(2u, 7u) to Rational(677988533153, 98784000), - listOf(3u, 7u) to Rational(-948417645827, 71124480), - listOf(4u, 7u) to Rational(-11320265215207, 711244800), - listOf(5u, 7u) to Rational(-676438627783, 50803200), - listOf(6u, 7u) to Rational(-7382274253, 1975680), - listOf(7u, 7u) to Rational(6505733, 2205), - listOf(8u, 7u) to Rational(450137, 882), - listOf(0u, 8u) to Rational(-8368253, 78400), - listOf(1u, 8u) to Rational(6833783, 117600), - listOf(2u, 8u) to Rational(4528971133, 5927040), - listOf(3u, 8u) to Rational(146252636617, 29635200), - listOf(4u, 8u) to Rational(8321882556889, 1659571200), - listOf(5u, 8u) to Rational(-4686033011, 1975680), - listOf(6u, 8u) to Rational(-1074445963, 987840), - listOf(7u, 8u) to Rational(-142313, 588), - listOf(8u, 8u) to Rational(-4281, 49) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(14, 4), - listOf(1u) to Rational(7, 6), - listOf(2u) to Rational(7, 2), - listOf(0u, 1u) to Rational(-15, 2), - listOf(1u, 1u) to Rational(-13, 8), - listOf(2u, 1u) to Rational(-14, 3), - listOf(0u, 2u) to Rational(-7, 6), - listOf(1u, 2u) to Rational(7, 4), - listOf(2u, 2u) to Rational(9, 7), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-7, 4), - listOf(1u) to Rational(-6, 3), - listOf(2u) to Rational(-16, 2), - listOf(0u, 1u) to Rational(-15, 5), - listOf(1u, 1u) to Rational(4, 6), - listOf(2u, 1u) to Rational(5, 4), - listOf(0u, 2u) to Rational(-12, 5), - listOf(1u, 2u) to Rational(-18, 2), - listOf(2u, 2u) to Rational(6, 7), - ) - ), - )), - "test 4" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-506213, 2800), - listOf(1u) to Rational(9859, 315), - listOf(2u) to Rational(17384377, 11340), - listOf(3u) to Rational(-9662, 63), - listOf(4u) to Rational(-12563, 4), - listOf(0u, 1u) to Rational(-486293, 22400), - listOf(1u, 1u) to Rational(-6530947, 25200), - listOf(2u, 1u) to Rational(866125, 18144), - listOf(3u, 1u) to Rational(2948747, 2520), - listOf(4u, 1u) to Rational(1196611, 2016), - listOf(0u, 2u) to Rational(-20266021, 117600), - listOf(1u, 2u) to Rational(26656339, 44100), - listOf(2u, 2u) to Rational(19499183, 18144), - listOf(3u, 2u) to Rational(-19801849, 7560), - listOf(4u, 2u) to Rational(-2639635, 1296), - listOf(0u, 3u) to Rational(-5017697, 29400), - listOf(1u, 3u) to Rational(-606007, 1575), - listOf(2u, 3u) to Rational(127494487, 132300), - listOf(3u, 3u) to Rational(166567, 105), - listOf(4u, 3u) to Rational(486403, 18144), - listOf(0u, 4u) to Rational(-32182, 735), - listOf(1u, 4u) to Rational(2420671, 8820), - listOf(2u, 4u) to Rational(-12619193, 26460), - listOf(3u, 4u) to Rational(-6823067, 5670), - listOf(4u, 4u) to Rational(-2311693, 13608), - listOf(0u, 5u) to Rational(-13324, 245), - listOf(1u, 5u) to Rational(1966, 35), - listOf(2u, 5u) to Rational(1052719, 2520), - listOf(3u, 5u) to Rational(19153, 270), - listOf(4u, 5u) to Rational(701, 54), - listOf(0u, 6u) to Rational(4647, 196), - listOf(1u, 6u) to Rational(2197, 28), - listOf(2u, 6u) to Rational(-43853, 336), - listOf(3u, 6u) to Rational(-301, 3), - listOf(4u, 6u) to Rational(34, 3) - ), - NumberedPolynomialAsIs( - listOf() to Rational(-2843, 1600), - listOf(1u) to Rational(-1483, 240), - listOf(2u) to Rational(110623, 1296), - listOf(3u) to Rational(1265, 72), - listOf(4u) to Rational(-5011, 16), - listOf(0u, 1u) to Rational(47743, 1800), - listOf(1u, 1u) to Rational(619229, 32400), - listOf(2u, 1u) to Rational(-5978369, 58320), - listOf(3u, 1u) to Rational(-86081, 1620), - listOf(4u, 1u) to Rational(6325, 72), - listOf(0u, 2u) to Rational(110951, 3360), - listOf(1u, 2u) to Rational(-9550649, 302400), - listOf(2u, 2u) to Rational(6542933, 85050), - listOf(3u, 2u) to Rational(4708291, 38880), - listOf(4u, 2u) to Rational(-433327, 1296), - listOf(0u, 3u) to Rational(56143, 600), - listOf(1u, 3u) to Rational(94243, 720), - listOf(2u, 3u) to Rational(-46779139, 226800), - listOf(3u, 3u) to Rational(-6948253, 12960), - listOf(4u, 3u) to Rational(-260261, 486), - listOf(0u, 4u) to Rational(-3205317, 19600), - listOf(1u, 4u) to Rational(-201253, 1050), - listOf(2u, 4u) to Rational(332192677, 302400), - listOf(3u, 4u) to Rational(351511, 360), - listOf(4u, 4u) to Rational(-40547, 81), - listOf(0u, 5u) to Rational(-65421, 1960), - listOf(1u, 5u) to Rational(-10118, 35), - listOf(2u, 5u) to Rational(-4341709, 10080), - listOf(3u, 5u) to Rational(-91703, 360), - listOf(4u, 5u) to Rational(-85, 9), - listOf(0u, 6u) to Rational(-25965, 784), - listOf(1u, 6u) to Rational(3351, 16), - listOf(2u, 6u) to Rational(595159, 1344), - listOf(3u, 6u) to Rational(-1381, 12), - listOf(4u, 6u) to Rational(-155, 3) - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, bufferOf( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-17, 5), - listOf(1u) to Rational(2, 6), - listOf(2u) to Rational(14, 1), - listOf(0u, 1u) to Rational(-6, 6), - listOf(1u, 1u) to Rational(-7, 3), - listOf(2u, 1u) to Rational(-2, 9), - listOf(0u, 2u) to Rational(-9, 6), - listOf(1u, 2u) to Rational(17, 4), - listOf(2u, 2u) to Rational(2, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(5, 4), - listOf(1u) to Rational(-5, 9), - listOf(2u) to Rational(-3, 6), - listOf(0u, 1u) to Rational(6, 5), - listOf(1u, 1u) to Rational(14, 5), - listOf(2u, 1u) to Rational(5, 2), - listOf(0u, 2u) to Rational(-18, 7), - listOf(1u, 2u) to Rational(-8, 2), - listOf(2u, 2u) to Rational(18, 9), - ) - ), - )), - "test 5" - ) - assertEquals( - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(10, 2), - listOf(1u) to Rational(6, 7), - listOf(2u) to Rational(-16, 1), - listOf(0u, 1u) to Rational(13, 8), - listOf(1u, 1u) to Rational(-12, 1), - listOf(2u, 1u) to Rational(16, 8), - listOf(0u, 2u) to Rational(10, 4), - listOf(1u, 2u) to Rational(4, 1), - listOf(2u, 2u) to Rational(-11, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1, 4), - listOf(1u) to Rational(-17, 4), - listOf(2u) to Rational(-14, 8), - listOf(0u, 1u) to Rational(17, 9), - listOf(1u, 1u) to Rational(1, 3), - listOf(2u, 1u) to Rational(7, 6), - listOf(0u, 2u) to Rational(16, 3), - listOf(1u, 2u) to Rational(-17, 1), - listOf(2u, 2u) to Rational(-10, 8), - ) - ).substitute(RationalField, bufferOf>()), - "test 6" - ) - } - @Test - fun test_Polynomial_substituteFully_Double_Buffer() { - assertEquals( - 0.0, - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ).substituteFully(bufferOf( - 1.0 - )), - 0.001, - "test 1" - ) - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 2" - ) { - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf()) - } - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 3" - ) { - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf( - 0.0, - )) - } - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 4" - ) { - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf( - 0.4846192734143442, - )) - } - assertEquals( - 1.934530767358133, - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - )), - 0.001, - "test 5" - ) - assertEquals( - 1.934530767358133, - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - 0.9211194782050933 - )), - 0.001, - "test 6" - ) - assertEquals( - 1.934530767358133, - NumberedPolynomialAsIs( - listOf() to 0.8597048543814783, - listOf(1u) to 0.22997637465889875, - listOf(2u) to 0.32675302591924016, - listOf(0u, 1u) to 0.4561746111587508, - listOf(1u, 1u) to 0.5304946210170756, - listOf(2u, 1u) to 0.6244313712888998, - listOf(0u, 2u) to 0.2700930201481795, - listOf(1u, 2u) to -0.06962351375204712, - listOf(2u, 2u) to -0.015206988092131501, - ).substituteFully(bufferOf( - 0.4846192734143442, - 0.8400458576651112, - 0.9211194782050933, - 0.4752854632152105 - )), - 0.001, - "test 7" - ) - } - @Test - fun test_Polynomial_substituteFully_Constant_Buffer() { - assertEquals( - Rational(0), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ).substituteFully(RationalField, bufferOf( - Rational(1) - )), - "test 1" - ) - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 2" - ) { - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substituteFully(RationalField, bufferOf()) - } - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 3" - ) { - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substituteFully( - RationalField, bufferOf( - Rational(-2, 5), - ) - ) - } - // https://www.wolframalpha.com/input?i=%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2+where+x+%3D+-2%2F5%2C+y+%3D+12%2F9 - assertEquals( - Rational(143, 150), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substituteFully(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - )), - "test 4" - ) - assertEquals( - Rational(143, 150), - NumberedPolynomialAsIs( - listOf() to Rational(-3, 2), - listOf(1u) to Rational(8, 6), - listOf(2u) to Rational(14, 6), - listOf(0u, 1u) to Rational(-3, 1), - listOf(1u, 1u) to Rational(-19, 2), - listOf(2u, 1u) to Rational(9, 4), - listOf(0u, 2u) to Rational(5, 5), - listOf(1u, 2u) to Rational(18, 9), - listOf(2u, 2u) to Rational(5, 2), - ).substituteFully(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - Rational(57, 179), - )), - "test 5" - ) - // https://www.wolframalpha.com/input?i=%28%28-3%2F2+%2B+8%2F6+x+%2B+14%2F6+x%5E2%29+%2B+%28-3%2F1+%2B+-19%2F2+x+%2B+9%2F4+x%5E2%29+y+%2B+%285%2F5+%2B+18%2F9+x+%2B+5%2F2+x%5E2%29+y%5E2%29+p%5E8+where+x+%3D+q%2Fp%2C+y+%3D+x%5E3%2C+p+%3D+-2%2F5%2C+q+%3D+12%2F9 - assertEquals( - Rational(47639065216, 2562890625), - NumberedPolynomialAsIs( - listOf(8u) to Rational(-3, 2), - listOf(7u, 1u) to Rational(8, 6), - listOf(6u, 2u) to Rational(14, 6), - listOf(5u, 3u) to Rational(-3, 1), - listOf(4u, 4u) to Rational(-19, 2), - listOf(3u, 5u) to Rational(9, 4), - listOf(2u, 6u) to Rational(5, 5), - listOf(1u, 7u) to Rational(18, 9), - listOf(0u, 8u) to Rational(5, 2), - ).substituteFully(RationalField, bufferOf( - Rational(-2, 5), - Rational(12, 9), - )), - "test 6" - ) - } - @Test - fun test_RationalFunction_substituteFully_Double_Buffer() { - assertEquals( - 0.0, - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 1.0, - listOf(1u) to -2.0, - listOf(2u) to 1.0, - ), - NumberedPolynomialAsIs( - listOf() to 1.0, - ) - ).substituteFully(bufferOf( - 1.0 - )), - 0.001, - "test 1" - ) - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 2" - ) { - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substituteFully(bufferOf()) - } - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 3" - ) { - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substituteFully( - bufferOf( - -8.11707689492641, - ) - ) - } - assertEquals( - -0.012718636022899672, - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substituteFully(bufferOf( - -8.11707689492641, - 0.795265651276015, - )), - 0.001, - "test 4" - ) - assertEquals( - -0.012718636022899672, - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to 6.593754860231304, - listOf(1u) to -7.853302571550634, - listOf(2u) to 1.2265042281530025, - listOf(0u, 1u) to 3.762648877294904, - listOf(1u, 1u) to -8.945144619305292, - listOf(2u, 1u) to -5.141384718042281, - listOf(0u, 2u) to 7.359794483988782, - listOf(1u, 2u) to -4.3526172680518815, - listOf(2u, 2u) to 0.907910924854372, - ), - NumberedPolynomialAsIs( - listOf() to 9.533292132172562, - listOf(1u) to -1.982814534018857, - listOf(2u) to -5.974248303415283, - listOf(0u, 1u) to 1.5876716499288879, - listOf(1u, 1u) to -7.535152566659664, - listOf(2u, 1u) to 0.7549300500153517, - listOf(0u, 2u) to -5.242030058021028, - listOf(1u, 2u) to -0.7265704289690582, - listOf(2u, 2u) to -7.139677818189821, - ) - ).substituteFully(bufferOf( - -8.11707689492641, - 0.795265651276015, - 0.9211194782050933 - )), - 0.001, - "test 5" - ) - } - @Test - fun test_RationalFunction_substituteFully_Constant_Buffer() { - assertEquals( - Rational(0), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1) - ), - NumberedPolynomialAsIs( - listOf() to Rational(1) - ) - ).substituteFully(RationalField, bufferOf( - Rational(1) - )), - "test 1" - ) - assertEquals( - Rational(-1322820, 2204953), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substituteFully(RationalField, bufferOf( - Rational(7, 5), - Rational(-13, 7), - Rational(-16, 4), - )), - "test 2" - ) - assertEquals( - Rational(-1322820, 2204953), - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substituteFully(RationalField, bufferOf( - Rational(7, 5), - Rational(-13, 7), - )), - "test 3" - ) - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 4" - ) { - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substituteFully( - RationalField, bufferOf( - Rational(7, 5), - ) - ) - } - assertFailsWithTypeAndMessage( - fullSubstitutionExceptionMessage, - "test 5" - ) { - NumberedRationalFunction( - NumberedPolynomialAsIs( - listOf() to Rational(-3, 5), - listOf(1u) to Rational(-18, 4), - listOf(2u) to Rational(9, 8), - listOf(0u, 1u) to Rational(-11, 6), - listOf(1u, 1u) to Rational(-16, 3), - listOf(2u, 1u) to Rational(12, 2), - listOf(0u, 2u) to Rational(5, 3), - listOf(1u, 2u) to Rational(17, 8), - listOf(2u, 2u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(11, 1), - listOf(1u) to Rational(4, 1), - listOf(2u) to Rational(-18, 3), - listOf(0u, 1u) to Rational(12, 9), - listOf(1u, 1u) to Rational(14, 7), - listOf(2u, 1u) to Rational(-17, 5), - listOf(0u, 2u) to Rational(-4, 1), - listOf(1u, 2u) to Rational(-5, 5), - listOf(2u, 2u) to Rational(-7, 8), - ) - ).substituteFully(RationalField, bufferOf()) - } - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_derivativeWithRespectTo_variable() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2), - listOf(1u) to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).derivativeWithRespectTo(RationalField, 0), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 3), - listOf(1u) to Rational(1, 1), - listOf(2u) to Rational(-33, 8), - listOf(3u) to Rational(72, 1), - listOf(0u, 1u) to Rational(2, 3), - listOf(1u, 1u) to Rational(-22, 1), - listOf(2u, 1u) to Rational(-1, 1), - listOf(3u, 1u) to Rational(-36, 1), - listOf(0u, 2u) to Rational(-8, 5), - listOf(1u, 2u) to Rational(-1, 4), - listOf(2u, 2u) to Rational(12, 7), - listOf(3u, 2u) to Rational(-2, 1), - listOf(0u, 3u) to Rational(16, 8), - listOf(1u, 3u) to Rational(-4, 1), - listOf(2u, 3u) to Rational(9, 2), - listOf(3u, 3u) to Rational(20, 9), - listOf(0u, 4u) to Rational(-10, 1), - listOf(1u, 4u) to Rational(-14, 1), - listOf(2u, 4u) to Rational(3, 7), - listOf(3u, 4u) to Rational(20, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, 0), - "test 2a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-18, 3), - listOf(1u) to Rational(2, 3), - listOf(2u) to Rational(-11, 1), - listOf(3u) to Rational(-1, 3), - listOf(4u) to Rational(-18, 2), - listOf(0u, 1u) to Rational(-20, 3), - listOf(1u, 1u) to Rational(-16, 5), - listOf(2u, 1u) to Rational(-1, 4), - listOf(3u, 1u) to Rational(8, 7), - listOf(4u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(9, 7), - listOf(1u, 2u) to Rational(6, 1), - listOf(2u, 2u) to Rational(-6, 1), - listOf(3u, 2u) to Rational(9, 2), - listOf(4u, 2u) to Rational(5, 3), - listOf(0u, 3u) to Rational(-9, 1), - listOf(1u, 3u) to Rational(-40, 1), - listOf(2u, 3u) to Rational(-28, 1), - listOf(3u, 3u) to Rational(4, 7), - listOf(4u, 3u) to Rational(20, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, 1), - "test 2b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(-1, 4), - listOf(2u, 2u) to Rational(12, 7), - listOf(3u, 2u) to Rational(-2, 1), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(-4, 1), - listOf(2u, 3u) to Rational(9, 2), - listOf(3u, 3u) to Rational(20, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(-14, 1), - listOf(2u, 4u) to Rational(3, 7), - listOf(3u, 4u) to Rational(20, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, 0), - "test 3a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(-1, 4), - listOf(3u, 1u) to Rational(8, 7), - listOf(4u, 1u) to Rational(-1, 1), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-6, 1), - listOf(3u, 2u) to Rational(9, 2), - listOf(4u, 2u) to Rational(5, 3), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-28, 1), - listOf(3u, 3u) to Rational(4, 7), - listOf(4u, 3u) to Rational(20, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, 1), - "test 3b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2, 3), - listOf(1u) to Rational(1, 1), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 1u) to Rational(2, 3), - listOf(1u, 1u) to Rational(-22, 1), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-8, 5), - listOf(1u, 2u) to Rational(-1, 4), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).derivativeWithRespectTo(RationalField, 0), - "test 4a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-18, 3), - listOf(1u) to Rational(2, 3), - listOf(2u) to Rational(-11, 1), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-20, 3), - listOf(1u, 1u) to Rational(-16, 5), - listOf(2u, 1u) to Rational(-1, 4), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).derivativeWithRespectTo(RationalField, 1), - "test 4b" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).derivativeWithRespectTo(RationalField, 5), - "test 5" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthDerivativeWithRespectTo_variable_order() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2), - listOf(1u) to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 0, 1u), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 0, 0u), - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 0, 2u), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 0, 3u), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 0, 4u), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 1, 0u), - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 1, 1u), - "test 7" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, 1, 2u), - "test 8" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1, 1), - listOf(1u) to Rational(-33, 4), - listOf(2u) to Rational(216, 1), - listOf(0u, 1u) to Rational(-22, 1), - listOf(1u, 1u) to Rational(-2, 1), - listOf(2u, 1u) to Rational(-108, 1), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(24, 7), - listOf(2u, 2u) to Rational(-6, 1), - listOf(0u, 3u) to Rational(-4, 1), - listOf(1u, 3u) to Rational(9, 1), - listOf(2u, 3u) to Rational(20, 3), - listOf(0u, 4u) to Rational(-14, 1), - listOf(1u, 4u) to Rational(6, 7), - listOf(2u, 4u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, 0, 2u), - "test 9a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-20, 3), - listOf(1u) to Rational(-16, 5), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(8, 7), - listOf(4u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(18, 7), - listOf(1u, 1u) to Rational(12, 1), - listOf(2u, 1u) to Rational(-12, 1), - listOf(3u, 1u) to Rational(9, 1), - listOf(4u, 1u) to Rational(10, 3), - listOf(0u, 2u) to Rational(-27, 1), - listOf(1u, 2u) to Rational(-120, 1), - listOf(2u, 2u) to Rational(-84, 1), - listOf(3u, 2u) to Rational(12, 7), - listOf(4u, 2u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, 1, 2u), - "test 9b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(24, 7), - listOf(2u, 2u) to Rational(-6, 1), - listOf(0u, 3u) to Rational(-4, 1), - listOf(1u, 3u) to Rational(9, 1), - listOf(2u, 3u) to Rational(20, 3), - listOf(0u, 4u) to Rational(-14, 1), - listOf(1u, 4u) to Rational(6, 7), - listOf(2u, 4u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, 0, 2u), - "test 10a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(8, 7), - listOf(4u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(-12, 1), - listOf(3u, 1u) to Rational(9, 1), - listOf(4u, 1u) to Rational(10, 3), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-84, 1), - listOf(3u, 2u) to Rational(12, 7), - listOf(4u, 2u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, 1, 2u), - "test 10b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1, 1), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(-22, 1), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, 0, 2u), - "test 11a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-20, 3), - listOf(1u) to Rational(-16, 5), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, 1, 2u), - "test 11b" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthDerivativeWithRespectTo_variablesAndOrders() { - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2), - listOf(1u) to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 1u)), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 0u)), - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 3u)), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 4u)), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 0u)), - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 1u)), - "test 7" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 8" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf()), - "test 9" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-2), - listOf(1u) to Rational(2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf( - 0 to 1u, - 1 to 0u - )), - "test 10" - ) - assertEquals( - NumberedPolynomialAsIs(), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthDerivativeWithRespectTo(RationalField, mapOf( - 0 to 0u, - 1 to 1u - )), - "test 11" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1, 1), - listOf(1u) to Rational(-33, 4), - listOf(2u) to Rational(216, 1), - listOf(0u, 1u) to Rational(-22, 1), - listOf(1u, 1u) to Rational(-2, 1), - listOf(2u, 1u) to Rational(-108, 1), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(24, 7), - listOf(2u, 2u) to Rational(-6, 1), - listOf(0u, 3u) to Rational(-4, 1), - listOf(1u, 3u) to Rational(9, 1), - listOf(2u, 3u) to Rational(20, 3), - listOf(0u, 4u) to Rational(-14, 1), - listOf(1u, 4u) to Rational(6, 7), - listOf(2u, 4u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 12a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(2, 3), - listOf(1u) to Rational(-22, 1), - listOf(2u) to Rational(-1, 1), - listOf(3u) to Rational(-36, 1), - listOf(0u, 1u) to Rational(-16, 5), - listOf(1u, 1u) to Rational(-1, 2), - listOf(2u, 1u) to Rational(24, 7), - listOf(3u, 1u) to Rational(-4, 1), - listOf(0u, 2u) to Rational(6, 1), - listOf(1u, 2u) to Rational(-12, 1), - listOf(2u, 2u) to Rational(27, 2), - listOf(3u, 2u) to Rational(20, 3), - listOf(0u, 3u) to Rational(-40, 1), - listOf(1u, 3u) to Rational(-56, 1), - listOf(2u, 3u) to Rational(12, 7), - listOf(3u, 3u) to Rational(80, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 12b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-20, 3), - listOf(1u) to Rational(-16, 5), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(8, 7), - listOf(4u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(18, 7), - listOf(1u, 1u) to Rational(12, 1), - listOf(2u, 1u) to Rational(-12, 1), - listOf(3u, 1u) to Rational(9, 1), - listOf(4u, 1u) to Rational(10, 3), - listOf(0u, 2u) to Rational(-27, 1), - listOf(1u, 2u) to Rational(-120, 1), - listOf(2u, 2u) to Rational(-84, 1), - listOf(3u, 2u) to Rational(12, 7), - listOf(4u, 2u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 12c" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(24, 7), - listOf(2u, 2u) to Rational(-6, 1), - listOf(0u, 3u) to Rational(-4, 1), - listOf(1u, 3u) to Rational(9, 1), - listOf(2u, 3u) to Rational(20, 3), - listOf(0u, 4u) to Rational(-14, 1), - listOf(1u, 4u) to Rational(6, 7), - listOf(2u, 4u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 13a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(-1, 2), - listOf(2u, 1u) to Rational(24, 7), - listOf(3u, 1u) to Rational(-4, 1), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(-12, 1), - listOf(2u, 2u) to Rational(27, 2), - listOf(3u, 2u) to Rational(20, 3), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(-56, 1), - listOf(2u, 3u) to Rational(12, 7), - listOf(3u, 3u) to Rational(80, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 13b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(8, 7), - listOf(4u) to Rational(-1, 1), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(-12, 1), - listOf(3u, 1u) to Rational(9, 1), - listOf(4u, 1u) to Rational(10, 3), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-84, 1), - listOf(3u, 2u) to Rational(12, 7), - listOf(4u, 2u) to Rational(60, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 13c" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1, 1), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(0u, 1u) to Rational(-22, 1), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-1, 4), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 14a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(2, 3), - listOf(1u) to Rational(-22, 1), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(0u, 1u) to Rational(-16, 5), - listOf(1u, 1u) to Rational(-1, 2), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 14b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(-20, 3), - listOf(1u) to Rational(-16, 5), - listOf(2u) to Rational(-1, 4), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthDerivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 14c" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_antiderivativeWithRespectTo_variable() { - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(1), - listOf(2u) to Rational(-1), - listOf(3u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).antiderivativeWithRespectTo(RationalField, 0), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(-6, 8), - listOf(2u) to Rational(-1, 3), - listOf(3u) to Rational(1, 6), - listOf(4u) to Rational(-11, 32), - listOf(5u) to Rational(18, 5), - listOf(1u, 1u) to Rational(-18, 3), - listOf(2u, 1u) to Rational(1, 3), - listOf(3u, 1u) to Rational(-11, 3), - listOf(4u, 1u) to Rational(-1, 12), - listOf(5u, 1u) to Rational(-18, 10), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(-4, 5), - listOf(3u, 2u) to Rational(-1, 24), - listOf(4u, 2u) to Rational(1, 7), - listOf(5u, 2u) to Rational(-1, 10), - listOf(1u, 3u) to Rational(3, 7), - listOf(2u, 3u) to Rational(1, 1), - listOf(3u, 3u) to Rational(-2, 3), - listOf(4u, 3u) to Rational(3, 8), - listOf(5u, 3u) to Rational(1, 9), - listOf(1u, 4u) to Rational(-18, 8), - listOf(2u, 4u) to Rational(-5, 1), - listOf(3u, 4u) to Rational(-7, 3), - listOf(4u, 4u) to Rational(1, 28), - listOf(5u, 4u) to Rational(1, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, 0), - "test 2a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(-6, 8), - listOf(1u, 1u) to Rational(-2, 3), - listOf(2u, 1u) to Rational(1, 2), - listOf(3u, 1u) to Rational(-11, 8), - listOf(4u, 1u) to Rational(18, 1), - listOf(0u, 2u) to Rational(-9, 3), - listOf(1u, 2u) to Rational(1, 3), - listOf(2u, 2u) to Rational(-11, 2), - listOf(3u, 2u) to Rational(-1, 6), - listOf(4u, 2u) to Rational(-9, 2), - listOf(0u, 3u) to Rational(-10, 9), - listOf(1u, 3u) to Rational(-8, 15), - listOf(2u, 3u) to Rational(-1, 24), - listOf(3u, 3u) to Rational(4, 21), - listOf(4u, 3u) to Rational(-1, 6), - listOf(0u, 4u) to Rational(3, 28), - listOf(1u, 4u) to Rational(1, 2), - listOf(2u, 4u) to Rational(-1, 2), - listOf(3u, 4u) to Rational(3, 8), - listOf(4u, 4u) to Rational(5, 36), - listOf(0u, 5u) to Rational(-9, 20), - listOf(1u, 5u) to Rational(-2, 1), - listOf(2u, 5u) to Rational(-7, 5), - listOf(3u, 5u) to Rational(1, 35), - listOf(4u, 5u) to Rational(1, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, 1), - "test 2b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(5u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(-1, 24), - listOf(4u, 2u) to Rational(1, 7), - listOf(5u, 2u) to Rational(-1, 10), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(-2, 3), - listOf(4u, 3u) to Rational(3, 8), - listOf(5u, 3u) to Rational(1, 9), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(-7, 3), - listOf(4u, 4u) to Rational(1, 28), - listOf(5u, 4u) to Rational(1, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, 0), - "test 3a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-1, 24), - listOf(3u, 3u) to Rational(4, 21), - listOf(4u, 3u) to Rational(-1, 6), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-1, 2), - listOf(3u, 4u) to Rational(3, 8), - listOf(4u, 4u) to Rational(5, 36), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(-7, 5), - listOf(3u, 5u) to Rational(1, 35), - listOf(4u, 5u) to Rational(1, 1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, 1), - "test 3b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(-6, 8), - listOf(2u) to Rational(-1, 3), - listOf(3u) to Rational(1, 6), - listOf(4u) to Rational(0), - listOf(5u) to Rational(0), - listOf(1u, 1u) to Rational(-18, 3), - listOf(2u, 1u) to Rational(1, 3), - listOf(3u, 1u) to Rational(-11, 3), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(1u, 2u) to Rational(-10, 3), - listOf(2u, 2u) to Rational(-4, 5), - listOf(3u, 2u) to Rational(-1, 24), - listOf(4u, 2u) to Rational(0), - listOf(5u, 2u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(5u, 3u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(5u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).antiderivativeWithRespectTo(RationalField, 0), - "test 4a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(-6, 8), - listOf(1u, 1u) to Rational(-2, 3), - listOf(2u, 1u) to Rational(1, 2), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-9, 3), - listOf(1u, 2u) to Rational(1, 3), - listOf(2u, 2u) to Rational(-11, 2), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(-10, 9), - listOf(1u, 3u) to Rational(-8, 15), - listOf(2u, 3u) to Rational(-1, 24), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(0), - listOf(3u, 5u) to Rational(0), - listOf(4u, 5u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).antiderivativeWithRespectTo(RationalField, 1), - "test 4b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 0u, 0u, 0u, 0u, 1u) to Rational(-6, 8), - listOf(1u, 0u, 0u, 0u, 0u, 1u) to Rational(-2, 3), - listOf(2u, 0u, 0u, 0u, 0u, 1u) to Rational(1, 2), - listOf(3u, 0u, 0u, 0u, 0u, 1u) to Rational(-11, 8), - listOf(4u, 0u, 0u, 0u, 0u, 1u) to Rational(18, 1), - listOf(0u, 1u, 0u, 0u, 0u, 1u) to Rational(-18, 3), - listOf(1u, 1u, 0u, 0u, 0u, 1u) to Rational(2, 3), - listOf(2u, 1u, 0u, 0u, 0u, 1u) to Rational(-11, 1), - listOf(3u, 1u, 0u, 0u, 0u, 1u) to Rational(-1, 3), - listOf(4u, 1u, 0u, 0u, 0u, 1u) to Rational(-18, 2), - listOf(0u, 2u, 0u, 0u, 0u, 1u) to Rational(-10, 3), - listOf(1u, 2u, 0u, 0u, 0u, 1u) to Rational(-8, 5), - listOf(2u, 2u, 0u, 0u, 0u, 1u) to Rational(-1, 8), - listOf(3u, 2u, 0u, 0u, 0u, 1u) to Rational(4, 7), - listOf(4u, 2u, 0u, 0u, 0u, 1u) to Rational(-4, 8), - listOf(0u, 3u, 0u, 0u, 0u, 1u) to Rational(3, 7), - listOf(1u, 3u, 0u, 0u, 0u, 1u) to Rational(16, 8), - listOf(2u, 3u, 0u, 0u, 0u, 1u) to Rational(-16, 8), - listOf(3u, 3u, 0u, 0u, 0u, 1u) to Rational(12, 8), - listOf(4u, 3u, 0u, 0u, 0u, 1u) to Rational(5, 9), - listOf(0u, 4u, 0u, 0u, 0u, 1u) to Rational(-18, 8), - listOf(1u, 4u, 0u, 0u, 0u, 1u) to Rational(-10, 1), - listOf(2u, 4u, 0u, 0u, 0u, 1u) to Rational(-14, 2), - listOf(3u, 4u, 0u, 0u, 0u, 1u) to Rational(1, 7), - listOf(4u, 4u, 0u, 0u, 0u, 1u) to Rational(15, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).antiderivativeWithRespectTo(RationalField, 5), - "test 5" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthAntiderivativeWithRespectTo_variable_order() { - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(1), - listOf(2u) to Rational(-1), - listOf(3u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 1u), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 0u), - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-1, 3), - listOf(4u) to Rational(1, 12), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 2u), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(3u) to Rational(1, 6), - listOf(4u) to Rational(-1, 12), - listOf(5u) to Rational(1, 60), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 3u), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(-1, 60), - listOf(6u) to Rational(1, 360), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 4u), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 0u), - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(1), - listOf(1u, 1u) to Rational(-2), - listOf(2u, 1u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 1u), - "test 7" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(1, 2), - listOf(1u, 2u) to Rational(-1), - listOf(2u, 2u) to Rational(1, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 2u), - "test 8" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(-3, 8), - listOf(3u) to Rational(-1, 9), - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(-11, 160), - listOf(6u) to Rational(3, 5), - listOf(2u, 1u) to Rational(-9, 3), - listOf(3u, 1u) to Rational(1, 9), - listOf(4u, 1u) to Rational(-11, 12), - listOf(5u, 1u) to Rational(-1, 60), - listOf(6u, 1u) to Rational(-3, 10), - listOf(2u, 2u) to Rational(-5, 3), - listOf(3u, 2u) to Rational(-4, 15), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(1, 35), - listOf(6u, 2u) to Rational(-1, 60), - listOf(2u, 3u) to Rational(3, 14), - listOf(3u, 3u) to Rational(1, 3), - listOf(4u, 3u) to Rational(-1, 6), - listOf(5u, 3u) to Rational(3, 40), - listOf(6u, 3u) to Rational(1, 54), - listOf(2u, 4u) to Rational(-9, 8), - listOf(3u, 4u) to Rational(-5, 3), - listOf(4u, 4u) to Rational(-7, 12), - listOf(5u, 4u) to Rational(1, 140), - listOf(6u, 4u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 2u), - "test 9a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(-3, 8), - listOf(1u, 2u) to Rational(-1, 3), - listOf(2u, 2u) to Rational(1, 4), - listOf(3u, 2u) to Rational(-11, 16), - listOf(4u, 2u) to Rational(9, 1), - listOf(0u, 3u) to Rational(-1, 1), - listOf(1u, 3u) to Rational(1, 9), - listOf(2u, 3u) to Rational(-11, 6), - listOf(3u, 3u) to Rational(-1, 18), - listOf(4u, 3u) to Rational(-9, 6), - listOf(0u, 4u) to Rational(-5, 18), - listOf(1u, 4u) to Rational(-2, 15), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(1, 21), - listOf(4u, 4u) to Rational(-1, 24), - listOf(0u, 5u) to Rational(3, 140), - listOf(1u, 5u) to Rational(1, 10), - listOf(2u, 5u) to Rational(-1, 10), - listOf(3u, 5u) to Rational(3, 40), - listOf(4u, 5u) to Rational(1, 36), - listOf(0u, 6u) to Rational(-3, 40), - listOf(1u, 6u) to Rational(-1, 3), - listOf(2u, 6u) to Rational(-7, 30), - listOf(3u, 6u) to Rational(1, 210), - listOf(4u, 6u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 2u), - "test 9b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(5u) to Rational(0), - listOf(6u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(6u, 1u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(1, 35), - listOf(6u, 2u) to Rational(-1, 60), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(-1, 6), - listOf(5u, 3u) to Rational(3, 40), - listOf(6u, 3u) to Rational(1, 54), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(-7, 12), - listOf(5u, 4u) to Rational(1, 140), - listOf(6u, 4u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 2u), - "test 10a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(1, 21), - listOf(4u, 4u) to Rational(-1, 24), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(-1, 10), - listOf(3u, 5u) to Rational(3, 40), - listOf(4u, 5u) to Rational(1, 36), - listOf(0u, 6u) to Rational(0), - listOf(1u, 6u) to Rational(0), - listOf(2u, 6u) to Rational(-7, 30), - listOf(3u, 6u) to Rational(1, 210), - listOf(4u, 6u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 2u), - "test 10b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(-3, 8), - listOf(3u) to Rational(-1, 9), - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(0), - listOf(6u) to Rational(0), - listOf(2u, 1u) to Rational(-9, 3), - listOf(3u, 1u) to Rational(1, 9), - listOf(4u, 1u) to Rational(-11, 12), - listOf(5u, 1u) to Rational(0), - listOf(6u, 1u) to Rational(0), - listOf(2u, 2u) to Rational(-5, 3), - listOf(3u, 2u) to Rational(-4, 15), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(0), - listOf(6u, 2u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(5u, 3u) to Rational(0), - listOf(6u, 3u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(5u, 4u) to Rational(0), - listOf(6u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 2u), - "test 11a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(-3, 8), - listOf(1u, 2u) to Rational(-1, 3), - listOf(2u, 2u) to Rational(1, 4), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(-1, 1), - listOf(1u, 3u) to Rational(1, 9), - listOf(2u, 3u) to Rational(-11, 6), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(-5, 18), - listOf(1u, 4u) to Rational(-2, 15), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(0), - listOf(3u, 5u) to Rational(0), - listOf(4u, 5u) to Rational(0), - listOf(0u, 6u) to Rational(0), - listOf(1u, 6u) to Rational(0), - listOf(2u, 6u) to Rational(0), - listOf(3u, 6u) to Rational(0), - listOf(4u, 6u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 2u), - "test 11b" - ) - } - @Test - @OptIn(UnstableKMathAPI::class) - fun test_Polynomial_nthAntiderivativeWithRespectTo_variablesAndOrders() { - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(1), - listOf(2u) to Rational(-1), - listOf(3u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 1u)), - "test 1" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 0u), - "test 2" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-1, 3), - listOf(4u) to Rational(1, 12), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 2u), - "test 3" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(3u) to Rational(1, 6), - listOf(4u) to Rational(-1, 12), - listOf(5u) to Rational(1, 60), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 3u), - "test 4" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(-1, 60), - listOf(6u) to Rational(1, 360), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 0, 4u), - "test 5" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 0u), - "test 6" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(1), - listOf(1u, 1u) to Rational(-2), - listOf(2u, 1u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 1u), - "test 7" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(1, 2), - listOf(1u, 2u) to Rational(-1), - listOf(2u, 2u) to Rational(1, 2), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, 1, 2u), - "test 8" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf()), - "test 9" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u) to Rational(1), - listOf(2u) to Rational(-1), - listOf(3u) to Rational(1, 3), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf( - 0 to 1u, - 1 to 0u - )), - "test 10" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 1u) to Rational(1), - listOf(1u, 1u) to Rational(-2), - listOf(2u, 1u) to Rational(1), - ), - NumberedPolynomialAsIs( - listOf() to Rational(1), - listOf(1u) to Rational(-2), - listOf(2u) to Rational(1), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf( - 0 to 0u, - 1 to 1u - )), - "test 11" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(-3, 8), - listOf(3u) to Rational(-1, 9), - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(-11, 160), - listOf(6u) to Rational(3, 5), - listOf(2u, 1u) to Rational(-9, 3), - listOf(3u, 1u) to Rational(1, 9), - listOf(4u, 1u) to Rational(-11, 12), - listOf(5u, 1u) to Rational(-1, 60), - listOf(6u, 1u) to Rational(-3, 10), - listOf(2u, 2u) to Rational(-5, 3), - listOf(3u, 2u) to Rational(-4, 15), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(1, 35), - listOf(6u, 2u) to Rational(-1, 60), - listOf(2u, 3u) to Rational(3, 14), - listOf(3u, 3u) to Rational(1, 3), - listOf(4u, 3u) to Rational(-1, 6), - listOf(5u, 3u) to Rational(3, 40), - listOf(6u, 3u) to Rational(1, 54), - listOf(2u, 4u) to Rational(-9, 8), - listOf(3u, 4u) to Rational(-5, 3), - listOf(4u, 4u) to Rational(-7, 12), - listOf(5u, 4u) to Rational(1, 140), - listOf(6u, 4u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 12a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u, 1u) to Rational(-6, 8), - listOf(2u, 1u) to Rational(-1, 3), - listOf(3u, 1u) to Rational(1, 6), - listOf(4u, 1u) to Rational(-11, 32), - listOf(5u, 1u) to Rational(18, 5), - listOf(1u, 2u) to Rational(-9, 3), - listOf(2u, 2u) to Rational(1, 6), - listOf(3u, 2u) to Rational(-11, 6), - listOf(4u, 2u) to Rational(-1, 24), - listOf(5u, 2u) to Rational(-9, 10), - listOf(1u, 3u) to Rational(-10, 9), - listOf(2u, 3u) to Rational(-4, 15), - listOf(3u, 3u) to Rational(-1, 72), - listOf(4u, 3u) to Rational(1, 21), - listOf(5u, 3u) to Rational(-1, 30), - listOf(1u, 4u) to Rational(3, 28), - listOf(2u, 4u) to Rational(1, 4), - listOf(3u, 4u) to Rational(-1, 6), - listOf(4u, 4u) to Rational(3, 32), - listOf(5u, 4u) to Rational(1, 36), - listOf(1u, 5u) to Rational(-9, 20), - listOf(2u, 5u) to Rational(-1, 1), - listOf(3u, 5u) to Rational(-7, 15), - listOf(4u, 5u) to Rational(1, 140), - listOf(5u, 5u) to Rational(1, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 12b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(-3, 8), - listOf(1u, 2u) to Rational(-1, 3), - listOf(2u, 2u) to Rational(1, 4), - listOf(3u, 2u) to Rational(-11, 16), - listOf(4u, 2u) to Rational(9, 1), - listOf(0u, 3u) to Rational(-1, 1), - listOf(1u, 3u) to Rational(1, 9), - listOf(2u, 3u) to Rational(-11, 6), - listOf(3u, 3u) to Rational(-1, 18), - listOf(4u, 3u) to Rational(-9, 6), - listOf(0u, 4u) to Rational(-5, 18), - listOf(1u, 4u) to Rational(-2, 15), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(1, 21), - listOf(4u, 4u) to Rational(-1, 24), - listOf(0u, 5u) to Rational(3, 140), - listOf(1u, 5u) to Rational(1, 10), - listOf(2u, 5u) to Rational(-1, 10), - listOf(3u, 5u) to Rational(3, 40), - listOf(4u, 5u) to Rational(1, 36), - listOf(0u, 6u) to Rational(-3, 40), - listOf(1u, 6u) to Rational(-1, 3), - listOf(2u, 6u) to Rational(-7, 30), - listOf(3u, 6u) to Rational(1, 210), - listOf(4u, 6u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(-11, 8), - listOf(4u) to Rational(18, 1), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(-1, 3), - listOf(4u, 1u) to Rational(-18, 2), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(3, 7), - listOf(1u, 3u) to Rational(16, 8), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(-18, 8), - listOf(1u, 4u) to Rational(-10, 1), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 12c" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(5u) to Rational(0), - listOf(6u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(6u, 1u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(1, 35), - listOf(6u, 2u) to Rational(-1, 60), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(-1, 6), - listOf(5u, 3u) to Rational(3, 40), - listOf(6u, 3u) to Rational(1, 54), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(-7, 12), - listOf(5u, 4u) to Rational(1, 140), - listOf(6u, 4u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 13a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(5u, 2u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(-1, 72), - listOf(4u, 3u) to Rational(1, 21), - listOf(5u, 3u) to Rational(-1, 30), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(-1, 6), - listOf(4u, 4u) to Rational(3, 32), - listOf(5u, 4u) to Rational(1, 36), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(0), - listOf(3u, 5u) to Rational(-7, 15), - listOf(4u, 5u) to Rational(1, 140), - listOf(5u, 5u) to Rational(1, 5), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 13b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(0), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(1, 21), - listOf(4u, 4u) to Rational(-1, 24), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(-1, 10), - listOf(3u, 5u) to Rational(3, 40), - listOf(4u, 5u) to Rational(1, 36), - listOf(0u, 6u) to Rational(0), - listOf(1u, 6u) to Rational(0), - listOf(2u, 6u) to Rational(-7, 30), - listOf(3u, 6u) to Rational(1, 210), - listOf(4u, 6u) to Rational(1, 6), - ), - NumberedPolynomialAsIs( - listOf() to Rational(0), - listOf(1u) to Rational(0), - listOf(2u) to Rational(0), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(0), - listOf(1u, 1u) to Rational(0), - listOf(2u, 1u) to Rational(0), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(0), - listOf(1u, 2u) to Rational(0), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(4, 7), - listOf(4u, 2u) to Rational(-4, 8), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(-16, 8), - listOf(3u, 3u) to Rational(12, 8), - listOf(4u, 3u) to Rational(5, 9), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(-14, 2), - listOf(3u, 4u) to Rational(1, 7), - listOf(4u, 4u) to Rational(15, 3), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 13c" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(2u) to Rational(-3, 8), - listOf(3u) to Rational(-1, 9), - listOf(4u) to Rational(1, 24), - listOf(5u) to Rational(0), - listOf(6u) to Rational(0), - listOf(2u, 1u) to Rational(-9, 3), - listOf(3u, 1u) to Rational(1, 9), - listOf(4u, 1u) to Rational(-11, 12), - listOf(5u, 1u) to Rational(0), - listOf(6u, 1u) to Rational(0), - listOf(2u, 2u) to Rational(-5, 3), - listOf(3u, 2u) to Rational(-4, 15), - listOf(4u, 2u) to Rational(-1, 96), - listOf(5u, 2u) to Rational(0), - listOf(6u, 2u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(5u, 3u) to Rational(0), - listOf(6u, 3u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(5u, 4u) to Rational(0), - listOf(6u, 4u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 2u)), - "test 14a" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(1u, 1u) to Rational(-6, 8), - listOf(2u, 1u) to Rational(-1, 3), - listOf(3u, 1u) to Rational(1, 6), - listOf(4u, 1u) to Rational(0), - listOf(5u, 1u) to Rational(0), - listOf(1u, 2u) to Rational(-9, 3), - listOf(2u, 2u) to Rational(1, 6), - listOf(3u, 2u) to Rational(-11, 6), - listOf(4u, 2u) to Rational(0), - listOf(5u, 2u) to Rational(0), - listOf(1u, 3u) to Rational(-10, 9), - listOf(2u, 3u) to Rational(-4, 15), - listOf(3u, 3u) to Rational(-1, 72), - listOf(4u, 3u) to Rational(0), - listOf(5u, 3u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(5u, 4u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(0), - listOf(3u, 5u) to Rational(0), - listOf(4u, 5u) to Rational(0), - listOf(5u, 5u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(0 to 1u, 1 to 1u)), - "test 14b" - ) - assertEquals( - NumberedPolynomialAsIs( - listOf(0u, 2u) to Rational(-3, 8), - listOf(1u, 2u) to Rational(-1, 3), - listOf(2u, 2u) to Rational(1, 4), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(-1, 1), - listOf(1u, 3u) to Rational(1, 9), - listOf(2u, 3u) to Rational(-11, 6), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(-5, 18), - listOf(1u, 4u) to Rational(-2, 15), - listOf(2u, 4u) to Rational(-1, 96), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - listOf(0u, 5u) to Rational(0), - listOf(1u, 5u) to Rational(0), - listOf(2u, 5u) to Rational(0), - listOf(3u, 5u) to Rational(0), - listOf(4u, 5u) to Rational(0), - listOf(0u, 6u) to Rational(0), - listOf(1u, 6u) to Rational(0), - listOf(2u, 6u) to Rational(0), - listOf(3u, 6u) to Rational(0), - listOf(4u, 6u) to Rational(0), - ), - NumberedPolynomialAsIs( - listOf() to Rational(-6, 8), - listOf(1u) to Rational(-2, 3), - listOf(2u) to Rational(1, 2), - listOf(3u) to Rational(0), - listOf(4u) to Rational(0), - listOf(0u, 1u) to Rational(-18, 3), - listOf(1u, 1u) to Rational(2, 3), - listOf(2u, 1u) to Rational(-11, 1), - listOf(3u, 1u) to Rational(0), - listOf(4u, 1u) to Rational(0), - listOf(0u, 2u) to Rational(-10, 3), - listOf(1u, 2u) to Rational(-8, 5), - listOf(2u, 2u) to Rational(-1, 8), - listOf(3u, 2u) to Rational(0), - listOf(4u, 2u) to Rational(0), - listOf(0u, 3u) to Rational(0), - listOf(1u, 3u) to Rational(0), - listOf(2u, 3u) to Rational(0), - listOf(3u, 3u) to Rational(0), - listOf(4u, 3u) to Rational(0), - listOf(0u, 4u) to Rational(0), - listOf(1u, 4u) to Rational(0), - listOf(2u, 4u) to Rational(0), - listOf(3u, 4u) to Rational(0), - listOf(4u, 4u) to Rational(0), - ).nthAntiderivativeWithRespectTo(RationalField, mapOf(1 to 2u)), - "test 14c" - ) - } -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/BufferUtils.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/BufferUtils.kt deleted file mode 100644 index 3297733b1..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/BufferUtils.kt +++ /dev/null @@ -1,12 +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.functions.testUtils - -import space.kscience.kmath.structures.Buffer -import space.kscience.kmath.structures.asBuffer - - -fun bufferOf(vararg elements: T): Buffer = elements.asBuffer() \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt deleted file mode 100644 index 5bac4cd73..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModulo.kt +++ /dev/null @@ -1,133 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions.testUtils - -import space.kscience.kmath.operations.Ring - - -class IntModulo { - val residue: Int - val modulus: Int - - @PublishedApi - internal constructor(residue: Int, modulus: Int, toCheckInput: Boolean = true) { - if (toCheckInput) { - require(modulus != 0) { "modulus can not be zero" } - this.modulus = if (modulus < 0) -modulus else modulus - this.residue = residue.mod(this.modulus) - } else { - this.residue = residue - this.modulus = modulus - } - } - - constructor(residue: Int, modulus: Int) : this(residue, modulus, true) - - operator fun unaryPlus(): IntModulo = this - operator fun unaryMinus(): IntModulo = - IntModulo( - if (residue == 0) 0 else modulus - residue, - modulus, - toCheckInput = false - ) - operator fun plus(other: IntModulo): IntModulo { - require(modulus == other.modulus) { "can not add two residue different modulo" } - return IntModulo( - (residue + other.residue) % modulus, - modulus, - toCheckInput = false - ) - } - operator fun plus(other: Int): IntModulo = - IntModulo( - (residue + other) % modulus, - modulus, - toCheckInput = false - ) - operator fun minus(other: IntModulo): IntModulo { - require(modulus == other.modulus) { "can not subtract two residue different modulo" } - return IntModulo( - (residue - other.residue) % modulus, - modulus, - toCheckInput = false - ) - } - operator fun minus(other: Int): IntModulo = - IntModulo( - (residue - other) % modulus, - modulus, - toCheckInput = false - ) - operator fun times(other: IntModulo): IntModulo { - require(modulus == other.modulus) { "can not multiply two residue different modulo" } - return IntModulo( - (residue * other.residue) % modulus, - modulus, - toCheckInput = false - ) - } - operator fun times(other: Int): IntModulo = - IntModulo( - (residue * other) % modulus, - modulus, - toCheckInput = false - ) - operator fun div(other: IntModulo): IntModulo { - require(modulus == other.modulus) { "can not divide two residue different modulo" } - val (reciprocalCandidate, gcdOfOtherResidueAndModulus) = bezoutIdentityWithGCD(other.residue, modulus) - require(gcdOfOtherResidueAndModulus == 1) { "can not divide to residue that has non-trivial GCD with modulo" } - return IntModulo( - (residue * reciprocalCandidate) % modulus, - modulus, - toCheckInput = false - ) - } - operator fun div(other: Int): IntModulo { - val (reciprocalCandidate, gcdOfOtherResidueAndModulus) = bezoutIdentityWithGCD(other, modulus) - require(gcdOfOtherResidueAndModulus == 1) { "can not divide to residue that has non-trivial GCD with modulo" } - return IntModulo( - (residue * reciprocalCandidate) % modulus, - modulus, - toCheckInput = false - ) - } - override fun equals(other: Any?): Boolean = - when (other) { - is IntModulo -> residue == other.residue && modulus == other.modulus - else -> false - } - - override fun hashCode(): Int = residue.hashCode() - - override fun toString(): String = "$residue mod $modulus" -} - -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") -class IntModuloRing : Ring { - - val modulus: Int - - constructor(modulus: Int) { - require(modulus != 0) { "modulus can not be zero" } - this.modulus = if (modulus < 0) -modulus else modulus - } - - override inline val zero: IntModulo get() = IntModulo(0, modulus, toCheckInput = false) - override inline val one: IntModulo get() = IntModulo(1, modulus, toCheckInput = false) - - fun number(arg: Int): IntModulo = IntModulo(arg, modulus, toCheckInput = false) - - override inline fun add(left: IntModulo, right: IntModulo): IntModulo = left + right - override inline fun multiply(left: IntModulo, right: IntModulo): IntModulo = left * right - - override inline fun IntModulo.unaryMinus(): IntModulo = -this - override inline fun IntModulo.plus(arg: IntModulo): IntModulo = this + arg - override inline fun IntModulo.minus(arg: IntModulo): IntModulo = this - arg - override inline fun IntModulo.times(arg: IntModulo): IntModulo = this * arg - inline fun IntModulo.div(arg: IntModulo): IntModulo = this / arg -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt deleted file mode 100644 index 33fd03aa0..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/IntModuloUtils.kt +++ /dev/null @@ -1,19 +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.functions.testUtils - -import space.kscience.kmath.functions.ListPolynomial -import space.kscience.kmath.functions.ListPolynomialSpace -import space.kscience.kmath.functions.PolynomialSpaceOverRing - - -fun ListPolynomialSpace.ListPolynomial(vararg coefs: Int): ListPolynomial = - ListPolynomial(coefs.map { IntModulo(it, ring.modulus) }) -fun IntModuloRing.ListPolynomial(vararg coefs: Int): ListPolynomial = - ListPolynomial(coefs.map { IntModulo(it, modulus) }) - -fun IntModuloRing.m(arg: Int): IntModulo = IntModulo(arg, modulus) -fun PolynomialSpaceOverRing.m(arg: Int): IntModulo = IntModulo(arg, ring.modulus) \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/NTMisc.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/NTMisc.kt deleted file mode 100644 index ff67f19d8..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/NTMisc.kt +++ /dev/null @@ -1,29 +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.functions.testUtils - -import kotlin.math.abs - - -internal data class BezoutIdentityWithGCD(val first: T, val second: T, val gcd: T) - -internal tailrec fun gcd(a: Long, b: Long): Long = if (a == 0L) abs(b) else gcd(b % a, a) - -internal fun bezoutIdentityWithGCD(a: Int, b: Int): BezoutIdentityWithGCD = - when { - a < 0 && b < 0 -> with(bezoutIdentityWithGCDInternalLogic(-a, -b, 1, 0, 0, 1)) { BezoutIdentityWithGCD(-first, -second, gcd) } - a < 0 -> with(bezoutIdentityWithGCDInternalLogic(-a, b, 1, 0, 0, 1)) { BezoutIdentityWithGCD(-first, second, gcd) } - b < 0 -> with(bezoutIdentityWithGCDInternalLogic(a, -b, 1, 0, 0, 1)) { BezoutIdentityWithGCD(first, -second, gcd) } - else -> bezoutIdentityWithGCDInternalLogic(a, b, 1, 0, 0, 1) - } - -internal tailrec fun bezoutIdentityWithGCDInternalLogic(a: Int, b: Int, m1: Int, m2: Int, m3: Int, m4: Int): BezoutIdentityWithGCD = - if (b == 0) BezoutIdentityWithGCD(m1, m3, a) - else { - val quotient = a / b - val reminder = a % b - bezoutIdentityWithGCDInternalLogic(b, reminder, m2, m1 - quotient * m2, m4, m3 - quotient * m4) - } \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt deleted file mode 100644 index 19cb77df5..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/Rational.kt +++ /dev/null @@ -1,177 +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:Suppress("NOTHING_TO_INLINE", "KotlinRedundantDiagnosticSuppress") - -package space.kscience.kmath.functions.testUtils - -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.operations.Field -import space.kscience.kmath.operations.NumbersAddOps - -@Suppress("NAME_SHADOWING") -class Rational { - companion object { - val ZERO: Rational = Rational(0L) - val ONE: Rational = Rational(1L) - } - - val numerator: Long - val denominator: Long - - internal constructor(numerator: Long, denominator: Long, toCheckInput: Boolean = true) { - if (toCheckInput) { - if (denominator == 0L) throw ArithmeticException("/ by zero") - - val greatestCommonDivider = gcd(numerator, denominator).let { if (denominator < 0L) -it else it } - - this.numerator = numerator / greatestCommonDivider - this.denominator = denominator / greatestCommonDivider - } else { - this.numerator = numerator - this.denominator = denominator - } - } - - constructor(numerator: Int, denominator: Int) : this(numerator.toLong(), denominator.toLong(), true) - constructor(numerator: Int, denominator: Long) : this(numerator.toLong(), denominator, true) - constructor(numerator: Long, denominator: Int) : this(numerator, denominator.toLong(), true) - constructor(numerator: Long, denominator: Long) : this(numerator, denominator, true) - constructor(numerator: Int) : this(numerator.toLong(), 1L, false) - constructor(numerator: Long) : this(numerator, 1L, false) - - operator fun unaryPlus(): Rational = this - operator fun unaryMinus(): Rational = Rational(-this.numerator, this.denominator) - operator fun plus(other: Rational): Rational { - val denominatorsGcd = gcd(denominator, other.denominator) - val dividedThisDenominator = denominator / denominatorsGcd - val dividedOtherDenominator = other.denominator / denominatorsGcd - val numeratorCandidate = numerator * dividedOtherDenominator + dividedThisDenominator * other.numerator - val secondGcd = gcd(numeratorCandidate, denominatorsGcd) - return Rational( - numeratorCandidate / secondGcd, - dividedThisDenominator * (other.denominator / secondGcd), - toCheckInput = false - ) - } - operator fun plus(other: Int): Rational = - Rational( - numerator + denominator * other.toLong(), - denominator, - toCheckInput = false - ) - operator fun plus(other: Long): Rational = - Rational( - numerator + denominator * other, - denominator, - toCheckInput = false - ) - operator fun minus(other: Rational): Rational { - val denominatorsGcd = gcd(denominator, other.denominator) - val dividedThisDenominator = denominator / denominatorsGcd - val dividedOtherDenominator = other.denominator / denominatorsGcd - val numeratorCandidate = numerator * dividedOtherDenominator - dividedThisDenominator * other.numerator - val secondGcd = gcd(numeratorCandidate, denominatorsGcd) - return Rational( - numeratorCandidate / secondGcd, - dividedThisDenominator * (other.denominator / secondGcd), - toCheckInput = false - ) - } - operator fun minus(other: Int): Rational = - Rational( - numerator - denominator * other.toLong(), - denominator, - toCheckInput = false - ) - operator fun minus(other: Long): Rational = - Rational( - numerator - denominator * other, - denominator, - toCheckInput = false - ) - operator fun times(other: Rational): Rational { - val thisDenominatorAndOtherNumeratorGcd = gcd(denominator, other.numerator) - val otherDenominatorAndThisNumeratorGcd = gcd(other.denominator, numerator) - return Rational( - (numerator / otherDenominatorAndThisNumeratorGcd) * (other.numerator / thisDenominatorAndOtherNumeratorGcd), - (denominator / thisDenominatorAndOtherNumeratorGcd) * (other.denominator / otherDenominatorAndThisNumeratorGcd), - toCheckInput = false - ) - } - operator fun times(other: Int): Rational { - val other = other.toLong() - val denominatorAndOtherGcd = gcd(denominator, other) - return Rational( - numerator * (other / denominatorAndOtherGcd), - denominator / denominatorAndOtherGcd, - toCheckInput = false - ) - } - operator fun times(other: Long): Rational { - val denominatorAndOtherGcd = gcd(denominator, other) - return Rational( - numerator * (other / denominatorAndOtherGcd), - denominator / denominatorAndOtherGcd, - toCheckInput = false - ) - } - operator fun div(other: Rational): Rational { - val denominatorsGcd = gcd(denominator, other.denominator) - val numeratorsGcd = gcd(numerator, other.numerator) - return Rational( - (numerator / numeratorsGcd) * (other.denominator / denominatorsGcd), - (denominator / denominatorsGcd) * (other.numerator / numeratorsGcd) - ) - } - operator fun div(other: Int): Rational { - val other = other.toLong() - val numeratorAndOtherGcd = gcd(numerator, other) - return Rational( - numerator / numeratorAndOtherGcd, - denominator * (other / numeratorAndOtherGcd), - toCheckInput = false - ) - } - operator fun div(other: Long): Rational { - val numeratorAndOtherGcd = gcd(numerator, other) - return Rational( - numerator / numeratorAndOtherGcd, - denominator * (other / numeratorAndOtherGcd), - toCheckInput = false - ) - } - override fun equals(other: Any?): Boolean = - when (other) { - is Rational -> numerator == other.numerator && denominator == other.denominator - is Int -> numerator == other && denominator == 1L - is Long -> numerator == other && denominator == 1L - else -> false - } - - override fun hashCode(): Int = 31 * numerator.hashCode() + denominator.hashCode() - - override fun toString(): String = if (denominator == 1L) "$numerator" else "$numerator/$denominator" -} - -@Suppress("EXTENSION_SHADOWED_BY_MEMBER", "OVERRIDE_BY_INLINE") -@OptIn(UnstableKMathAPI::class) -object RationalField : Field, NumbersAddOps { - override inline val zero: Rational get() = Rational.ZERO - override inline val one: Rational get() = Rational.ONE - - override inline fun number(value: Number): Rational = Rational(value.toLong()) - - override inline fun add(left: Rational, right: Rational): Rational = left + right - override inline fun multiply(left: Rational, right: Rational): Rational = left * right - override inline fun divide(left: Rational, right: Rational): Rational = left / right - override inline fun scale(a: Rational, value: Double): Rational = a * number(value) - - override inline fun Rational.unaryMinus(): Rational = -this - override inline fun Rational.plus(arg: Rational): Rational = this + arg - override inline fun Rational.minus(arg: Rational): Rational = this - arg - override inline fun Rational.times(arg: Rational): Rational = this * arg - override inline fun Rational.div(arg: Rational): Rational = this / arg -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/assertion.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/assertion.kt deleted file mode 100644 index 4ef87f736..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/assertion.kt +++ /dev/null @@ -1,104 +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.functions.testUtils - -import space.kscience.kmath.functions.LabeledPolynomial -import space.kscience.kmath.functions.LabeledRationalFunction -import space.kscience.kmath.functions.NumberedPolynomial -import space.kscience.kmath.functions.NumberedRationalFunction -import kotlin.test.assertEquals -import kotlin.test.assertFailsWith - - -fun assertContentEquals( - expected: Map, - actual: Map, - absoluteTolerance: Double, - message: String? = null -) { - assertEquals(expected.keys, actual.keys, message) - for ((key, expectedValue) in expected) assertEquals(expectedValue, actual[key]!!, absoluteTolerance, message) -} - -fun assertEquals( - expected: NumberedPolynomial, - actual: NumberedPolynomial, - absoluteTolerance: Double, - message: String? = null -) { - assertContentEquals( - expected.coefficients, - actual.coefficients, - absoluteTolerance, - message - ) -} - -fun assertEquals( - expected: LabeledPolynomial, - actual: LabeledPolynomial, - absoluteTolerance: Double, - message: String? = null -) { - assertContentEquals( - expected.coefficients, - actual.coefficients, - absoluteTolerance, - message - ) -} - -fun assertEquals( - expected: NumberedRationalFunction, - actual: NumberedRationalFunction, - absoluteTolerance: Double, - message: String? = null -) { - assertEquals( - expected.numerator, - actual.numerator, - absoluteTolerance, - message - ) - assertEquals( - expected.denominator, - actual.denominator, - absoluteTolerance, - message - ) -} - -fun assertEquals( - expected: LabeledRationalFunction, - actual: LabeledRationalFunction, - absoluteTolerance: Double, - message: String? = null -) { - assertEquals( - expected.numerator, - actual.numerator, - absoluteTolerance, - message - ) - assertEquals( - expected.denominator, - actual.denominator, - absoluteTolerance, - message - ) -} - -inline fun assertFailsWithTypeAndMessage( - expectedMessage: String? = null, - assertionMessage: String? = null, - block: () -> Unit -) { - assertEquals( - expectedMessage, - assertFailsWith(T::class, assertionMessage, block).message, - assertionMessage - ) -} \ No newline at end of file diff --git a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt b/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt deleted file mode 100644 index 93c3f8ea5..000000000 --- a/kmath-polynomial/src/commonTest/kotlin/space/kscience/kmath/functions/testUtils/misc.kt +++ /dev/null @@ -1,19 +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.functions.testUtils - -import space.kscience.kmath.expressions.Symbol -import space.kscience.kmath.expressions.symbol - - -val o: Rational = Rational(0) - -val x: Symbol by symbol -val y: Symbol by symbol -val z: Symbol by symbol -val t: Symbol by symbol -val s: Symbol by symbol -val iota: Symbol by symbol \ No newline at end of file diff --git a/kmath-stat/README.md b/kmath-stat/README.md index 7ed20fcf4..e7e0a4d92 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-stat:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-stat:0.3.1-dev-1' + implementation 'space.kscience:kmath-stat:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-stat:0.3.1-dev-1") + implementation("space.kscience:kmath-stat:0.4.0-dev-1") } ``` diff --git a/kmath-stat/build.gradle.kts b/kmath-stat/build.gradle.kts index b458135b3..000280def 100644 --- a/kmath-stat/build.gradle.kts +++ b/kmath-stat/build.gradle.kts @@ -1,17 +1,22 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") +} + +kscience{ + jvm() + js() + native() } kotlin.sourceSets { commonMain { dependencies { - api(project(":kmath-coroutines")) - implementation(npmlibs.atomicfu) + api(projects.kmathCoroutines) + //implementation(spclibs.atomicfu) } } - jvmMain { + getByName("jvmMain") { dependencies { api("org.apache.commons:commons-rng-sampling:1.3") api("org.apache.commons:commons-rng-simple:1.3") @@ -20,5 +25,5 @@ kotlin.sourceSets { } readme { - maturity = ru.mipt.npm.gradle.Maturity.EXPERIMENTAL + maturity = space.kscience.gradle.Maturity.EXPERIMENTAL } \ 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 8dbcb3367..806da5560 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 @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.distributions import space.kscience.kmath.chains.Chain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.stat.Sampler /** diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/FactorizedDistribution.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/FactorizedDistribution.kt index 1218f13c5..999fbffbc 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/FactorizedDistribution.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/FactorizedDistribution.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,7 +7,7 @@ package space.kscience.kmath.distributions import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.SimpleChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator /** * A multivariate distribution that takes a map of parameters. 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 cfc6eba04..ae814254b 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 @@ -1,16 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.distributions import space.kscience.kmath.chains.Chain -import space.kscience.kmath.internal.InternalErf +import space.kscience.kmath.operations.DoubleField.pow +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.samplers.GaussianSampler +import space.kscience.kmath.samplers.InternalErf import space.kscience.kmath.samplers.NormalizedGaussianSampler import space.kscience.kmath.samplers.ZigguratNormalizedGaussianSampler -import space.kscience.kmath.stat.RandomGenerator import kotlin.math.* /** @@ -34,8 +35,23 @@ public class NormalDistribution(public val sampler: GaussianSampler) : Distribut } } - private companion object { + public companion object { private val SQRT2 = sqrt(2.0) + + /** + * Zelen & Severo approximation for the standard normal CDF. + * The error upper boundary by 7.5 * 10e-8. + */ + public fun zSNormalCDF(x: Double): Double { + val t = 1 / (1 + 0.2316419 * abs(x)) + val sum = 0.319381530 * t - + 0.356563782 * t.pow(2) + + 1.781477937 * t.pow(3) - + 1.821255978 * t.pow(4) + + 1.330274429 * t.pow(5) + val temp = sum * exp(-abs(x).pow(2) / 2) / (2 * PI).pow(0.5) + return if (x >= 0) 1 - temp else temp + } } } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/UniformDistribution.kt similarity index 83% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/UniformDistribution.kt index 20cc0e802..953be06fd 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/UniformDistribution.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/distributions/UniformDistribution.kt @@ -1,14 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 +package space.kscience.kmath.distributions import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.SimpleChain -import space.kscience.kmath.distributions.Distribution -import space.kscience.kmath.distributions.Distribution1D +import space.kscience.kmath.random.RandomGenerator public class UniformDistribution(public val range: ClosedFloatingPointRange) : Distribution1D { private val length: Double = range.endInclusive - range.start diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/MCScope.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/MCScope.kt similarity index 89% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/MCScope.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/MCScope.kt index 0e06fa162..2049a84fc 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/MCScope.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/MCScope.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 +package space.kscience.kmath.random import kotlinx.coroutines.* import kotlin.contracts.InvocationKind @@ -22,6 +22,10 @@ public class MCScope( public val random: RandomGenerator, ) +public fun MCScope.asCoroutineScope(): CoroutineScope = object : CoroutineScope { + override val coroutineContext: CoroutineContext get() = this@asCoroutineScope.coroutineContext +} + /** * Launches a supervised Monte-Carlo scope */ diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomChain.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomChain.kt similarity index 94% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomChain.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomChain.kt index d4bc36b5b..7e0ee3cd4 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomChain.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomChain.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 +package space.kscience.kmath.random import space.kscience.kmath.chains.BlockingDoubleChain import space.kscience.kmath.chains.Chain diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomGenerator.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomGenerator.kt similarity index 98% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomGenerator.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomGenerator.kt index f280a78aa..f7388006e 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/RandomGenerator.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/random/RandomGenerator.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 +package space.kscience.kmath.random import space.kscience.kmath.structures.DoubleBuffer import kotlin.random.Random diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterExponentialSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterExponentialSampler.kt index 77d29981f..e5a48d4d8 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterExponentialSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterExponentialSampler.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingDoubleChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.stat.Sampler import space.kscience.kmath.structures.DoubleBuffer import kotlin.math.ln @@ -67,7 +67,7 @@ public class AhrensDieterExponentialSampler(public val mean: Double) : Sampler - qi += ln2.pow(i + 1.0) / space.kscience.kmath.internal.InternalUtils.factorial(i + 1) + qi += ln2.pow(i + 1.0) / InternalUtils.factorial(i + 1) qi } } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterMarsagliaTsangGammaSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterMarsagliaTsangGammaSampler.kt index 993215d41..d301ff637 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterMarsagliaTsangGammaSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AhrensDieterMarsagliaTsangGammaSampler.kt @@ -1,14 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.Chain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.random.chain import space.kscience.kmath.stat.Sampler -import space.kscience.kmath.stat.chain import space.kscience.kmath.stat.next import kotlin.math.* @@ -25,14 +25,14 @@ import kotlin.math.* */ public class AhrensDieterMarsagliaTsangGammaSampler private constructor( alpha: Double, - theta: Double + theta: Double, ) : Sampler { private val delegate: BaseGammaSampler = if (alpha < 1) AhrensDieterGammaSampler(alpha, theta) else MarsagliaTsangGammaSampler(alpha, theta) private abstract class BaseGammaSampler internal constructor( protected val alpha: Double, - protected val theta: Double + protected val theta: Double, ) : Sampler { init { require(alpha > 0) { "alpha is not strictly positive: $alpha" } @@ -119,7 +119,7 @@ public class AhrensDieterMarsagliaTsangGammaSampler private constructor( public companion object { public fun of( alpha: Double, - theta: Double + theta: Double, ): Sampler = AhrensDieterMarsagliaTsangGammaSampler(alpha, theta) } } \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AliasMethodDiscreteSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AliasMethodDiscreteSampler.kt index 5390a2e09..2ec40c347 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AliasMethodDiscreteSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/AliasMethodDiscreteSampler.kt @@ -1,15 +1,14 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.Chain -import space.kscience.kmath.internal.InternalUtils -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.random.chain import space.kscience.kmath.stat.Sampler -import space.kscience.kmath.stat.chain import kotlin.math.ceil import kotlin.math.max import kotlin.math.min diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/BoxMullerSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/BoxMullerSampler.kt index b3c014553..7795ff297 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/BoxMullerSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/BoxMullerSampler.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingDoubleChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.structures.DoubleBuffer import kotlin.math.* diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/GaussianSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/GaussianSampler.kt index 9219df43e..28d588165 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/GaussianSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/GaussianSampler.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,7 +7,7 @@ package space.kscience.kmath.samplers import space.kscience.kmath.chains.BlockingDoubleChain import space.kscience.kmath.chains.map -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator /** * Sampling from a Gaussian distribution with given mean and standard deviation. @@ -21,7 +21,7 @@ import space.kscience.kmath.stat.RandomGenerator public class GaussianSampler( public val mean: Double, public val standardDeviation: Double, - private val normalized: NormalizedGaussianSampler = BoxMullerSampler + private val normalized: NormalizedGaussianSampler = BoxMullerSampler, ) : BlockingDoubleSampler { init { diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalErf.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalErf.kt similarity index 87% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalErf.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalErf.kt index 25668446c..0c1a5b36f 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalErf.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalErf.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.internal +package space.kscience.kmath.samplers import kotlin.math.abs diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalGamma.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalGamma.kt similarity index 99% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalGamma.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalGamma.kt index 63db1c56f..43c5a0d3c 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalGamma.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalGamma.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.internal +package space.kscience.kmath.samplers import kotlin.math.* diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalUtils.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalUtils.kt similarity index 96% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalUtils.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalUtils.kt index 71fd15fe6..9f633e3db 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/internal/InternalUtils.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/InternalUtils.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.internal +package space.kscience.kmath.samplers import kotlin.math.ln import kotlin.math.min diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/KempSmallMeanPoissonSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/KempSmallMeanPoissonSampler.kt index 0105731c4..6d2899314 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/KempSmallMeanPoissonSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/KempSmallMeanPoissonSampler.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingIntChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.stat.Sampler import space.kscience.kmath.structures.IntBuffer import kotlin.math.exp diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/MarsagliaNormalizedGaussianSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/MarsagliaNormalizedGaussianSampler.kt index 0a68e5c88..3c3fe10fd 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/MarsagliaNormalizedGaussianSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/MarsagliaNormalizedGaussianSampler.kt @@ -1,12 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingDoubleChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.structures.DoubleBuffer import kotlin.math.ln import kotlin.math.sqrt diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/NormalizedGaussianSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/NormalizedGaussianSampler.kt index 83f87e832..291d0bffe 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/NormalizedGaussianSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/NormalizedGaussianSampler.kt @@ -1,15 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingDoubleChain -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.stat.Sampler -public interface BlockingDoubleSampler: Sampler{ +public interface BlockingDoubleSampler : Sampler { override fun sample(generator: RandomGenerator): BlockingDoubleChain } @@ -18,6 +18,6 @@ public interface BlockingDoubleSampler: Sampler{ * Marker interface for a sampler that generates values from an N(0,1) * [Gaussian distribution](https://en.wikipedia.org/wiki/Normal_distribution). */ -public fun interface NormalizedGaussianSampler : BlockingDoubleSampler{ +public fun interface NormalizedGaussianSampler : BlockingDoubleSampler { public companion object } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/PoissonSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/PoissonSampler.kt index f0f94900e..454691e05 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/PoissonSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/PoissonSampler.kt @@ -1,14 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingIntChain -import space.kscience.kmath.internal.InternalUtils import space.kscience.kmath.misc.toIntExact -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.stat.Sampler import space.kscience.kmath.structures.IntBuffer import kotlin.math.* diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/Sampler.kt similarity index 94% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/Sampler.kt index 1c88922ac..b87a429df 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Sampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/Sampler.kt @@ -1,14 +1,15 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.coroutines.flow.first +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.combine -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.BufferFactory import space.kscience.kmath.structures.DoubleBuffer diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/SamplerAlgebra.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/SamplerAlgebra.kt similarity index 91% rename from kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/SamplerAlgebra.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/SamplerAlgebra.kt index 1f442c09b..44b87a431 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/SamplerAlgebra.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/SamplerAlgebra.kt @@ -1,9 +1,9 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 +package space.kscience.kmath.samplers import space.kscience.kmath.chains.Chain import space.kscience.kmath.chains.ConstantChain @@ -12,6 +12,8 @@ import space.kscience.kmath.chains.zip import space.kscience.kmath.operations.Group import space.kscience.kmath.operations.ScaleOperations import space.kscience.kmath.operations.invoke +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.stat.Sampler /** * Implements [Sampler] by sampling only certain [value]. diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/ZigguratNormalizedGaussianSampler.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/ZigguratNormalizedGaussianSampler.kt index b534fdc14..40ce37d15 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/ZigguratNormalizedGaussianSampler.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/samplers/ZigguratNormalizedGaussianSampler.kt @@ -1,13 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.samplers import space.kscience.kmath.chains.BlockingDoubleChain -import space.kscience.kmath.misc.toIntExact -import space.kscience.kmath.stat.RandomGenerator +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.structures.DoubleBuffer import kotlin.math.* diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/MonotonicSeriesAlgebra.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/MonotonicSeriesAlgebra.kt new file mode 100644 index 000000000..ed6f4e07b --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/MonotonicSeriesAlgebra.kt @@ -0,0 +1,41 @@ +/* + * Copyright 2018-2023 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.series + +import space.kscience.kmath.operations.BufferAlgebra +import space.kscience.kmath.operations.Ring +import space.kscience.kmath.structures.Buffer +import kotlin.math.ceil +import kotlin.math.floor + +/** + * A [SeriesAlgebra] with reverse label to index transformation. + * + * @param [labelToOffset] returns floating point number that is used for index resolution. + */ +public class MonotonicSeriesAlgebra, out BA : BufferAlgebra, L : Comparable>( + bufferAlgebra: BA, + offsetToLabel: (Int) -> L, + private val labelToOffset: (L) -> Double, +) : SeriesAlgebra(bufferAlgebra, offsetToLabel) { + + public val Buffer.labelRange: ClosedRange get() = offsetToLabel(startOffset)..offsetToLabel(startOffset + size) + + /** + * An offset of the given [label] rounded down + */ + public fun floorOffset(label: L): Int = floor(labelToOffset(label)).toInt() + + /** + * An offset of the given [label] rounded up + */ + public fun ceilOffset(label: L): Int = ceil(labelToOffset(label)).toInt() + + /** + * Get value by label (rounded down) or return null if the value is outside series boundaries. + */ + override fun Buffer.getByLabelOrNull(label: L): T? = getByOffsetOrNull(floorOffset(label)) +} \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/SeriesAlgebra.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/SeriesAlgebra.kt new file mode 100644 index 000000000..cabff25e6 --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/SeriesAlgebra.kt @@ -0,0 +1,238 @@ +package space.kscience.kmath.series + +import space.kscience.kmath.operations.BufferAlgebra +import space.kscience.kmath.operations.Ring +import space.kscience.kmath.operations.RingOps +import space.kscience.kmath.stat.StatisticalAlgebra +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.BufferView +import space.kscience.kmath.structures.getOrNull +import kotlin.math.max +import kotlin.math.min + +@PublishedApi +internal fun IntRange.intersect(other: IntRange): IntRange = + max(first, other.first)..min(last, other.last) + +@PublishedApi +internal val IntRange.size: Int + get() = last - first + 1 + +@PublishedApi +internal operator fun IntRange.contains(other: IntRange): Boolean = (other.first in this) && (other.last in this) + +//TODO add permutation sort +//TODO check rank statistics + +/** + * A [Buffer] with an offset relative to the [SeriesAlgebra] zero. + */ +public interface Series : Buffer { + public val origin: Buffer + + /** + * Absolute position of start of this [Series] in [SeriesAlgebra] + */ + public val position: Int +} + +/** + * A [BufferView] with index offset (both positive and negative) and possible size change + */ +private class SeriesImpl( + override val origin: Buffer, + override val position: Int, + override val size: Int = origin.size, +) : Series, Buffer by origin { + + init { + require(size > 0) { "Size must be positive" } + require(size <= origin.size) { "Slice size is larger than the original buffer" } + } + + override fun toString(): String = "$origin-->${position}" +} + +/** + * A scope to operation on series + */ +public open class SeriesAlgebra, out BA : BufferAlgebra, L>( + override val bufferAlgebra: BA, + public val offsetToLabel: (Int) -> L, +) : RingOps>, StatisticalAlgebra { + + /** + * A range of valid offset indices. In general, does not start with zero. + */ + public val Buffer.offsetIndices: IntRange + get() = if (this is Series) { + position until position + size + } else { + 0 until size + } + + /** + * Get the value by absolute offset in the series algebra or return null if index is out of range + */ + public fun Buffer.getByOffsetOrNull(index: Int): T? = when { + index !in offsetIndices -> null + this is Series -> origin.getOrNull(index - position) + else -> getOrNull(index) + } + + /** + * Get the value by absolute index in the series algebra or throw [IndexOutOfBoundsException] if index is out of range + */ + public fun Buffer.getByOffset(index: Int): T = + getByOffsetOrNull(index) ?: throw IndexOutOfBoundsException("Index $index is not in $offsetIndices") + + /** + * Zero-copy move [Buffer] or [Series] to given [position] ignoring series offset if it is present. + */ + public fun Buffer.moveTo(position: Int): Series = if (this is Series) { + SeriesImpl(origin, position, size) + } else { + SeriesImpl(this, position, size) + } + + /** + * Zero-copy move [Buffer] or [Series] by given [offset]. If it is [Series], sum intrinsic series position and the [offset]. + */ + public fun Buffer.moveBy(offset: Int): Series = if (this is Series) { + SeriesImpl(origin, position + offset, size) + } else { + SeriesImpl(this, offset, size) + } + + /** + * An offset of the buffer start relative to [SeriesAlgebra] zero offset + */ + public val Buffer.startOffset: Int get() = if (this is Series) position else 0 + + public val Buffer.startLabel: L get() = offsetToLabel(startOffset) + + /** + * Build a new series by offset positioned at [startOffset]. + */ + public inline fun seriesByOffset( + size: Int, + startOffset: Int = 0, + crossinline block: A.(offset: Int) -> T, + ): Series = elementAlgebra.bufferFactory(size) { + elementAlgebra.block(it + startOffset) + }.moveTo(startOffset) + + /** + * Build a new series by label positioned at [startOffset]. + */ + public inline fun series(size: Int, startOffset: Int = 0, crossinline block: A.(label: L) -> T): Series = + seriesByOffset(size, startOffset) { offset -> block(offsetToLabel(offset)) } + + /** + * Get a label buffer for given buffer. + */ + public val Buffer.labels: List get() = offsetIndices.map(offsetToLabel) + + /** + * Try to resolve element by label and return null if element with a given label is not found + */ + public open fun Buffer.getByLabelOrNull(label: L): T? { + val index = labels.indexOf(label) + if (index == -1) return null + return getByOffset(index + startOffset) + } + + /** + * Get value by label (rounded down) or throw [IndexOutOfBoundsException] if the value is outside series boundaries. + */ + public open fun Buffer.getByLabel(label: L): T = getByLabelOrNull(label) + ?: throw IndexOutOfBoundsException("Label $label is not in ${labels.first()}..${labels.last()}") + + /** + * Map a series to another series of the same size + */ + public inline fun Buffer.map(crossinline transform: A.(T) -> T): Series { + val buf = elementAlgebra.bufferFactory(size) { + elementAlgebra.transform(get(it)) + } + return buf.moveTo(offsetIndices.first) + } + + /** + * Map series to another series of the same size with label + */ + public inline fun Buffer.mapWithLabel(crossinline transform: A.(arg: T, label: L) -> T): Series { + val labels = labels + val buf = elementAlgebra.bufferFactory(size) { + elementAlgebra.transform(getByOffset(it), labels[it]) + } + return buf.moveTo(offsetIndices.first) + } + + public inline fun Buffer.fold(initial: R, operation: A.(acc: R, T) -> R): R { + var accumulator = initial + for (index in this.offsetIndices) accumulator = elementAlgebra.operation(accumulator, getByOffset(index)) + return accumulator + } + + public inline fun Buffer.foldWithLabel(initial: R, operation: A.(acc: R, arg: T, label: L) -> R): R { + val labels = labels + var accumulator = initial + for (index in this.offsetIndices) accumulator = + elementAlgebra.operation(accumulator, getByOffset(index), labels[index]) + return accumulator + } + + /** + * Zip two buffers in the range whe they overlap + */ + public inline fun Buffer.zip( + other: Buffer, + crossinline operation: A.(left: T, right: T) -> T, + ): Series { + val newRange = offsetIndices.intersect(other.offsetIndices) + return seriesByOffset(startOffset = newRange.first, size = newRange.last + 1 - newRange.first) { offset -> + elementAlgebra.operation( + getByOffset(offset), + other.getByOffset(offset) + ) + } + } + + /** + * Zip buffer with itself, but shifted + * */ + public inline fun Buffer.zipWithShift( + shift: Int = 1, + crossinline operation: A.(left: T, right: T) -> T + ): Buffer { + val shifted = this.moveBy(shift) + return zip(shifted, operation) + } + + override fun Buffer.unaryMinus(): Buffer = map { -it } + + override fun add(left: Buffer, right: Buffer): Series = left.zip(right) { l, r -> l + r } + + override fun multiply(left: Buffer, right: Buffer): Buffer = left.zip(right) { l, r -> l * r } + + public fun Buffer.difference(shift: Int=1): Buffer = this.zipWithShift(shift) {l, r -> r - l} + + public companion object +} + +public fun , BA : BufferAlgebra, L> BA.seriesAlgebra(labels: Iterable): SeriesAlgebra { + val l = labels.toList() + return SeriesAlgebra(this) { + if (it in l.indices) l[it] else error("Index $it is outside of labels range ${l.indices}") + } +} + +public fun , BA : BufferAlgebra, L> BA.seriesAlgebra(labelGenerator: (Int) -> L): SeriesAlgebra = + SeriesAlgebra(this, labelGenerator) + +/** + * Create a series algebra using offset as a label + */ +public fun , BA : BufferAlgebra> BA.seriesAlgebra(): SeriesAlgebra = + SeriesAlgebra(this) { it } \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/VarianceRatioTest.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/VarianceRatioTest.kt new file mode 100644 index 000000000..4becb3413 --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/VarianceRatioTest.kt @@ -0,0 +1,82 @@ +/* + * Copyright 2018-2023 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.series + +import space.kscience.kmath.distributions.NormalDistribution +import space.kscience.kmath.operations.DoubleField.pow +import space.kscience.kmath.operations.fold +import kotlin.math.absoluteValue + + +/** + * Container class for Variance Ratio Test result: + * ratio itself, corresponding Z-score, also it's p-value + */ +public data class VarianceRatioTestResult( + val varianceRatio: Double = 1.0, + val zScore: Double = 0.0, + val pValue: Double = 0.5, +) + + +/** + * Calculates the Z-statistic and the p-value for the Lo and MacKinlay's Variance Ratio test (1987) + * under Homoscedastic or Heteroscedstic assumptions + * with two-sided p-value test + * https://ssrn.com/abstract=346975 + * + * @author https://github.com/mrFendel + */ +public fun SeriesAlgebra.varianceRatioTest( + series: Series, + shift: Int, + homoscedastic: Boolean = true, +): VarianceRatioTestResult { + + require(shift > 1) { "Shift must be greater than one" } + require(shift < series.size) { "Shift must be smaller than sample size" } + val sum = { x: Double, y: Double -> x + y } + + + val mean = series.fold(0.0, sum) / series.size + val demeanedSquares = series.map { (it - mean).pow(2) } + val variance = demeanedSquares.fold(0.0, sum) + if (variance == 0.0) return VarianceRatioTestResult() + + + var seriesAgg = series + for (i in 1.. v1 + v2 } + } + + val demeanedSquaresAgg = seriesAgg.map { (it - shift * mean).pow(2) } + val varianceAgg = demeanedSquaresAgg.fold(0.0, sum) + + val varianceRatio = + varianceAgg * (series.size.toDouble() - 1) / variance / (series.size.toDouble() - shift.toDouble() + 1) / (1 - shift.toDouble() / series.size.toDouble()) / shift.toDouble() + + + // calculating asymptotic variance + val phi = if (homoscedastic) { // under homoscedastic null hypothesis + 2 * (2 * shift - 1.0) * (shift - 1.0) / (3 * shift * series.size) + } else { // under heteroscedastic null hypothesis + var accumulator = 0.0 + for (j in 1.. v1 * v2 }.fold(0.0, sum) / variance.pow(2) + accumulator += delta * 4 * (shift - j).toDouble().pow(2) / shift.toDouble().pow(2) + } + accumulator + } + + val zScore = (varianceRatio - 1) / phi.pow(0.5) + val pValue = 2 * (1 - NormalDistribution.zSNormalCDF(zScore.absoluteValue)) + return VarianceRatioTestResult(varianceRatio, zScore, pValue) +} + + + + diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/resampling.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/resampling.kt new file mode 100644 index 000000000..dc21fe6d9 --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/resampling.kt @@ -0,0 +1,22 @@ +/* + * Copyright 2018-2023 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.series + +import space.kscience.kmath.operations.BufferAlgebra +import space.kscience.kmath.operations.Ring +import space.kscience.kmath.operations.sumWithGroupOf + +public fun , BA : BufferAlgebra, L : Comparable> MonotonicSeriesAlgebra.import( + data: List>, +): Series { + val groupedData: Map>> = data.groupBy { floorOffset(it.first) } + val minIndex = groupedData.minOf { it.key } + val maxIndex = groupedData.maxOf { it.key } + return elementAlgebra.bufferFactory(maxIndex - minIndex) { relativeIndex -> + val index = relativeIndex + minIndex + groupedData[index]?.sumWithGroupOf(elementAlgebra) { it.second } ?: elementAlgebra.zero + }.moveTo(minIndex) +} \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/seriesExtensions.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/seriesExtensions.kt new file mode 100644 index 000000000..fa5e0addd --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/series/seriesExtensions.kt @@ -0,0 +1,97 @@ +package space.kscience.kmath.series + +import space.kscience.kmath.operations.BufferAlgebra +import space.kscience.kmath.operations.ExponentialOperations +import space.kscience.kmath.operations.PowerOperations +import space.kscience.kmath.operations.TrigonometricOperations +import space.kscience.kmath.structures.Buffer + + +//trigonometric + +public fun SeriesAlgebra.sin( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.sin(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.cos( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.cos(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.tan( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.tan(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.asin( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.asin(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.acos( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.acos(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.atan( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : TrigonometricOperations> = + bufferAlgebra.atan(arg).moveTo(arg.startOffset) + + +//exponential + +public fun SeriesAlgebra.exp( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.exp(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.ln( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.ln(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.sinh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.sinh(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.cosh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.cosh(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.tanh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.tanh(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.asinh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.asinh(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.acosh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.acosh(arg).moveTo(arg.startOffset) + +public fun SeriesAlgebra.atanh( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : ExponentialOperations> = + bufferAlgebra.atanh(arg).moveTo(arg.startOffset) + + +//power + +public fun SeriesAlgebra.power( + arg: Buffer, + pow: Number, +): Series where BA : BufferAlgebra, BA : PowerOperations> = + bufferAlgebra.power(arg, pow).moveTo(arg.startOffset) + +public fun SeriesAlgebra.sqrt( + arg: Buffer, +): Series where BA : BufferAlgebra, BA : PowerOperations> = + bufferAlgebra.sqrt(arg).moveTo(arg.startOffset) \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Mean.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Mean.kt index aff7d03d9..3bf8b33e8 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Mean.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Mean.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -45,21 +45,23 @@ public class Mean( public companion object { @Deprecated("Use Double.mean instead") public val double: Mean = Mean(DoubleField) { sum, count -> sum / count } + @Deprecated("Use Int.mean instead") public val int: Mean = Mean(IntRing) { sum, count -> sum / count } + @Deprecated("Use Long.mean instead") public val long: Mean = Mean(LongRing) { sum, count -> sum / count } - public fun evaluate(buffer: Buffer): Double = Double.mean.evaluateBlocking(buffer) - public fun evaluate(buffer: Buffer): Int = Int.mean.evaluateBlocking(buffer) - public fun evaluate(buffer: Buffer): Long = Long.mean.evaluateBlocking(buffer) + public fun evaluate(buffer: Buffer): Double = DoubleField.mean.evaluateBlocking(buffer) + public fun evaluate(buffer: Buffer): Int = IntRing.mean.evaluateBlocking(buffer) + public fun evaluate(buffer: Buffer): Long = LongRing.mean.evaluateBlocking(buffer) } } //TODO replace with optimized version which respects overflow -public val Double.Companion.mean: Mean get() = Mean(DoubleField) { sum, count -> sum / count } -public val Int.Companion.mean: Mean get() = Mean(IntRing) { sum, count -> sum / count } -public val Long.Companion.mean: Mean get() = Mean(LongRing) { sum, count -> sum / count } +public val DoubleField.mean: Mean get() = Mean(DoubleField) { sum, count -> sum / count } +public val IntRing.mean: Mean get() = Mean(IntRing) { sum, count -> sum / count } +public val LongRing.mean: Mean get() = Mean(LongRing) { sum, count -> sum / count } diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Median.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Median.kt index c587277f9..87046cd46 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Median.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Median.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Rank.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Rank.kt new file mode 100644 index 000000000..5a873b466 --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Rank.kt @@ -0,0 +1,35 @@ +package space.kscience.kmath.stat + +import space.kscience.kmath.operations.asIterable +import space.kscience.kmath.structures.Buffer + +/** + * Rank statistics + */ +public class Rank> : BlockingStatistic { + override fun evaluateBlocking(data: Buffer): IntArray = Companion.evaluate(data) + + public companion object { + public fun > evaluate(data: Buffer): IntArray { + // https://www.geeksforgeeks.org/rank-elements-array/ + val permutations = ArrayList>(data.size) + data.asIterable().mapIndexedTo(permutations) { i, v -> v to i } + permutations.sortBy { it.first } + var rank = 1 + var i = 0 + val r = IntArray(data.size) + while (i < data.size) { + var j = i + while (j < data.size - 1 && permutations[j].first == permutations[j + 1]) ++j + val n = j - i + 1 + (0 until n).map { k -> + val idx = permutations[i + k].second + r[idx] = rank + ((n - 1) * 0.5f).toInt() + } + rank += n + i += n + } + return r + } + } +} \ No newline at end of file diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Statistic.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Statistic.kt index 43cd5b402..d7638ff81 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Statistic.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/Statistic.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/StatisticalAlgebra.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/StatisticalAlgebra.kt new file mode 100644 index 000000000..cce61519b --- /dev/null +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/StatisticalAlgebra.kt @@ -0,0 +1,67 @@ +package space.kscience.kmath.stat + +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.misc.sorted +import space.kscience.kmath.operations.* +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.MutableBufferFactory + +public interface StatisticalAlgebra, out BA : BufferAlgebra> : Algebra> { + public val bufferAlgebra: BA + public val elementAlgebra: A get() = bufferAlgebra.elementAlgebra + override val bufferFactory: MutableBufferFactory> get() = bufferAlgebra.bufferFactory +} + +/** + * Compute [empirical CDF function](https://en.wikipedia.org/wiki/Empirical_distribution_function) + */ +public fun > StatisticalAlgebra.ecdf(buffer: Buffer): (T) -> Double = { arg -> + buffer.asIterable().count { it < arg }.toDouble() / buffer.size +} + +/** + * Resulting value of kolmogorov-smirnov two-sample statistic + */ +@UnstableKMathAPI +public data class KMComparisonResult>(val n: Int, val m: Int, val value: T) + +/** + * Kolmogorov-Smirnov sample comparison test + * Implementation copied from https://commons.apache.org/proper/commons-math/javadocs/api-3.6.1/index.html?org/apache/commons/math3/stat/inference/KolmogorovSmirnovTest.html + */ +@UnstableKMathAPI +public fun , A, BA : BufferAlgebra> StatisticalAlgebra.ksComparisonStatistic( + x: Buffer, + y: Buffer, +): KMComparisonResult where A : Group, A : NumericAlgebra = with(elementAlgebra) { + // Copy and sort the sample arrays + val sx = x.sorted() + val sy = y.sorted() + val n = sx.size + val m = sy.size + + var rankX: Int = 0 + var rankY: Int = 0 + var curD: T = zero + + // Find the max difference between cdf_x and cdf_y + var supD: T = zero + do { + val z = if (sx[rankX] <= sy[rankY]) sx[rankX] else sy[rankY] + while (rankX < n && sx[rankX].compareTo(z) == 0) { + rankX += 1 + curD += number(m) + } + + while (rankY < m && sy[rankY].compareTo(z) == 0) { + rankY += 1 + curD -= number(n) + } + + when { + curD > supD -> supD = curD + -curD > supD -> supD = -curD + } + } while (rankX < n && rankY < m) + return KMComparisonResult(n, m, supD) +} \ 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 index 5949213e7..38cd5f900 100644 --- a/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/ValueAndErrorField.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/specialExpressions.kt b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/chiSquaredExpression.kt similarity index 86% rename from kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/specialExpressions.kt rename to kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/chiSquaredExpression.kt index 907ce4004..ca9755ad5 100644 --- a/kmath-core/src/commonMain/kotlin/space/kscience/kmath/expressions/specialExpressions.kt +++ b/kmath-stat/src/commonMain/kotlin/space/kscience/kmath/stat/chiSquaredExpression.kt @@ -1,16 +1,21 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2023 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.expressions +package space.kscience.kmath.stat +import space.kscience.kmath.expressions.AutoDiffProcessor +import space.kscience.kmath.expressions.DifferentiableExpression +import space.kscience.kmath.expressions.ExpressionAlgebra import space.kscience.kmath.operations.ExtendedField import space.kscience.kmath.operations.asIterable import space.kscience.kmath.structures.Buffer import space.kscience.kmath.structures.indices import kotlin.jvm.JvmName +//TODO move to stat + /** * Generate a chi squared expression from given x-y-sigma data and inline model. Provides automatic * differentiation. diff --git a/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestSeries.kt b/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestSeries.kt new file mode 100644 index 000000000..d83abb3f4 --- /dev/null +++ b/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestSeries.kt @@ -0,0 +1,28 @@ +/* + * Copyright 2018-2023 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.series + +import space.kscience.kmath.operations.algebra +import space.kscience.kmath.operations.bufferAlgebra +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.slice +import kotlin.math.PI +import kotlin.test.Test +import kotlin.test.assertEquals + +class TestSeries { + + @Test + fun zip() = with(Double.algebra.bufferAlgebra.seriesAlgebra()){ + val s1 = series(100) { sin(2 * PI * it / 100) + 1.0 } + + val s2 = s1.slice(20..50).moveTo(40) + + val s3: Buffer = s1.zip(s2) { l, r -> l + r } //s1 + s2 + + assertEquals(s3.getByOffset(40),s1.getByOffset(40) + s1.getByOffset(20)) + } +} \ No newline at end of file diff --git a/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestVarianceRatioTest.kt b/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestVarianceRatioTest.kt new file mode 100644 index 000000000..afc0d541d --- /dev/null +++ b/kmath-stat/src/commonTest/kotlin/space/kscience/kmath/series/TestVarianceRatioTest.kt @@ -0,0 +1,72 @@ +/* + * Copyright 2018-2023 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.series + +import space.kscience.kmath.operations.algebra +import space.kscience.kmath.operations.bufferAlgebra +import kotlin.math.PI +import kotlin.test.Test +import kotlin.test.assertEquals + +class TestVarianceRatioTest { + + @Test + fun monotonicData() { + with(Double.algebra.bufferAlgebra.seriesAlgebra()) { + val monotonicData = series(10) { it * 1.0 } + val resultHomo = varianceRatioTest(monotonicData, 2, homoscedastic = true) + assertEquals(1.818181, resultHomo.varianceRatio, 1e-6) + // homoscedastic zScore + assertEquals(2.587318, resultHomo.zScore, 1e-6) + assertEquals(.0096, resultHomo.pValue, 1e-4) + val resultHetero = varianceRatioTest(monotonicData, 2, homoscedastic = false) + // heteroscedastic zScore + assertEquals(0.819424, resultHetero.zScore, 1e-6) + assertEquals(.4125, resultHetero.pValue, 1e-4) + } + } + + @Test + fun volatileData() { + with(Double.algebra.bufferAlgebra.seriesAlgebra()) { + val volatileData = series(10) { sin(PI * it + PI/2) + 1.0} + val resultHomo = varianceRatioTest(volatileData, 2) + assertEquals(0.0, resultHomo.varianceRatio, 1e-6) + // homoscedastic zScore + assertEquals(-3.162277, resultHomo.zScore, 1e-6) + assertEquals(.0015, resultHomo.pValue, 1e-4) + val resultHetero = varianceRatioTest(volatileData, 2, homoscedastic = false) + // heteroscedastic zScore + assertEquals(-1.0540925, resultHetero.zScore, 1e-6) + assertEquals(.2918, resultHetero.pValue, 1e-4) + } + } + + @Test + fun negativeData() { + with(Double.algebra.bufferAlgebra.seriesAlgebra()) { + val negativeData = series(10) { sin(it * 1.2)} + val resultHomo = varianceRatioTest(negativeData, 3) + assertEquals(1.240031, resultHomo.varianceRatio, 1e-6) + // homoscedastic zScore + assertEquals(0.509183, resultHomo.zScore, 1e-6) + val resultHetero = varianceRatioTest(negativeData, 3, homoscedastic = false) + // heteroscedastic zScore + assertEquals(0.209202, resultHetero.zScore, 1e-6) + } + } + + @Test + fun zeroVolatility() { + with(Double.algebra.bufferAlgebra.seriesAlgebra()) { + val zeroVolData = series(10) { 0.0 } + val result = varianceRatioTest(zeroVolData, 4) + assertEquals(1.0, result.varianceRatio, 1e-6) + assertEquals(0.0, result.zScore, 1e-6) + assertEquals(0.5, result.pValue, 1e-4) + } + } +} \ No newline at end of file diff --git a/kmath-stat/src/jvmMain/kotlin/space/kscience/kmath/stat/RandomSourceGenerator.kt b/kmath-stat/src/jvmMain/kotlin/space/kscience/kmath/stat/RandomSourceGenerator.kt index 202a1c8dd..2c6391612 100644 --- a/kmath-stat/src/jvmMain/kotlin/space/kscience/kmath/stat/RandomSourceGenerator.kt +++ b/kmath-stat/src/jvmMain/kotlin/space/kscience/kmath/stat/RandomSourceGenerator.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,13 +7,17 @@ package space.kscience.kmath.stat import org.apache.commons.rng.UniformRandomProvider import org.apache.commons.rng.simple.RandomSource +import space.kscience.kmath.random.RandomGenerator /** * Implements [RandomGenerator] by delegating all operations to [RandomSource]. * * @property source the underlying [RandomSource] object. */ -public class RandomSourceGenerator internal constructor(public val source: RandomSource, seed: Long?) : RandomGenerator { +public class RandomSourceGenerator internal constructor( + public val source: RandomSource, + seed: Long?, +) : RandomGenerator { internal val random: UniformRandomProvider = seed?.let { RandomSource.create(source, seed) } ?: RandomSource.create(source) diff --git a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/CommonsDistributionsTest.kt b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/CommonsDistributionsTest.kt index 19c01e099..b9b9dadba 100644 --- a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/CommonsDistributionsTest.kt +++ b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/CommonsDistributionsTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,6 +8,7 @@ package space.kscience.kmath.stat import kotlinx.coroutines.runBlocking import org.junit.jupiter.api.Assertions import org.junit.jupiter.api.Test +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.samplers.GaussianSampler internal class CommonsDistributionsTest { 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 cca645809..dbcf32e27 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 @@ -1,25 +1,27 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.coroutines.* +import space.kscience.kmath.random.launch +import space.kscience.kmath.random.mcScope import java.util.* import kotlin.test.Test import kotlin.test.assertEquals data class RandomResult(val branch: String, val order: Int, val value: Int) -typealias ATest = suspend CoroutineScope.() -> Set +internal typealias ATest = suspend () -> Set -class MCScopeTest { +internal class MCScopeTest { val simpleTest: ATest = { mcScope(1111) { val res = Collections.synchronizedSet(HashSet()) - launch { + launch{ //println(random) repeat(10) { delay(10) diff --git a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/SamplerTest.kt b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/SamplerTest.kt index 1dbbf591b..0076006e6 100644 --- a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/SamplerTest.kt +++ b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/SamplerTest.kt @@ -1,11 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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 kotlinx.coroutines.runBlocking +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.random.chain import kotlin.test.Test class SamplerTest { diff --git a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/StatisticTest.kt b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/StatisticTest.kt index 9eb84899c..3be7fa314 100644 --- a/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/StatisticTest.kt +++ b/kmath-stat/src/jvmTest/kotlin/space/kscience/kmath/stat/StatisticTest.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -9,6 +9,9 @@ import kotlinx.coroutines.flow.first import kotlinx.coroutines.flow.last import kotlinx.coroutines.flow.take import kotlinx.coroutines.runBlocking +import space.kscience.kmath.operations.DoubleField +import space.kscience.kmath.random.RandomGenerator +import space.kscience.kmath.random.chain import space.kscience.kmath.streaming.chunked import kotlin.test.Test import kotlin.test.assertEquals @@ -25,26 +28,26 @@ internal class StatisticTest { @Test fun singleBlockingMean() { - val first = runBlocking { chunked.first()} - val res = Double.mean(first) - assertEquals(0.5,res, 1e-1) + val first = runBlocking { chunked.first() } + val res = DoubleField.mean(first) + assertEquals(0.5, res, 1e-1) } @Test fun singleSuspendMean() = runBlocking { - val first = runBlocking { chunked.first()} - val res = Double.mean(first) - assertEquals(0.5,res, 1e-1) + val first = runBlocking { chunked.first() } + val res = DoubleField.mean(first) + assertEquals(0.5, res, 1e-1) } @Test fun parallelMean() = runBlocking { - val average = Double.mean + val average = DoubleField.mean .flow(chunked) //create a flow from evaluated results .take(100) // Take 100 data chunks from the source and accumulate them .last() //get 1e5 data samples average - assertEquals(0.5,average, 1e-2) + assertEquals(0.5, average, 1e-2) } } diff --git a/kmath-symja/README.md b/kmath-symja/README.md index a96b0e835..8672c6a71 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-symja:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-symja:0.3.1-dev-1' + implementation 'space.kscience:kmath-symja:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-symja:0.3.1-dev-1") + implementation("space.kscience:kmath-symja:0.4.0-dev-1") } ``` diff --git a/kmath-symja/build.gradle.kts b/kmath-symja/build.gradle.kts index 65c329d52..a996f3bec 100644 --- a/kmath-symja/build.gradle.kts +++ b/kmath-symja/build.gradle.kts @@ -4,14 +4,13 @@ */ plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } description = "Symja integration module" dependencies { - api("org.matheclipse:matheclipse-core:2.0.0-SNAPSHOT") { + api("org.matheclipse:matheclipse-core:2.0.0") { // Incorrect transitive dependencies exclude("org.apfloat", "apfloat") exclude("org.hipparchus", "hipparchus-clustering") @@ -38,5 +37,5 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } diff --git a/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/SymjaExpression.kt b/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/SymjaExpression.kt index 3067b5efb..0f8014913 100644 --- a/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/SymjaExpression.kt +++ b/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/SymjaExpression.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/adapters.kt b/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/adapters.kt index 30c37c799..92f2474b8 100644 --- a/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/adapters.kt +++ b/kmath-symja/src/main/kotlin/space/kscience/kmath/symja/adapters.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-tensorflow/README.md b/kmath-tensorflow/README.md index 83f2eb315..a5b48de4d 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-tensorflow:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-tensorflow:0.3.1-dev-1' + implementation 'space.kscience:kmath-tensorflow:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-tensorflow:0.3.1-dev-1") + implementation("space.kscience:kmath-tensorflow:0.4.0-dev-1") } ``` diff --git a/kmath-tensorflow/build.gradle.kts b/kmath-tensorflow/build.gradle.kts index 9380a7308..1e4ba12da 100644 --- a/kmath-tensorflow/build.gradle.kts +++ b/kmath-tensorflow/build.gradle.kts @@ -1,5 +1,5 @@ plugins { - id("ru.mipt.npm.gradle.jvm") + id("space.kscience.gradle.jvm") } description = "Google tensorflow connector" @@ -11,5 +11,5 @@ dependencies { } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE } \ 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 ad7a978a0..41c7c0b68 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 @@ -1,3 +1,8 @@ +/* + * Copyright 2018-2022 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.tensorflow import org.tensorflow.Graph @@ -5,11 +10,11 @@ import org.tensorflow.Output import org.tensorflow.ndarray.NdArray import org.tensorflow.op.core.Constant import org.tensorflow.types.TFloat64 +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI 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.ColumnStrides +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.PowerOperations @@ -23,6 +28,8 @@ public class DoubleTensorFlowOutput( } +internal fun ShapeND.toLongArray(): LongArray = LongArray(size) { get(it).toLong() } + public class DoubleTensorFlowAlgebra internal constructor( graph: Graph, ) : TensorFlowAlgebra(graph), PowerOperations> { @@ -30,11 +37,11 @@ public class DoubleTensorFlowAlgebra internal constructor( override val elementAlgebra: DoubleField get() = DoubleField override fun structureND( - shape: Shape, + shape: ShapeND, initializer: DoubleField.(IntArray) -> Double, ): StructureND { val res = TFloat64.tensorOf(org.tensorflow.ndarray.Shape.of(*shape.toLongArray())) { array -> - DefaultStrides(shape).forEach { index -> + ColumnStrides(shape).forEach { index -> array.setDouble(elementAlgebra.initializer(index), *index.toLongArray()) } } @@ -88,6 +95,7 @@ public fun DoubleField.produceWithTF( * * The resulting tensors are available outside of scope */ +@OptIn(UnstableKMathAPI::class) public fun DoubleField.produceMapWithTF( block: DoubleTensorFlowAlgebra.() -> Map>, ): Map> = Graph().use { graph -> diff --git a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/IntTensorFlowAlgebra.kt b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/IntTensorFlowAlgebra.kt index 084a445e0..01c8054b3 100644 --- a/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/IntTensorFlowAlgebra.kt +++ b/kmath-tensorflow/src/main/kotlin/space/kscience/kmath/tensorflow/IntTensorFlowAlgebra.kt @@ -1,3 +1,8 @@ +/* + * Copyright 2018-2022 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.tensorflow import org.tensorflow.Graph 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 7185b84d6..73b36cd67 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 @@ -1,3 +1,8 @@ +/* + * Copyright 2018-2022 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.tensorflow @@ -12,10 +17,13 @@ import org.tensorflow.op.core.* import org.tensorflow.types.TInt32 import org.tensorflow.types.family.TNumber import org.tensorflow.types.family.TType -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.nd.asArray +import space.kscience.kmath.nd.contentEquals import space.kscience.kmath.operations.Ring import space.kscience.kmath.tensors.api.Tensor import space.kscience.kmath.tensors.api.TensorAlgebra @@ -33,12 +41,14 @@ public sealed interface TensorFlowTensor : Tensor */ @JvmInline public value class TensorFlowArray(public val tensor: NdArray) : Tensor { - override val shape: Shape get() = tensor.shape().asArray().toIntArray() + override val shape: ShapeND get() = ShapeND(tensor.shape().asArray().toIntArray()) + @PerformancePitfall override fun get(index: IntArray): T = tensor.getObject(*index.toLongArray()) //TODO implement native element sequence + @PerformancePitfall override fun set(index: IntArray, value: T) { tensor.setObject(value, *index.toLongArray()) } @@ -57,7 +67,7 @@ public abstract class TensorFlowOutput( public var output: Output = output internal set - override val shape: Shape get() = output.shape().asArray().toIntArray() + override val shape: ShapeND get() = ShapeND(output.shape().asArray().toIntArray()) protected abstract fun org.tensorflow.Tensor.actualizeTensor(): NdArray @@ -67,11 +77,13 @@ public abstract class TensorFlowOutput( } } + @PerformancePitfall override fun get(index: IntArray): T = actualTensor[index] @PerformancePitfall override fun elements(): Sequence> = actualTensor.elements() + @PerformancePitfall override fun set(index: IntArray, value: T) { actualTensor[index] = value } @@ -91,8 +103,9 @@ public abstract class TensorFlowAlgebra> internal c protected abstract fun const(value: T): Constant - override fun StructureND.valueOrNull(): T? = if (shape contentEquals intArrayOf(1)) - get(Shape(0)) else null + @OptIn(PerformancePitfall::class) + override fun StructureND.valueOrNull(): T? = if (shape contentEquals ShapeND(1)) + get(intArrayOf(0)) else null /** * Perform binary lazy operation on tensor. Both arguments are implicitly converted @@ -179,16 +192,17 @@ public abstract class TensorFlowAlgebra> internal c override fun StructureND.unaryMinus(): TensorFlowOutput = operate(ops.math::neg) - override fun Tensor.get(i: Int): Tensor = operate { + override fun Tensor.getTensor(i: Int): Tensor = operate { StridedSliceHelper.stridedSlice(ops.scope(), it, Indices.at(i.toLong())) } - override fun Tensor.transpose(i: Int, j: Int): Tensor = operate { + override fun StructureND.transposed(i: Int, j: Int): Tensor = operate { ops.linalg.transpose(it, ops.constant(intArrayOf(i, j))) } - override fun Tensor.view(shape: IntArray): Tensor = operate { - ops.reshape(it, ops.constant(shape)) + override fun Tensor.view(shape: ShapeND): Tensor = operate { + @OptIn(UnsafeKMathAPI::class) + ops.reshape(it, ops.constant(shape.asArray())) } override fun Tensor.viewAs(other: StructureND): Tensor = operate(other) { l, r -> @@ -203,7 +217,7 @@ public abstract class TensorFlowAlgebra> internal c } override fun diagonalEmbedding( - diagonalEntries: Tensor, + diagonalEntries: StructureND, offset: Int, dim1: Int, dim2: Int, @@ -233,6 +247,11 @@ public abstract class TensorFlowAlgebra> internal c ops.min(it, ops.constant(dim), Min.keepDims(keepDim)) } + override fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor = IntTensorFlowOutput( + graph, + ops.math.argMin(asTensorFlow().output, ops.constant(dim), TInt32::class.java).output() + ).actualTensor + override fun StructureND.max(): T = operate { ops.max(it, ops.constant(intArrayOf())) }.value() 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 f67c333ce..a0a2ddc80 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ 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 308469eed..730feede6 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 @@ -1,13 +1,22 @@ +/* + * Copyright 2018-2022 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.tensorflow import org.junit.jupiter.api.Test +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.nd.ShapeND 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 space.kscience.kmath.tensors.core.randomNormal import kotlin.test.assertEquals +@OptIn(UnstableKMathAPI::class) class DoubleTensorFlowOps { @Test fun basicOps() { @@ -24,8 +33,8 @@ class DoubleTensorFlowOps { fun dot(){ val dim = 1000 - val tensor1 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12224) - val tensor2 = DoubleTensorAlgebra.randomNormal(shape = intArrayOf(dim, dim), 12225) + val tensor1 = DoubleTensorAlgebra.randomNormal(shape = ShapeND(dim, dim), 12224) + val tensor2 = DoubleTensorAlgebra.randomNormal(shape = ShapeND(dim, dim), 12225) DoubleField.produceWithTF { tensor1 dot tensor2 diff --git a/kmath-tensors/README.md b/kmath-tensors/README.md index 4208cd83d..80f751ffe 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-tensors:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -19,7 +19,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-tensors:0.3.1-dev-1' + implementation 'space.kscience:kmath-tensors:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -30,6 +30,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-tensors:0.3.1-dev-1") + implementation("space.kscience:kmath-tensors:0.4.0-dev-1") } ``` diff --git a/kmath-tensors/build.gradle.kts b/kmath-tensors/build.gradle.kts index 66316d21d..2497314f0 100644 --- a/kmath-tensors/build.gradle.kts +++ b/kmath-tensors/build.gradle.kts @@ -1,17 +1,25 @@ plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") } -kotlin.sourceSets { - all { - languageSettings.optIn("space.kscience.kmath.misc.UnstableKMathAPI") +kscience{ + jvm() + js { + browser { + testTask { + useMocha().timeout = "0" + } + } } + native() - filter { it.name.contains("test", true) } - .map(org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet::languageSettings) - .forEach { it.optIn("space.kscience.kmath.misc.PerformancePitfall") } + dependencies { + api(projects.kmathCore) + api(projects.kmathStat) + } +} + +kotlin.sourceSets { commonMain { dependencies { @@ -19,10 +27,16 @@ kotlin.sourceSets { api(project(":kmath-stat")) } } + + commonTest{ + dependencies{ + implementation(projects.testUtils) + } + } } readme { - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE + maturity = space.kscience.gradle.Maturity.PROTOTYPE propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) feature( 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..1a324b200 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -21,7 +21,7 @@ public interface AnalyticTensorAlgebra> : /** * @return the mean of all elements in the input tensor. */ - public fun StructureND.mean(): T + public fun mean(structureND: StructureND): T /** * Returns the mean of each row of the input tensor in the given dimension [dim]. @@ -34,12 +34,12 @@ public interface AnalyticTensorAlgebra> : * @param keepDim whether the output tensor has [dim] retained or not. * @return the mean of each row of the input tensor in the given dimension [dim]. */ - public fun StructureND.mean(dim: Int, keepDim: Boolean): Tensor + public fun mean(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor /** * @return the standard deviation of all elements in the input tensor. */ - public fun StructureND.std(): T + public fun std(structureND: StructureND): T /** * Returns the standard deviation of each row of the input tensor in the given dimension [dim]. @@ -52,12 +52,12 @@ public interface AnalyticTensorAlgebra> : * @param keepDim whether the output tensor has [dim] retained or not. * @return the standard deviation of each row of the input tensor in the given dimension [dim]. */ - public fun StructureND.std(dim: Int, keepDim: Boolean): Tensor + public fun std(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor /** * @return the variance of all elements in the input tensor. */ - public fun StructureND.variance(): T + public fun variance(structureND: StructureND): T /** * Returns the variance of each row of the input tensor in the given dimension [dim]. @@ -70,80 +70,45 @@ public interface AnalyticTensorAlgebra> : * @param keepDim whether the output tensor has [dim] retained or not. * @return the variance of each row of the input tensor in the given dimension [dim]. */ - public fun StructureND.variance(dim: Int, keepDim: Boolean): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.exp.html - public fun StructureND.exp(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.log.html - public fun StructureND.ln(): Tensor + public fun variance(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor //For information: https://pytorch.org/docs/stable/generated/torch.sqrt.html - public fun StructureND.sqrt(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.acos.html#torch.cos - public fun StructureND.cos(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.acos.html#torch.acos - public fun StructureND.acos(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.acosh.html#torch.cosh - public fun StructureND.cosh(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.acosh.html#torch.acosh - public fun StructureND.acosh(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.asin.html#torch.sin - public fun StructureND.sin(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.asin.html#torch.asin - public fun StructureND.asin(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.asin.html#torch.sinh - public fun StructureND.sinh(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.asin.html#torch.asinh - public fun StructureND.asinh(): Tensor + override fun sqrt(arg: StructureND): Tensor //For information: https://pytorch.org/docs/stable/generated/torch.atan.html#torch.tan - public fun StructureND.tan(): Tensor + override fun tan(arg: StructureND): Tensor //https://pytorch.org/docs/stable/generated/torch.atan.html#torch.atan - public fun StructureND.atan(): Tensor + override fun atan(arg: StructureND): Tensor //For information: https://pytorch.org/docs/stable/generated/torch.atanh.html#torch.tanh - public fun StructureND.tanh(): Tensor - - //For information: https://pytorch.org/docs/stable/generated/torch.atanh.html#torch.atanh - public fun StructureND.atanh(): Tensor + override fun tanh(arg: StructureND): Tensor //For information: https://pytorch.org/docs/stable/generated/torch.ceil.html#torch.ceil - public fun StructureND.ceil(): Tensor + public fun ceil(arg: StructureND): Tensor //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() + public fun floor(structureND: StructureND): Tensor - override fun cos(arg: StructureND): StructureND = arg.cos() + override fun sin(arg: StructureND): StructureND - override fun asin(arg: StructureND): StructureND = arg.asin() + override fun cos(arg: StructureND): StructureND - override fun acos(arg: StructureND): StructureND = arg.acos() + override fun asin(arg: StructureND): StructureND - override fun atan(arg: StructureND): StructureND = arg.atan() + override fun acos(arg: StructureND): StructureND - override fun exp(arg: StructureND): StructureND = arg.exp() + override fun exp(arg: StructureND): StructureND - override fun ln(arg: StructureND): StructureND = arg.ln() + override fun ln(arg: StructureND): StructureND - override fun sinh(arg: StructureND): StructureND = arg.sinh() + override fun sinh(arg: StructureND): StructureND - override fun cosh(arg: StructureND): StructureND = arg.cosh() + override fun cosh(arg: StructureND): StructureND - override fun asinh(arg: StructureND): StructureND = arg.asinh() + override fun asinh(arg: StructureND): StructureND - override fun acosh(arg: StructureND): StructureND = arg.acosh() + override fun acosh(arg: StructureND): StructureND - override fun atanh(arg: StructureND): StructureND = arg.atanh() + override fun atanh(arg: StructureND): StructureND } \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/LinearOpsTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/LinearOpsTensorAlgebra.kt index 0bddc3f9c..f2c7f1821 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/LinearOpsTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/LinearOpsTensorAlgebra.kt @@ -1,10 +1,11 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.api +import space.kscience.kmath.nd.MutableStructure2D import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.Field @@ -21,7 +22,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * * @return the determinant. */ - public fun StructureND.det(): Tensor + public fun StructureND.det(): StructureND /** * Computes the multiplicative inverse matrix of a square matrix input, or of each square matrix in a batched input. @@ -31,7 +32,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * * @return the multiplicative inverse of a matrix. */ - public fun StructureND.inv(): Tensor + public fun StructureND.inv(): StructureND /** * Cholesky decomposition. @@ -47,7 +48,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * @receiver the `input`. * @return the batch of `L` matrices. */ - public fun StructureND.cholesky(): Tensor + public fun cholesky(structureND: StructureND): StructureND /** * QR decomposition. @@ -61,7 +62,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * @receiver the `input`. * @return pair of `Q` and `R` tensors. */ - public fun StructureND.qr(): Pair, Tensor> + public fun qr(structureND: StructureND): Pair, StructureND> /** * LUP decomposition @@ -75,7 +76,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * @receiver the `input`. * @return triple of P, L and U tensors */ - public fun StructureND.lu(): Triple, Tensor, Tensor> + public fun lu(structureND: StructureND): Triple, StructureND, StructureND> /** * Singular Value Decomposition. @@ -91,7 +92,7 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * @receiver the `input`. * @return triple `Triple(U, S, V)`. */ - public fun StructureND.svd(): Triple, Tensor, Tensor> + public fun svd(structureND: StructureND): Triple, StructureND, StructureND> /** * Returns eigenvalues and eigenvectors of a real symmetric matrix `input` or a batch of real symmetric matrices, @@ -101,6 +102,13 @@ public interface LinearOpsTensorAlgebra> : TensorPartialDivision * @receiver the `input`. * @return a pair `eigenvalues to eigenvectors` */ - public fun StructureND.symEig(): Pair, Tensor> + public fun symEig(structureND: StructureND): Pair, StructureND> + /** Returns the solution to the equation Ax = B for the square matrix A as `input1` and + * for the square matrix B as `input2`. + * + * @receiver the `input1` and the `input2`. + * @return the square matrix x which is the solution of the equation. + */ + public fun solve(a: MutableStructure2D, b: MutableStructure2D): MutableStructure2D } diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/Tensor.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/Tensor.kt index 482bb5244..b328fbeec 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/Tensor.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/Tensor.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorAlgebra.kt index 86d4eaa4e..f923400c5 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorAlgebra.kt @@ -1,11 +1,12 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.api import space.kscience.kmath.nd.RingOpsND +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.StructureND import space.kscience.kmath.operations.Ring @@ -166,17 +167,23 @@ public interface TensorAlgebra> : RingOpsND { * @param i index of the extractable tensor * @return subtensor of the original tensor with index [i] */ - public operator fun Tensor.get(i: Int): Tensor + public fun Tensor.getTensor(i: Int): Tensor + + public fun Tensor.getTensor(first: Int, second: Int): Tensor { + return getTensor(first).getTensor(second) + } /** * Returns a tensor that is a transposed version of this tensor. The given dimensions [i] and [j] are swapped. * For more information: https://pytorch.org/docs/stable/generated/torch.transpose.html * + * If axis indices are negative, they are counted from shape end. + * * @param i the first dimension to be transposed * @param j the second dimension to be transposed * @return transposed tensor */ - public fun Tensor.transpose(i: Int = -2, j: Int = -1): Tensor + public fun StructureND.transposed(i: Int = shape.size - 2, j: Int = shape.size - 1): Tensor /** * Returns a new tensor with the same data as the self tensor but of a different shape. @@ -186,7 +193,7 @@ public interface TensorAlgebra> : RingOpsND { * @param shape the desired size * @return tensor with new shape */ - public fun Tensor.view(shape: IntArray): Tensor + public fun Tensor.view(shape: ShapeND): Tensor /** * View this tensor as the same size as [other]. @@ -213,16 +220,7 @@ public interface TensorAlgebra> : RingOpsND { * 4. If the first argument is 2-dimensional and the second argument is 1-dimensional, * the matrix-vector product is returned. * - * 5. If both arguments are at least 1-dimensional and at least one argument is N-dimensional (where N > 2), - * then a batched matrix multiply is returned. If the first argument is 1-dimensional, - * a 1 is prepended to its dimension for the purpose of the batched matrix multiply and removed after. - * If the second argument is 1-dimensional, a 1 is appended to its dimension for the purpose of the batched matrix - * multiple and removed after. - * The non-matrix (i.e., batch) dimensions are broadcast (and thus must be broadcastable). - * For example, if `input` is a (j × 1 × n × n) tensor and `other` is a - * (k × n × n) tensor, out will be a (j × k × n × n) tensor. - * - * For more information: https://pytorch.org/docs/stable/generated/torch.matmul.html + * Otherwise, throw an exception. * * @param other tensor to be multiplied. * @return a mathematical product of two tensors. @@ -253,7 +251,7 @@ public interface TensorAlgebra> : RingOpsND { * are filled by [diagonalEntries] */ public fun diagonalEmbedding( - diagonalEntries: Tensor, + diagonalEntries: StructureND, offset: Int = 0, dim1: Int = -2, dim2: Int = -1, @@ -295,6 +293,19 @@ public interface TensorAlgebra> : RingOpsND { */ public fun StructureND.min(dim: Int, keepDim: Boolean): Tensor + /** + * Returns the index of minimum value of each row of the input tensor in the given dimension [dim]. + * + * If [keepDim] is true, the output tensor is of the same size as + * input except in the dimension [dim] where it is of size 1. + * Otherwise, [dim] is squeezed, resulting in the output tensor having 1 fewer dimension. + * + * @param dim the dimension to reduce. + * @param keepDim whether the output tensor has [dim] retained or not. + * @return the index of maximum value of each row of the input tensor in the given dimension [dim]. + */ + public fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor + /** * Returns the maximum value of all elements in the input tensor or null if there are no values */ @@ -329,4 +340,4 @@ public interface TensorAlgebra> : RingOpsND { override fun add(left: StructureND, right: StructureND): Tensor = left + right override fun multiply(left: StructureND, right: StructureND): Tensor = left * right -} +} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorPartialDivisionAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorPartialDivisionAlgebra.kt index 9c492cda1..33effb2d2 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorPartialDivisionAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/api/TensorPartialDivisionAlgebra.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BroadcastDoubleTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BroadcastDoubleTensorAlgebra.kt index e412ab5bb..7db91722f 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BroadcastDoubleTensorAlgebra.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BroadcastDoubleTensorAlgebra.kt @@ -1,98 +1,88 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.StructureND +import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.tensors.api.Tensor -import space.kscience.kmath.tensors.core.internal.array import space.kscience.kmath.tensors.core.internal.broadcastTensors import space.kscience.kmath.tensors.core.internal.broadcastTo -import space.kscience.kmath.tensors.core.internal.tensor /** * Basic linear algebra operations implemented with broadcasting. * For more information: https://pytorch.org/docs/stable/notes/broadcasting.html */ - -@PerformancePitfall public object BroadcastDoubleTensorAlgebra : DoubleTensorAlgebra() { override fun StructureND.plus(arg: StructureND): DoubleTensor { - val broadcast = broadcastTensors(tensor, arg.tensor) + val broadcast = broadcastTensors(asDoubleTensor(), arg.asDoubleTensor()) val newThis = broadcast[0] val newOther = broadcast[1] - val resBuffer = DoubleArray(newThis.indices.linearSize) { i -> - newThis.mutableBuffer.array()[i] + newOther.mutableBuffer.array()[i] + val resBuffer = DoubleBuffer(newThis.indices.linearSize) { i -> + newThis.source[i] + newOther.source[i] } return DoubleTensor(newThis.shape, resBuffer) } override fun Tensor.plusAssign(arg: StructureND) { - val newOther = broadcastTo(arg.tensor, tensor.shape) - for (i in 0 until tensor.indices.linearSize) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] += - newOther.mutableBuffer.array()[tensor.bufferStart + i] + val newOther = broadcastTo(arg.asDoubleTensor(), asDoubleTensor().shape) + for (i in 0 until asDoubleTensor().indices.linearSize) { + asDoubleTensor().source[i] += newOther.source[i] } } override fun StructureND.minus(arg: StructureND): DoubleTensor { - val broadcast = broadcastTensors(tensor, arg.tensor) + val broadcast = broadcastTensors(asDoubleTensor(), arg.asDoubleTensor()) val newThis = broadcast[0] val newOther = broadcast[1] - val resBuffer = DoubleArray(newThis.indices.linearSize) { i -> - newThis.mutableBuffer.array()[i] - newOther.mutableBuffer.array()[i] + val resBuffer = DoubleBuffer(newThis.indices.linearSize) { i -> + newThis.source[i] - newOther.source[i] } return DoubleTensor(newThis.shape, resBuffer) } override fun Tensor.minusAssign(arg: StructureND) { - val newOther = broadcastTo(arg.tensor, tensor.shape) - for (i in 0 until tensor.indices.linearSize) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] -= - newOther.mutableBuffer.array()[tensor.bufferStart + i] + val newOther = broadcastTo(arg.asDoubleTensor(), asDoubleTensor().shape) + for (i in 0 until indices.linearSize) { + asDoubleTensor().source[i] -= newOther.source[i] } } override fun StructureND.times(arg: StructureND): DoubleTensor { - val broadcast = broadcastTensors(tensor, arg.tensor) + val broadcast = broadcastTensors(asDoubleTensor(), arg.asDoubleTensor()) val newThis = broadcast[0] val newOther = broadcast[1] - val resBuffer = DoubleArray(newThis.indices.linearSize) { i -> - newThis.mutableBuffer.array()[newThis.bufferStart + i] * - newOther.mutableBuffer.array()[newOther.bufferStart + i] + val resBuffer = DoubleBuffer(newThis.indices.linearSize) { i -> + newThis.source[i] * newOther.source[i] } return DoubleTensor(newThis.shape, resBuffer) } override fun Tensor.timesAssign(arg: StructureND) { - val newOther = broadcastTo(arg.tensor, tensor.shape) - for (i in 0 until tensor.indices.linearSize) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] *= - newOther.mutableBuffer.array()[tensor.bufferStart + i] + val newOther = broadcastTo(arg.asDoubleTensor(), asDoubleTensor().shape) + for (i in 0 until indices.linearSize) { + asDoubleTensor().source[+i] *= newOther.source[i] } } override fun StructureND.div(arg: StructureND): DoubleTensor { - val broadcast = broadcastTensors(tensor, arg.tensor) + val broadcast = broadcastTensors(asDoubleTensor(), arg.asDoubleTensor()) val newThis = broadcast[0] val newOther = broadcast[1] - val resBuffer = DoubleArray(newThis.indices.linearSize) { i -> - newThis.mutableBuffer.array()[newOther.bufferStart + i] / - newOther.mutableBuffer.array()[newOther.bufferStart + i] + val resBuffer = DoubleBuffer(newThis.indices.linearSize) { i -> + newThis.source[i] / newOther.source[i] } return DoubleTensor(newThis.shape, resBuffer) } override fun Tensor.divAssign(arg: StructureND) { - val newOther = broadcastTo(arg.tensor, tensor.shape) - for (i in 0 until tensor.indices.linearSize) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] /= - newOther.mutableBuffer.array()[tensor.bufferStart + i] + val newOther = broadcastTo(arg.asDoubleTensor(), asDoubleTensor().shape) + for (i in 0 until indices.linearSize) { + asDoubleTensor().source[i] /= newOther.source[i] } } } @@ -102,6 +92,5 @@ public object BroadcastDoubleTensorAlgebra : DoubleTensorAlgebra() { * Compute a value using broadcast double tensor algebra */ @UnstableKMathAPI -@PerformancePitfall public fun DoubleTensorAlgebra.withBroadcast(block: BroadcastDoubleTensorAlgebra.() -> R): R = BroadcastDoubleTensorAlgebra.block() \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BufferedTensor.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BufferedTensor.kt index 73a89502c..eaec43e2c 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BufferedTensor.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/BufferedTensor.kt @@ -1,11 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.RowStrides +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.nd.Strides import space.kscience.kmath.structures.MutableBuffer import space.kscience.kmath.tensors.api.Tensor @@ -13,28 +15,22 @@ import space.kscience.kmath.tensors.api.Tensor /** * Represents [Tensor] over a [MutableBuffer] intended to be used through [DoubleTensor] and [IntTensor] */ -public open class BufferedTensor internal constructor( - override val shape: IntArray, - @PublishedApi internal val mutableBuffer: MutableBuffer, - @PublishedApi internal val bufferStart: Int, +public abstract class BufferedTensor( + override val shape: ShapeND, ) : Tensor { + public abstract val source: MutableBuffer + /** - * Buffer strides based on [TensorLinearStructure] implementation + * Buffer strides based on [RowStrides] implementation */ - override val indices: Strides get() = TensorLinearStructure(shape) + override val indices: Strides get() = RowStrides(shape) /** * Number of elements in tensor */ - public val numElements: Int - get() = indices.linearSize - - override fun get(index: IntArray): T = mutableBuffer[bufferStart + indices.offset(index)] + public val linearSize: Int get() = indices.linearSize - override fun set(index: IntArray, value: T) { - mutableBuffer[bufferStart + indices.offset(index)] = value - } @PerformancePitfall override fun elements(): Sequence> = indices.asSequence().map { diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor.kt index 8e5116336..d2c2e9d5d 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor.kt @@ -1,20 +1,119 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core -import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnstableKMathAPI +import space.kscience.kmath.nd.MutableStructureNDOfDouble +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.structures.* import space.kscience.kmath.tensors.core.internal.toPrettyString +public class OffsetDoubleBuffer( + override val origin: DoubleBuffer, + private val offset: Int, + override val size: Int, +) : MutableBuffer, BufferView { + + init { + require(offset >= 0) { "Offset must be non-negative" } + require(size >= 0) { "Size must be non-negative" } + require(offset + size <= origin.size) { "Maximum index must be inside source dimension" } + } + + override fun set(index: Int, value: Double) { + require(index in 0 until size) { "Index must be in [0, size)" } + origin[index + offset] = value + } + + override fun get(index: Int): Double = origin[index + offset] + + /** + * Copy only a part of buffer that belongs to this [OffsetDoubleBuffer] + */ + override fun copy(): DoubleBuffer = origin.array.copyOfRange(offset, offset + size).asBuffer() + + override fun iterator(): Iterator = iterator { + for (i in indices) { + yield(get(i)) + } + } + + override fun toString(): String = Buffer.toString(this) + + public fun view(addOffset: Int, newSize: Int = size - addOffset): OffsetDoubleBuffer = + OffsetDoubleBuffer(origin, offset + addOffset, newSize) + + @UnstableKMathAPI + override fun originIndex(index: Int): Int = if (index in 0 until size) { + index + offset + } else { + -1 + } +} + +public fun OffsetDoubleBuffer.slice(range: IntRange): OffsetDoubleBuffer = view(range.first, range.last - range.first) + +/** + * Map only operable content of the offset buffer + */ +public inline fun OffsetDoubleBuffer.map(operation: (Double) -> Double): DoubleBuffer = + DoubleBuffer(size) { operation(get(it)) } + +public inline fun OffsetDoubleBuffer.zip( + other: OffsetDoubleBuffer, + operation: (l: Double, r: Double) -> Double, +): DoubleBuffer { + require(size == other.size) { "The sizes of zipped buffers must be the same" } + return DoubleBuffer(size) { operation(get(it), other[it]) } +} + +/** + * map in place + */ +public inline fun OffsetDoubleBuffer.mapInPlace(operation: (Double) -> Double) { + indices.forEach { set(it, operation(get(it))) } +} + /** - * Default [BufferedTensor] implementation for [Double] values + * Default [BufferedTensor] implementation for [Double] values. + * + * [DoubleTensor] always uses row-based strides */ -public class DoubleTensor @PublishedApi internal constructor( - shape: IntArray, - buffer: DoubleArray, - offset: Int = 0 -) : BufferedTensor(shape, DoubleBuffer(buffer), offset) { +public open class DoubleTensor( + shape: ShapeND, + final override val source: OffsetDoubleBuffer, +) : BufferedTensor(shape), MutableStructureNDOfDouble { + + init { + require(linearSize == source.size) { "Source buffer size must be equal tensor size" } + } + + public constructor(shape: ShapeND, buffer: DoubleBuffer) : this(shape, OffsetDoubleBuffer(buffer, 0, buffer.size)) + + + @OptIn(PerformancePitfall::class) + override fun get(index: IntArray): Double = source[indices.offset(index)] + + @OptIn(PerformancePitfall::class) + override fun set(index: IntArray, value: Double) { + source[indices.offset(index)] = value + } + + override fun getDouble(index: IntArray): Double = source[indices.offset(index)] + + override fun setDouble(index: IntArray, value: Double) { + set(index, value) + } + override fun toString(): String = toPrettyString() } + +public fun DoubleTensor.asDoubleBuffer(): OffsetDoubleBuffer = if (shape.size == 1) { + source +} else { + error("Only 1D tensors could be cast to 1D") +} diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor1D.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor1D.kt new file mode 100644 index 000000000..d2066e404 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor1D.kt @@ -0,0 +1,45 @@ +/* + * Copyright 2018-2022 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.tensors.core + +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.MutableStructure1D +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.structures.MutableBuffer + +public class DoubleTensor1D( + source: OffsetDoubleBuffer, +) : DoubleTensor(ShapeND(source.size), source), MutableStructure1D { + + @PerformancePitfall + override fun get(index: IntArray): Double = super.get(index) + + @PerformancePitfall + override fun set(index: IntArray, value: Double) { + super.set(index, value) + } + + override val size: Int get() = source.size + + override fun get(index: Int): Double = source[index] + + override fun set(index: Int, value: Double) { + source[index] = value + } + + override fun copy(): MutableBuffer = source.copy() + + @PerformancePitfall + override fun elements(): Sequence> = super.elements() +} + +/** + * A zero-copy cast to 1D structure. Changes in resulting structure are reflected on original tensor. + */ +public fun DoubleTensor.asDoubleTensor1D(): DoubleTensor1D { + require(shape.size == 1) { "Only 1D tensors could be cast to 1D" } + return DoubleTensor1D(source) +} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor2D.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor2D.kt new file mode 100644 index 000000000..fa142afa0 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/DoubleTensor2D.kt @@ -0,0 +1,71 @@ +/* + * Copyright 2018-2022 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.tensors.core + +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.MutableStructure2D +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.linearSize +import space.kscience.kmath.structures.PermutedMutableBuffer +import space.kscience.kmath.structures.permute + +public class DoubleTensor2D( + override val rowNum: Int, + override val colNum: Int, + source: OffsetDoubleBuffer, +) : DoubleTensor(ShapeND(rowNum, colNum), source), MutableStructure2D { + + override fun get(i: Int, j: Int): Double = source[i * colNum + j] + + @OptIn(PerformancePitfall::class) + override fun get(index: IntArray): Double = getDouble(index) + + override fun set(i: Int, j: Int, value: Double) { + source[i * colNum + j] = value + } + + @OptIn(PerformancePitfall::class) + override val rows: List + get() = List(rowNum) { i -> + source.view(i * colNum, colNum) + } + + + @OptIn(PerformancePitfall::class) + override val columns: List> + get() = List(colNum) { j -> + val indices = IntArray(rowNum) { i -> j + i * colNum } + source.permute(indices) + } + + override val shape: ShapeND get() = super.shape + + @PerformancePitfall + override fun elements(): Sequence> = super.elements() +} + +/** + * A zero-copy cast to 2D structure. Changes in resulting structure are reflected on original tensor. + */ +public fun DoubleTensor.asDoubleTensor2D(): DoubleTensor2D { + require(shape.size == 2) { "Only 2D tensors could be cast to 2D" } + return DoubleTensor2D(shape[0], shape[1], source) +} + + +public inline fun DoubleTensor.forEachMatrix(block: (index: IntArray, matrix: DoubleTensor2D) -> Unit) { + val n = shape.size + check(n >= 2) { "Expected tensor with 2 or more dimensions, got size $n" } + val matrixOffset = shape[n - 1] * shape[n - 2] + val matrixShape = ShapeND(shape[n - 2], shape[n - 1]) + + val size = matrixShape.linearSize + for (i in 0 until linearSize / matrixOffset) { + val offset = i * matrixOffset + val index = indices.index(offset).sliceArray(0 until (shape.size - 2)) + block(index, DoubleTensor(matrixShape, source.view(offset, size)).asDoubleTensor2D()) + } +} 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 e9dc34748..c8cf56888 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,30 +8,30 @@ package space.kscience.kmath.tensors.core -import space.kscience.kmath.misc.PerformancePitfall +import space.kscience.kmath.PerformancePitfall import space.kscience.kmath.nd.* +import space.kscience.kmath.operations.DoubleBufferOps import space.kscience.kmath.operations.DoubleField -import space.kscience.kmath.structures.MutableBuffer -import space.kscience.kmath.structures.indices +import space.kscience.kmath.structures.* import space.kscience.kmath.tensors.api.AnalyticTensorAlgebra import space.kscience.kmath.tensors.api.LinearOpsTensorAlgebra import space.kscience.kmath.tensors.api.Tensor -import space.kscience.kmath.tensors.api.TensorPartialDivisionAlgebra import space.kscience.kmath.tensors.core.internal.* import kotlin.math.* /** * Implementation of basic operations over double tensors and basic algebra operations on them. */ +@OptIn(PerformancePitfall::class) public open class DoubleTensorAlgebra : - TensorPartialDivisionAlgebra, AnalyticTensorAlgebra, LinearOpsTensorAlgebra { public companion object : DoubleTensorAlgebra() - override val elementAlgebra: DoubleField - get() = DoubleField + override val elementAlgebra: DoubleField get() = DoubleField + + public val bufferAlgebra: DoubleBufferOps get() = DoubleBufferOps /** @@ -40,73 +40,82 @@ public open class DoubleTensorAlgebra : * @param transform the function to be applied to each element of the tensor. * @return the resulting tensor after applying the function. */ - @PerformancePitfall @Suppress("OVERRIDE_BY_INLINE") final override inline fun StructureND.map(transform: DoubleField.(Double) -> Double): DoubleTensor { - val tensor = this.tensor + val tensor = asDoubleTensor() //TODO remove additional copy - val sourceArray = tensor.copyArray() - val array = DoubleArray(tensor.numElements) { DoubleField.transform(sourceArray[it]) } + val array = DoubleBuffer(tensor.source.size) { DoubleField.transform(tensor.source[it]) } return DoubleTensor( tensor.shape, array, - tensor.bufferStart ) } - @PerformancePitfall + public inline fun Tensor.mapInPlace(operation: (Double) -> Double) { + if (this is DoubleTensor) { + source.mapInPlace(operation) + } else { + indices.forEach { set(it, operation(get(it))) } + } + } + + public inline fun Tensor.mapIndexedInPlace(operation: DoubleField.(IntArray, Double) -> Double) { + indices.forEach { set(it, DoubleField.operation(it, get(it))) } + } + @Suppress("OVERRIDE_BY_INLINE") final override inline fun StructureND.mapIndexed(transform: DoubleField.(index: IntArray, Double) -> Double): DoubleTensor { - val tensor = this.tensor - //TODO remove additional copy - val sourceArray = tensor.copyArray() - val array = DoubleArray(tensor.numElements) { DoubleField.transform(tensor.indices.index(it), sourceArray[it]) } - return DoubleTensor( - tensor.shape, - array, - tensor.bufferStart - ) + return copyToTensor().apply { mapIndexedInPlace(transform) } } - @PerformancePitfall - override fun zip( + + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun zip( left: StructureND, right: StructureND, transform: DoubleField.(Double, Double) -> Double, ): DoubleTensor { - require(left.shape.contentEquals(right.shape)) { - "The shapes in zip are not equal: left - ${left.shape}, right - ${right.shape}" + checkShapesCompatible(left, right) + + val leftTensor = left.asDoubleTensor() + val rightTensor = right.asDoubleTensor() + val buffer = DoubleBuffer(leftTensor.source.size) { + DoubleField.transform(leftTensor.source[it], rightTensor.source[it]) } - val leftTensor = left.tensor - val leftArray = leftTensor.copyArray() - val rightTensor = right.tensor - val rightArray = rightTensor.copyArray() - val array = DoubleArray(leftTensor.numElements) { DoubleField.transform(leftArray[it], rightArray[it]) } - return DoubleTensor( - leftTensor.shape, - array - ) + return DoubleTensor(leftTensor.shape, buffer) } - override fun StructureND.valueOrNull(): Double? = if (tensor.shape contentEquals intArrayOf(1)) - tensor.mutableBuffer.array()[tensor.bufferStart] else null + + public inline fun StructureND.reduceElements(transform: (DoubleBuffer) -> Double): Double = + transform(asDoubleTensor().source.copy()) + //TODO Add read-only DoubleBuffer wrapper. To avoid protective copy + + override fun StructureND.valueOrNull(): Double? { + val dt = asDoubleTensor() + return if (dt.shape contentEquals ShapeND(1)) dt.source[0] else null + } override fun StructureND.value(): Double = valueOrNull() ?: throw IllegalArgumentException("The tensor shape is $shape, but value method is allowed only for shape [1]") + public fun fromBuffer(shape: ShapeND, buffer: Buffer): DoubleTensor { + checkNotEmptyShape(shape) + check(buffer.size > 0) { "Illegal empty buffer provided" } + check(buffer.size == shape.linearSize) { + "Inconsistent shape $shape for buffer of size ${buffer.size} provided" + } + return DoubleTensor(shape, buffer.toDoubleBuffer()) + } + + /** * Constructs a tensor with the specified shape and data. * * @param shape the desired shape for the tensor. - * @param buffer one-dimensional data array. - * @return tensor with the [shape] shape and [buffer] data. + * @param array one-dimensional data array. + * @return tensor with the [shape] shape and [array] data. */ - public fun fromArray(shape: IntArray, buffer: DoubleArray): DoubleTensor { - checkEmptyShape(shape) - checkEmptyDoubleBuffer(buffer) - checkBufferShapeConsistency(shape, buffer) - return DoubleTensor(shape, buffer, 0) - } + public fun fromArray(shape: ShapeND, array: DoubleArray): DoubleTensor = fromBuffer(shape, array.asBuffer()) /** * Constructs a tensor with the specified shape and initializer. @@ -115,16 +124,19 @@ public open class DoubleTensorAlgebra : * @param initializer mapping tensor indices to values. * @return tensor with the [shape] shape and data generated by the [initializer]. */ - override fun structureND(shape: IntArray, initializer: DoubleField.(IntArray) -> Double): DoubleTensor = fromArray( + override fun structureND(shape: ShapeND, initializer: DoubleField.(IntArray) -> Double): DoubleTensor = fromArray( shape, - TensorLinearStructure(shape).asSequence().map { DoubleField.initializer(it) }.toMutableList().toDoubleArray() + RowStrides(shape).asSequence().map { DoubleField.initializer(it) }.toMutableList().toDoubleArray() ) - override operator fun Tensor.get(i: Int): DoubleTensor { - val lastShape = tensor.shape.drop(1).toIntArray() - val newShape = if (lastShape.isNotEmpty()) lastShape else intArrayOf(1) - val newStart = newShape.reduce(Int::times) * i + tensor.bufferStart - return DoubleTensor(newShape, tensor.mutableBuffer.array(), newStart) + override fun Tensor.getTensor(i: Int): DoubleTensor { + val dt = asDoubleTensor() + val lastShape = shape.last(shape.size - 1) + val newShape: ShapeND = if (lastShape.isNotEmpty()) lastShape else ShapeND(1) + return DoubleTensor( + newShape, + dt.source.view(newShape.linearSize * i, newShape.linearSize) + ) } /** @@ -134,9 +146,9 @@ public open class DoubleTensorAlgebra : * @param shape array of integers defining the shape of the output tensor. * @return tensor with the [shape] shape and filled with [value]. */ - public fun full(value: Double, shape: IntArray): DoubleTensor { - checkEmptyShape(shape) - val buffer = DoubleArray(shape.reduce(Int::times)) { value } + public fun full(value: Double, shape: ShapeND): DoubleTensor { + checkNotEmptyShape(shape) + val buffer = DoubleBuffer(shape.linearSize) { value } return DoubleTensor(shape, buffer) } @@ -146,9 +158,9 @@ public open class DoubleTensorAlgebra : * @param value the value to fill the output tensor with. * @return tensor with the `input` tensor shape and filled with [value]. */ - public fun Tensor.fullLike(value: Double): DoubleTensor { - val shape = tensor.shape - val buffer = DoubleArray(tensor.numElements) { value } + public fun fullLike(structureND: StructureND<*>, value: Double): DoubleTensor { + val shape = structureND.shape + val buffer = DoubleBuffer(structureND.indices.linearSize) { value } return DoubleTensor(shape, buffer) } @@ -158,14 +170,14 @@ public open class DoubleTensorAlgebra : * @param shape array of integers defining the shape of the output tensor. * @return tensor filled with the scalar value `0.0`, with the [shape] shape. */ - public fun zeros(shape: IntArray): DoubleTensor = full(0.0, shape) + public fun zeros(shape: ShapeND): DoubleTensor = full(0.0, shape) /** * Returns a tensor filled with the scalar value `0.0`, with the same shape as a given array. * * @return tensor filled with the scalar value `0.0`, with the same shape as `input` tensor. */ - public fun StructureND.zeroesLike(): DoubleTensor = tensor.fullLike(0.0) + public fun zeroesLike(structureND: StructureND<*>): DoubleTensor = fullLike(structureND, 0.0) /** * Returns a tensor filled with the scalar value `1.0`, with the shape defined by the variable argument [shape]. @@ -173,14 +185,14 @@ public open class DoubleTensorAlgebra : * @param shape array of integers defining the shape of the output tensor. * @return tensor filled with the scalar value `1.0`, with the [shape] shape. */ - public fun ones(shape: IntArray): DoubleTensor = full(1.0, shape) + public fun ones(shape: ShapeND): DoubleTensor = full(1.0, shape) /** * Returns a tensor filled with the scalar value `1.0`, with the same shape as a given array. * * @return tensor filled with the scalar value `1.0`, with the same shape as `input` tensor. */ - public fun Tensor.onesLike(): DoubleTensor = tensor.fullLike(1.0) + public fun onesLike(structureND: StructureND<*>): DoubleTensor = fullLike(structureND, 1.0) /** * Returns a 2D tensor with shape ([n], [n]), with ones on the diagonal and zeros elsewhere. @@ -189,8 +201,8 @@ public open class DoubleTensorAlgebra : * @return a 2-D tensor with ones on the diagonal and zeros elsewhere. */ public fun eye(n: Int): DoubleTensor { - val shape = intArrayOf(n, n) - val buffer = DoubleArray(n * n) { 0.0 } + val shape = ShapeND(n, n) + val buffer = DoubleBuffer(n * n) { 0.0 } val res = DoubleTensor(shape, buffer) for (i in 0 until n) { res[intArrayOf(i, i)] = 1.0 @@ -198,209 +210,167 @@ public open class DoubleTensorAlgebra : return res } - /** - * Return a copy of the tensor. - * - * @return a copy of the `input` tensor with a copied buffer. - */ - public fun StructureND.copy(): DoubleTensor = - DoubleTensor(tensor.shape, tensor.mutableBuffer.array().copyOf(), tensor.bufferStart) - - override fun Double.plus(arg: StructureND): DoubleTensor { - val resBuffer = DoubleArray(arg.tensor.numElements) { i -> - arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] + this - } - return DoubleTensor(arg.shape, resBuffer) - } + override fun Double.plus(arg: StructureND): DoubleTensor = arg.map { this@plus + it } - override fun StructureND.plus(arg: Double): DoubleTensor = arg + tensor + override fun StructureND.plus(arg: Double): DoubleTensor = map { it + arg } - override fun StructureND.plus(arg: StructureND): DoubleTensor { - checkShapesCompatible(tensor, arg.tensor) - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[i] + arg.tensor.mutableBuffer.array()[i] - } - return DoubleTensor(tensor.shape, resBuffer) - } + override fun StructureND.plus(arg: StructureND): DoubleTensor = zip(this, arg) { l, r -> l + r } override fun Tensor.plusAssign(value: Double) { - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] += value - } + mapInPlace { it + value } } override fun Tensor.plusAssign(arg: StructureND) { - checkShapesCompatible(tensor, arg.tensor) - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] += - arg.tensor.mutableBuffer.array()[tensor.bufferStart + i] + checkShapesCompatible(asDoubleTensor(), arg.asDoubleTensor()) + mapIndexedInPlace { index, value -> + value + arg[index] } } - override fun Double.minus(arg: StructureND): DoubleTensor { - val resBuffer = DoubleArray(arg.tensor.numElements) { i -> - this - arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] - } - return DoubleTensor(arg.shape, resBuffer) - } + override fun Double.minus(arg: StructureND): DoubleTensor = arg.map { this@minus - it } - override fun StructureND.minus(arg: Double): DoubleTensor { - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[tensor.bufferStart + i] - arg - } - return DoubleTensor(tensor.shape, resBuffer) - } + override fun StructureND.minus(arg: Double): DoubleTensor = map { it - arg } - override fun StructureND.minus(arg: StructureND): DoubleTensor { - checkShapesCompatible(tensor, arg) - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[i] - arg.tensor.mutableBuffer.array()[i] - } - return DoubleTensor(tensor.shape, resBuffer) - } + override fun StructureND.minus(arg: StructureND): DoubleTensor = zip(this, arg) { l, r -> l - r } override fun Tensor.minusAssign(value: Double) { - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] -= value - } + mapInPlace { it - value } } override fun Tensor.minusAssign(arg: StructureND) { - checkShapesCompatible(tensor, arg) - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] -= - arg.tensor.mutableBuffer.array()[tensor.bufferStart + i] - } + checkShapesCompatible(this, arg) + mapIndexedInPlace { index, value -> value - arg.getDouble(index) } } - override fun Double.times(arg: StructureND): DoubleTensor { - val resBuffer = DoubleArray(arg.tensor.numElements) { i -> - arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] * this - } - return DoubleTensor(arg.shape, resBuffer) - } + override fun Double.times(arg: StructureND): DoubleTensor = arg.map { this@times * it } - override fun StructureND.times(arg: Double): DoubleTensor = arg * tensor + override fun StructureND.times(arg: Double): DoubleTensor = arg * asDoubleTensor() - override fun StructureND.times(arg: StructureND): DoubleTensor { - checkShapesCompatible(tensor, arg) - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[tensor.bufferStart + i] * - arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] - } - return DoubleTensor(tensor.shape, resBuffer) - } + override fun StructureND.times(arg: StructureND): DoubleTensor = zip(this, arg) { l, r -> l * r } override fun Tensor.timesAssign(value: Double) { - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] *= value - } + mapInPlace { it * value } } override fun Tensor.timesAssign(arg: StructureND) { - checkShapesCompatible(tensor, arg) - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] *= - arg.tensor.mutableBuffer.array()[tensor.bufferStart + i] - } + checkShapesCompatible(this, arg) + mapIndexedInPlace { index, value -> value * arg[index] } } - override fun Double.div(arg: StructureND): DoubleTensor { - val resBuffer = DoubleArray(arg.tensor.numElements) { i -> - this / arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] - } - return DoubleTensor(arg.shape, resBuffer) - } + override fun Double.div(arg: StructureND): DoubleTensor = arg.map { this@div / it } - override fun StructureND.div(arg: Double): DoubleTensor { - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[tensor.bufferStart + i] / arg - } - return DoubleTensor(shape, resBuffer) - } + override fun StructureND.div(arg: Double): DoubleTensor = map { it / arg } - override fun StructureND.div(arg: StructureND): DoubleTensor { - checkShapesCompatible(tensor, arg) - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] / - arg.tensor.mutableBuffer.array()[arg.tensor.bufferStart + i] - } - return DoubleTensor(tensor.shape, resBuffer) - } + override fun StructureND.div(arg: StructureND): DoubleTensor = zip(this, arg) { l, r -> l / r } override fun Tensor.divAssign(value: Double) { - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] /= value - } + mapInPlace { it / value } } override fun Tensor.divAssign(arg: StructureND) { - checkShapesCompatible(tensor, arg) - for (i in 0 until tensor.numElements) { - tensor.mutableBuffer.array()[tensor.bufferStart + i] /= - arg.tensor.mutableBuffer.array()[tensor.bufferStart + i] - } - } - - override fun StructureND.unaryMinus(): DoubleTensor { - val resBuffer = DoubleArray(tensor.numElements) { i -> - tensor.mutableBuffer.array()[tensor.bufferStart + i].unaryMinus() + checkShapesCompatible(asDoubleTensor(), arg) + mapIndexedInPlace { index, value -> value / arg[index] } + } + + override fun StructureND.unaryMinus(): DoubleTensor = map { -it } + + override fun StructureND.transposed(i: Int, j: Int): Tensor { + val actualI = if (i >= 0) i else shape.size + i + val actualJ = if (j >= 0) j else shape.size + j + return asDoubleTensor().permute( + shape.transposed(actualI, actualJ) + ) { originIndex -> + originIndex.copyOf().apply { + val ith = get(actualI) + val jth = get(actualJ) + set(actualI, jth) + set(actualJ, ith) + } } - return DoubleTensor(tensor.shape, resBuffer) - } - - override fun Tensor.transpose(i: Int, j: Int): DoubleTensor { - val ii = tensor.minusIndex(i) - val jj = tensor.minusIndex(j) - checkTranspose(tensor.dimension, ii, jj) - val n = tensor.numElements - val resBuffer = DoubleArray(n) - - val resShape = tensor.shape.copyOf() - resShape[ii] = resShape[jj].also { resShape[jj] = resShape[ii] } - - val resTensor = DoubleTensor(resShape, resBuffer) - - for (offset in 0 until n) { - val oldMultiIndex = tensor.indices.index(offset) - val newMultiIndex = oldMultiIndex.copyOf() - newMultiIndex[ii] = newMultiIndex[jj].also { newMultiIndex[jj] = newMultiIndex[ii] } - - val linearIndex = resTensor.indices.offset(newMultiIndex) - resTensor.mutableBuffer.array()[linearIndex] = - tensor.mutableBuffer.array()[tensor.bufferStart + offset] - } - return resTensor - } - - override fun Tensor.view(shape: IntArray): DoubleTensor { - checkView(tensor, shape) - return DoubleTensor(shape, tensor.mutableBuffer.array(), tensor.bufferStart) +// // TODO change strides instead of changing content +// val dt = asDoubleTensor() +// val ii = dt.minusIndex(i) +// val jj = dt.minusIndex(j) +// checkTranspose(dt.dimension, ii, jj) +// val n = dt.linearSize +// val resBuffer = DoubleArray(n) +// +// val resShape = dt.shape.copyOf() +// resShape[ii] = resShape[jj].also { resShape[jj] = resShape[ii] } +// +// val resTensor = DoubleTensor(resShape, resBuffer.asBuffer()) +// +// for (offset in 0 until n) { +// val oldMultiIndex = dt.indices.index(offset) +// val newMultiIndex = oldMultiIndex.copyOf() +// newMultiIndex[ii] = newMultiIndex[jj].also { newMultiIndex[jj] = newMultiIndex[ii] } +// +// val linearIndex = resTensor.indices.offset(newMultiIndex) +// resTensor.source[linearIndex] = dt.source[offset] +// } +// return resTensor + } + + override fun Tensor.view(shape: ShapeND): DoubleTensor { + checkView(asDoubleTensor(), shape) + return DoubleTensor(shape, asDoubleTensor().source) } override fun Tensor.viewAs(other: StructureND): DoubleTensor = - tensor.view(other.shape) + view(other.shape) - override infix fun StructureND.dot(other: StructureND): DoubleTensor { - if (tensor.shape.size == 1 && other.shape.size == 1) { - return DoubleTensor(intArrayOf(1), doubleArrayOf(tensor.times(other).tensor.mutableBuffer.array().sum())) + /** + * Broadcasting Matrix product of two tensors. + * + * The behavior depends on the dimensionality of the tensors as follows: + * 1. If both tensors are 1-dimensional, the dot product (scalar) is returned. + * + * 2. If both arguments are 2-dimensional, the matrix-matrix product is returned. + * + * 3. If the first argument is 1-dimensional and the second argument is 2-dimensional, + * a 1 is prepended to its dimension for the purpose of the matrix multiply. + * After the matrix multiply, depending on the implementation the prepended dimension might be removed. + * + * 4. If the first argument is 2-dimensional and the second argument is 1-dimensional, + * the matrix-vector product is returned. + * + * 5. If both arguments are at least 1-dimensional and at least one argument is N-dimensional (where N > 2), + * then a batched matrix multiply is returned. If the first argument is 1-dimensional, + * a 1 is prepended to its dimension for the purpose of the batched matrix multiply and removed after. + * If the second argument is 1-dimensional, a 1 is appended to its dimension for the purpose of the batched matrix + * multiple and removed after. + * The non-matrix (i.e., batch) dimensions are broadcast (and thus must be broadcastable). + * For example, if `input` is a (j × 1 × n × n) tensor and `other` is a + * (k × n × n) tensor, out will be a (j × k × n × n) tensor. + * + * For more information: https://pytorch.org/docs/stable/generated/torch.matmul.html + * + * @param other tensor to be multiplied. + * @return a mathematical product of two tensors. + */ + public infix fun StructureND.matmul(other: StructureND): DoubleTensor { + if (shape.size == 1 && other.shape.size == 1) { + return DoubleTensor(ShapeND(1), DoubleBuffer(times(other).sum())) } - var newThis = tensor.copy() - var newOther = other.copy() - var penultimateDim = false var lastDim = false - if (tensor.shape.size == 1) { + + //TODO do we need protective copy here? + var newThis: DoubleTensor = copyToTensor() + var newOther: DoubleTensor = other.copyToTensor() + + if (shape.size == 1) { penultimateDim = true - newThis = tensor.view(intArrayOf(1) + tensor.shape) + newThis = newThis.view(ShapeND(1) + shape) } + if (other.shape.size == 1) { lastDim = true - newOther = other.tensor.view(other.shape + intArrayOf(1)) + newOther = newOther.view(other.shape + intArrayOf(1)) } - val broadcastTensors = broadcastOuterTensors(newThis.tensor, newOther.tensor) + val broadcastTensors = broadcastOuterTensors(newThis, newOther) newThis = broadcastTensors[0] newOther = broadcastTensors[1] @@ -412,26 +382,39 @@ public open class DoubleTensorAlgebra : "Tensors dot operation dimension mismatch: ($l, $m1) x ($m2, $n)" } - val resShape = newThis.shape.sliceArray(0..(newThis.shape.size - 2)) + intArrayOf(newOther.shape.last()) - val resSize = resShape.reduce { acc, i -> acc * i } - val resTensor = DoubleTensor(resShape, DoubleArray(resSize)) + val resShape = newThis.shape.slice(0..(newThis.shape.size - 2)) + intArrayOf(newOther.shape.last()) + val resSize = resShape.linearSize + val resTensor = DoubleTensor(resShape, DoubleArray(resSize).asBuffer()) + + val resMatrices = resTensor.matrices + val newThisMatrices = newThis.matrices + val newOtherMatrices = newOther.matrices - for ((res, ab) in resTensor.matrixSequence().zip(newThis.matrixSequence().zip(newOther.matrixSequence()))) { - val (a, b) = ab - dotTo(a, b, res, l, m1, n) + for (i in resMatrices.indices) { + dotTo(newThisMatrices[i], newOtherMatrices[i], resMatrices[i], l, m1, n) } +// +// for ((res, ab) in resTensor.matrixSequence().zip(newThis.matrixSequence().zip(newOther.matrixSequence()))) { +// val (a, b) = ab +// dotTo(a, b, res, l, m1, n) +// } return if (penultimateDim) { - resTensor.view(resTensor.shape.dropLast(2).toIntArray() + intArrayOf(resTensor.shape.last())) + resTensor.view(resTensor.shape.first(resTensor.shape.size - 2) + ShapeND(resTensor.shape.last())) } else if (lastDim) { - resTensor.view(resTensor.shape.dropLast(1).toIntArray()) + resTensor.view(resTensor.shape.first(resTensor.shape.size - 1)) } else { resTensor } } + override fun StructureND.dot(other: StructureND): DoubleTensor { + return if (dimension in 0..2 && other.dimension in 0..2) this.matmul(other) + else error("Only vectors and matrices are allowed in non-broadcasting dot operation") + } + override fun diagonalEmbedding( - diagonalEntries: Tensor, + diagonalEntries: StructureND, offset: Int, dim1: Int, dim2: Int, @@ -455,15 +438,15 @@ public open class DoubleTensorAlgebra : lessDim = greaterDim.also { greaterDim = lessDim } } - val resShape = diagonalEntries.shape.slice(0 until lessDim).toIntArray() + + val resShape = diagonalEntries.shape.slice(0 until lessDim) + intArrayOf(diagonalEntries.shape[n - 1] + abs(realOffset)) + - diagonalEntries.shape.slice(lessDim until greaterDim - 1).toIntArray() + + diagonalEntries.shape.slice(lessDim until greaterDim - 1) + intArrayOf(diagonalEntries.shape[n - 1] + abs(realOffset)) + - diagonalEntries.shape.slice(greaterDim - 1 until n - 1).toIntArray() - val resTensor = zeros(resShape) + diagonalEntries.shape.slice(greaterDim - 1 until n - 1) + val resTensor: DoubleTensor = zeros(resShape) - for (i in 0 until diagonalEntries.tensor.numElements) { - val multiIndex = diagonalEntries.tensor.indices.index(i) + for (i in 0 until diagonalEntries.indices.linearSize) { + val multiIndex = diagonalEntries.indices.index(i) var offset1 = 0 var offset2 = abs(realOffset) @@ -479,7 +462,7 @@ public open class DoubleTensorAlgebra : resTensor[diagonalMultiIndex] = diagonalEntries[multiIndex] } - return resTensor.tensor + return resTensor } /** @@ -490,7 +473,7 @@ public open class DoubleTensorAlgebra : * @return true if two tensors have the same shape and elements, false otherwise. */ public fun Tensor.eq(other: Tensor, epsilon: Double): Boolean = - tensor.eq(other) { x, y -> abs(x - y) < epsilon } + asDoubleTensor().eq(other) { x, y -> abs(x - y) < epsilon } /** * Compares element-wise two tensors. @@ -499,646 +482,239 @@ public open class DoubleTensorAlgebra : * @param other the tensor to compare with `input` tensor. * @return true if two tensors have the same shape and elements, false otherwise. */ - public infix fun Tensor.eq(other: Tensor): Boolean = tensor.eq(other, 1e-5) + public infix fun Tensor.eq(other: Tensor): Boolean = eq(other, 1e-5) private fun Tensor.eq( other: Tensor, eqFunction: (Double, Double) -> Boolean, ): Boolean { - checkShapesCompatible(tensor, other) - val n = tensor.numElements - if (n != other.tensor.numElements) { + //TODO optimize tensor conversion + checkShapesCompatible(asDoubleTensor(), other) + val n = asDoubleTensor().linearSize + if (n != other.asDoubleTensor().linearSize) { return false } for (i in 0 until n) { - if (!eqFunction( - tensor.mutableBuffer[tensor.bufferStart + i], - other.tensor.mutableBuffer[other.tensor.bufferStart + i] - ) - ) { + if (!eqFunction(asDoubleTensor().source[i], other.asDoubleTensor().source[i])) { return false } } return true } - /** - * Returns a tensor of random numbers drawn from normal distributions with `0.0` mean and `1.0` standard deviation. - * - * @param shape the desired shape for the output tensor. - * @param seed the random seed of the pseudo-random number generator. - * @return tensor of a given shape filled with numbers from the normal distribution - * with `0.0` mean and `1.0` standard deviation. - */ - public fun randomNormal(shape: IntArray, seed: Long = 0): DoubleTensor = - DoubleTensor(shape, getRandomNormals(shape.reduce(Int::times), seed)) - - /** - * Returns a tensor with the same shape as `input` of random numbers drawn from normal distributions - * with `0.0` mean and `1.0` standard deviation. - * - * @receiver the `input`. - * @param seed the random seed of the pseudo-random number generator. - * @return a tensor with the same shape as `input` filled with numbers from the normal distribution - * with `0.0` mean and `1.0` standard deviation. - */ - public fun Tensor.randomNormalLike(seed: Long = 0): DoubleTensor = - DoubleTensor(tensor.shape, getRandomNormals(tensor.shape.reduce(Int::times), seed)) - - /** - * Concatenates a sequence of tensors with equal shapes along the first dimension. - * - * @param tensors the [List] of tensors with same shapes to concatenate - * @return tensor with concatenation result - */ - public fun stack(tensors: List>): DoubleTensor { - check(tensors.isNotEmpty()) { "List must have at least 1 element" } - val shape = tensors[0].shape - check(tensors.all { it.shape contentEquals shape }) { "Tensors must have same shapes" } - val resShape = intArrayOf(tensors.size) + shape - val resBuffer = tensors.flatMap { - it.tensor.mutableBuffer.array().drop(it.tensor.bufferStart).take(it.tensor.numElements) - }.toDoubleArray() - return DoubleTensor(resShape, resBuffer, 0) - } - /** * Builds tensor from rows of the input tensor. * * @param indices the [IntArray] of 1-dimensional indices * @return tensor with rows corresponding to row by [indices] */ - public fun Tensor.rowsByIndices(indices: IntArray): DoubleTensor = stack(indices.map { this[it] }) + public fun Tensor.rowsByIndices(indices: IntArray): DoubleTensor = stack(indices.map { getTensor(it) }) + - private inline fun StructureND.fold(foldFunction: (DoubleArray) -> Double): Double = - foldFunction(tensor.copyArray()) + private inline fun StructureND.foldDimToDouble( + dim: Int, + keepDim: Boolean, + foldFunction: (DoubleArray) -> Double, + ): DoubleTensor { + check(dim < dimension) { "Dimension $dim out of range $dimension" } + val resShape = if (keepDim) { + shape.first(dim) + intArrayOf(1) + shape.last(dimension - dim - 1) + } else { + shape.first(dim) + shape.last(dimension - dim - 1) + } + val resNumElements = resShape.linearSize + val init = foldFunction(DoubleArray(1) { 0.0 }) + val resTensor = DoubleTensor( + resShape, + DoubleBuffer(resNumElements) { init } + ) + val dt = asDoubleTensor() + for (index in resTensor.indices) { + val prefix = index.take(dim).toIntArray() + val suffix = index.takeLast(dimension - dim - 1).toIntArray() + resTensor[index] = foldFunction(DoubleArray(shape[dim]) { i -> + dt[prefix + intArrayOf(i) + suffix] + }) + } + return resTensor + } - private inline fun StructureND.foldDim( + private inline fun StructureND.foldDimToInt( dim: Int, keepDim: Boolean, - foldFunction: (DoubleArray) -> R, - ): BufferedTensor { + foldFunction: (DoubleArray) -> Int, + ): IntTensor { check(dim < dimension) { "Dimension $dim out of range $dimension" } val resShape = if (keepDim) { - shape.take(dim).toIntArray() + intArrayOf(1) + shape.takeLast(dimension - dim - 1).toIntArray() + shape.first(dim) + intArrayOf(1) + shape.last(dimension - dim - 1) } else { - shape.take(dim).toIntArray() + shape.takeLast(dimension - dim - 1).toIntArray() + shape.first(dim) + shape.last(dimension - dim - 1) } - val resNumElements = resShape.reduce(Int::times) + val resNumElements = resShape.linearSize val init = foldFunction(DoubleArray(1) { 0.0 }) - val resTensor = BufferedTensor(resShape, - MutableBuffer.auto(resNumElements) { init }, 0) + val resTensor = IntTensor( + resShape, + IntBuffer(resNumElements) { init } + ) for (index in resTensor.indices) { val prefix = index.take(dim).toIntArray() val suffix = index.takeLast(dimension - dim - 1).toIntArray() resTensor[index] = foldFunction(DoubleArray(shape[dim]) { i -> - tensor[prefix + intArrayOf(i) + suffix] + asDoubleTensor()[prefix + intArrayOf(i) + suffix] }) } return resTensor } - override fun StructureND.sum(): Double = tensor.fold { it.sum() } + + override fun StructureND.sum(): Double = reduceElements { it.array.sum() } override fun StructureND.sum(dim: Int, keepDim: Boolean): DoubleTensor = - foldDim(dim, keepDim) { x -> x.sum() }.toDoubleTensor() + foldDimToDouble(dim, keepDim) { x -> x.sum() } - override fun StructureND.min(): Double = this.fold { it.minOrNull()!! } + override fun StructureND.min(): Double = reduceElements { it.array.min() } override fun StructureND.min(dim: Int, keepDim: Boolean): DoubleTensor = - foldDim(dim, keepDim) { x -> x.minOrNull()!! }.toDoubleTensor() + foldDimToDouble(dim, keepDim) { x -> x.minOrNull()!! } + + override fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor = foldDimToInt(dim, keepDim) { x -> + x.withIndex().minBy { it.value }.index + } - override fun StructureND.max(): Double = this.fold { it.maxOrNull()!! } + override fun StructureND.max(): Double = reduceElements { it.array.max() } override fun StructureND.max(dim: Int, keepDim: Boolean): DoubleTensor = - foldDim(dim, keepDim) { x -> x.maxOrNull()!! }.toDoubleTensor() + foldDimToDouble(dim, keepDim) { x -> x.maxOrNull()!! } override fun StructureND.argMax(dim: Int, keepDim: Boolean): IntTensor = - foldDim(dim, keepDim) { x -> - x.withIndex().maxByOrNull { it.value }?.index!! - }.toIntTensor() - + foldDimToInt(dim, keepDim) { x -> + x.withIndex().maxBy { it.value }.index + } - override fun StructureND.mean(): Double = this.fold { it.sum() / tensor.numElements } - override fun StructureND.mean(dim: Int, keepDim: Boolean): DoubleTensor = foldDim(dim, keepDim) { arr -> - check(dim < dimension) { "Dimension $dim out of range $dimension" } - arr.sum() / shape[dim] - }.toDoubleTensor() + override fun mean(structureND: StructureND): Double = structureND.sum() / structureND.indices.linearSize - override fun StructureND.std(): Double = fold { arr -> - val mean = arr.sum() / tensor.numElements - sqrt(arr.sumOf { (it - mean) * (it - mean) } / (tensor.numElements - 1)) - } - - override fun StructureND.std(dim: Int, keepDim: Boolean): DoubleTensor = foldDim( - dim, - keepDim - ) { arr -> - check(dim < dimension) { "Dimension $dim out of range $dimension" } - val mean = arr.sum() / shape[dim] - sqrt(arr.sumOf { (it - mean) * (it - mean) } / (shape[dim] - 1)) - }.toDoubleTensor() + override fun mean(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + structureND.foldDimToDouble(dim, keepDim) { arr -> + check(dim < structureND.dimension) { "Dimension $dim out of range ${structureND.dimension}" } + arr.sum() / structureND.shape[dim] + } - override fun StructureND.variance(): Double = fold { arr -> - val mean = arr.sum() / tensor.numElements - arr.sumOf { (it - mean) * (it - mean) } / (tensor.numElements - 1) + override fun std(structureND: StructureND): Double = structureND.reduceElements { arr -> + val mean = arr.array.sum() / structureND.indices.linearSize + sqrt(arr.array.sumOf { (it - mean) * (it - mean) } / (structureND.indices.linearSize - 1)) } - override fun StructureND.variance(dim: Int, keepDim: Boolean): DoubleTensor = foldDim( - dim, - keepDim - ) { arr -> - check(dim < dimension) { "Dimension $dim out of range $dimension" } - val mean = arr.sum() / shape[dim] - arr.sumOf { (it - mean) * (it - mean) } / (shape[dim] - 1) - }.toDoubleTensor() + override fun std(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + structureND.foldDimToDouble( + dim, + keepDim + ) { arr -> + check(dim < structureND.dimension) { "Dimension $dim out of range ${structureND.dimension}" } + val mean = arr.sum() / structureND.shape[dim] + sqrt(arr.sumOf { (it - mean) * (it - mean) } / (structureND.shape[dim] - 1)) + } - private fun cov(x: DoubleTensor, y: DoubleTensor): Double { - val n = x.shape[0] - return ((x - x.mean()) * (y - y.mean())).mean() * n / (n - 1) + override fun variance(structureND: StructureND): Double = structureND.reduceElements { arr -> + val linearSize = structureND.indices.linearSize + val mean = arr.array.sum() / linearSize + arr.array.sumOf { (it - mean) * (it - mean) } / (linearSize - 1) } - /** - * Returns the covariance matrix `M` of given vectors. - * - * `M[i, j]` contains covariance of `i`-th and `j`-th given vectors - * - * @param tensors the [List] of 1-dimensional tensors with same shape - * @return `M`. - */ - public fun cov(tensors: List>): DoubleTensor { - check(tensors.isNotEmpty()) { "List must have at least 1 element" } - val n = tensors.size - val m = tensors[0].shape[0] - check(tensors.all { it.shape contentEquals intArrayOf(m) }) { "Tensors must have same shapes" } - val resTensor = DoubleTensor( - intArrayOf(n, n), - DoubleArray(n * n) { 0.0 } - ) - for (i in 0 until n) { - for (j in 0 until n) { - resTensor[intArrayOf(i, j)] = cov(tensors[i].tensor, tensors[j].tensor) - } + override fun variance(structureND: StructureND, dim: Int, keepDim: Boolean): Tensor = + structureND.foldDimToDouble( + dim, + keepDim + ) { arr -> + check(dim < structureND.dimension) { "Dimension $dim out of range ${structureND.dimension}" } + val mean = arr.sum() / structureND.shape[dim] + arr.sumOf { (it - mean) * (it - mean) } / (structureND.shape[dim] - 1) } - return resTensor - } - override fun StructureND.exp(): DoubleTensor = tensor.map { exp(it) } - override fun StructureND.ln(): DoubleTensor = tensor.map { ln(it) } + override fun exp(arg: StructureND): DoubleTensor = arg.map { this.exp(it) } - override fun StructureND.sqrt(): DoubleTensor = tensor.map { sqrt(it) } + override fun ln(arg: StructureND): DoubleTensor = arg.map { this.ln(it) } - override fun StructureND.cos(): DoubleTensor = tensor.map { cos(it) } + override fun sqrt(arg: StructureND): DoubleTensor = arg.map { this.sqrt(it) } - override fun StructureND.acos(): DoubleTensor = tensor.map { acos(it) } + override fun cos(arg: StructureND): DoubleTensor = arg.map { this.cos(it) } - override fun StructureND.cosh(): DoubleTensor = tensor.map { cosh(it) } + override fun acos(arg: StructureND): DoubleTensor = arg.map { this.acos(it) } - override fun StructureND.acosh(): DoubleTensor = tensor.map { acosh(it) } + override fun cosh(arg: StructureND): DoubleTensor = arg.map { this.cosh(it) } - override fun StructureND.sin(): DoubleTensor = tensor.map { sin(it) } + override fun acosh(arg: StructureND): DoubleTensor = arg.map { this.acosh(it) } - override fun StructureND.asin(): DoubleTensor = tensor.map { asin(it) } + override fun sin(arg: StructureND): DoubleTensor = arg.map { this.sin(it) } - override fun StructureND.sinh(): DoubleTensor = tensor.map { sinh(it) } + override fun asin(arg: StructureND): DoubleTensor = arg.map { this.asin(it) } - override fun StructureND.asinh(): DoubleTensor = tensor.map { asinh(it) } + override fun sinh(arg: StructureND): DoubleTensor = arg.map { this.sinh(it) } - override fun StructureND.tan(): DoubleTensor = tensor.map { tan(it) } + override fun asinh(arg: StructureND): DoubleTensor = arg.map { this.asinh(it) } - override fun StructureND.atan(): DoubleTensor = tensor.map { atan(it) } + override fun tan(arg: StructureND): DoubleTensor = arg.map { this.tan(it) } - override fun StructureND.tanh(): DoubleTensor = tensor.map { tanh(it) } + override fun atan(arg: StructureND): DoubleTensor = arg.map { this.atan(it) } - override fun StructureND.atanh(): DoubleTensor = tensor.map { atanh(it) } + override fun tanh(arg: StructureND): DoubleTensor = arg.map { this.tanh(it) } - override fun StructureND.ceil(): DoubleTensor = tensor.map { ceil(it) } - - override fun StructureND.floor(): DoubleTensor = tensor.map { floor(it) } - - override fun StructureND.inv(): DoubleTensor = invLU(1e-9) - - override fun StructureND.det(): DoubleTensor = detLU(1e-9) - - /** - * Computes the LU factorization of a matrix or batches of matrices `input`. - * Returns a tuple containing the LU factorization and pivots of `input`. - * - * @param epsilon permissible error when comparing the determinant of a matrix with zero - * @return pair of `factorization` and `pivots`. - * The `factorization` has the shape ``(*, m, n)``, where``(*, m, n)`` is the shape of the `input` tensor. - * The `pivots` has the shape ``(∗, min(m, n))``. `pivots` stores all the intermediate transpositions of rows. - */ - public fun StructureND.luFactor(epsilon: Double): Pair = - computeLU(tensor, epsilon) - ?: throw IllegalArgumentException("Tensor contains matrices which are singular at precision $epsilon") + override fun atanh(arg: StructureND): DoubleTensor = arg.map { this.atanh(it) } - /** - * Computes the LU factorization of a matrix or batches of matrices `input`. - * Returns a tuple containing the LU factorization and pivots of `input`. - * Uses an error of ``1e-9`` when calculating whether a matrix is degenerate. - * - * @return pair of `factorization` and `pivots`. - * The `factorization` has the shape ``(*, m, n)``, where``(*, m, n)`` is the shape of the `input` tensor. - * The `pivots` has the shape ``(∗, min(m, n))``. `pivots` stores all the intermediate transpositions of rows. - */ - public fun StructureND.luFactor(): Pair = luFactor(1e-9) + override fun power(arg: StructureND, pow: Number): StructureND = if (pow is Int) { + arg.map { it.pow(pow) } + } else { + arg.map { it.pow(pow.toDouble()) } + } - /** - * Unpacks the data and pivots from a LU factorization of a tensor. - * Given a tensor [luTensor], return tensors `Triple(P, L, U)` satisfying `P dot luTensor = L dot U`, - * with `P` being a permutation matrix or batch of matrices, - * `L` being a lower triangular matrix or batch of matrices, - * `U` being an upper triangular matrix or batch of matrices. - * - * @param luTensor the packed LU factorization data - * @param pivotsTensor the packed LU factorization pivots - * @return triple of `P`, `L` and `U` tensors - */ - public fun luPivot( - luTensor: StructureND, - pivotsTensor: Tensor, - ): Triple { - checkSquareMatrix(luTensor.shape) - check( - luTensor.shape.dropLast(2).toIntArray() contentEquals pivotsTensor.shape.dropLast(1).toIntArray() || - luTensor.shape.last() == pivotsTensor.shape.last() - 1 - ) { "Inappropriate shapes of input tensors" } - - val n = luTensor.shape.last() - val pTensor = luTensor.zeroesLike() - pTensor - .matrixSequence() - .zip(pivotsTensor.tensor.vectorSequence()) - .forEach { (p, pivot) -> pivInit(p.as2D(), pivot.as1D(), n) } - - val lTensor = luTensor.zeroesLike() - val uTensor = luTensor.zeroesLike() - - lTensor.matrixSequence() - .zip(uTensor.matrixSequence()) - .zip(luTensor.tensor.matrixSequence()) - .forEach { (pairLU, lu) -> - val (l, u) = pairLU - luPivotHelper(l.as2D(), u.as2D(), lu.as2D(), n) - } + override fun ceil(arg: StructureND): DoubleTensor = arg.map { ceil(it) } - return Triple(pTensor, lTensor, uTensor) - } + override fun floor(structureND: StructureND): DoubleTensor = structureND.map { floor(it) } - /** - * QR decomposition. - * - * Computes the QR decomposition of a matrix or a batch of matrices, and returns a pair `Q to R` of tensors. - * Given a tensor `input`, return tensors `Q to R` satisfying `input == Q dot R`, - * with `Q` being an orthogonal matrix or batch of orthogonal matrices - * and `R` being an upper triangular matrix or batch of upper triangular matrices. - * - * @receiver the `input`. - * @param epsilon the permissible error when comparing tensors for equality. - * Used when checking the positive definiteness of the input matrix or matrices. - * @return a pair of `Q` and `R` tensors. - */ - public fun StructureND.cholesky(epsilon: Double): DoubleTensor { - checkSquareMatrix(shape) - checkPositiveDefinite(tensor, epsilon) + override fun StructureND.inv(): DoubleTensor = invLU(this, 1e-9) - val n = shape.last() - val lTensor = zeroesLike() + override fun StructureND.det(): DoubleTensor = detLU(this, 1e-9) - for ((a, l) in tensor.matrixSequence().zip(lTensor.matrixSequence())) - for (i in 0 until n) choleskyHelper(a.as2D(), l.as2D(), n) + override fun lu(structureND: StructureND): Triple = + lu(structureND, 1e-9) - return lTensor - } + override fun cholesky(structureND: StructureND): DoubleTensor = cholesky(structureND, 1e-6) - override fun StructureND.cholesky(): DoubleTensor = cholesky(1e-6) + override fun qr(structureND: StructureND): Pair { + checkSquareMatrix(structureND.shape) + val qTensor = zeroesLike(structureND) + val rTensor = zeroesLike(structureND) - override fun StructureND.qr(): Pair { - checkSquareMatrix(shape) - val qTensor = zeroesLike() - val rTensor = zeroesLike() - tensor.matrixSequence() + //TODO replace with cycle + structureND.asDoubleTensor().matrixSequence() .zip( (qTensor.matrixSequence() .zip(rTensor.matrixSequence())) ).forEach { (matrix, qr) -> val (q, r) = qr - qrHelper(matrix.asTensor(), q.asTensor(), r.as2D()) + qrHelper(matrix, q, r.asDoubleTensor2D()) } return qTensor to rTensor } - override fun StructureND.svd(): Triple = - svd(epsilon = 1e-10) - - /** - * Singular Value Decomposition. - * - * Computes the singular value decomposition of either a matrix or batch of matrices `input`. - * The singular value decomposition is represented as a triple `Triple(U, S, V)`, - * such that `input == U dot diagonalEmbedding(S) dot V.transpose()`. - * If `input` is a batch of tensors, then U, S, and Vh are also batched with the same batch dimensions as `input. - * - * @receiver the `input`. - * @param epsilon permissible error when calculating the dot product of vectors - * i.e., the precision with which the cosine approaches 1 in an iterative algorithm. - * @return a triple `Triple(U, S, V)`. - */ - public fun StructureND.svd(epsilon: Double): Triple { - val size = tensor.dimension - val commonShape = tensor.shape.sliceArray(0 until size - 2) - val (n, m) = tensor.shape.sliceArray(size - 2 until size) - val uTensor = zeros(commonShape + intArrayOf(min(n, m), n)) - val sTensor = zeros(commonShape + intArrayOf(min(n, m))) - val vTensor = zeros(commonShape + intArrayOf(min(n, m), m)) - - val matrices = tensor.matrices - val uTensors = uTensor.matrices - val sTensorVectors = sTensor.vectors - val vTensors = vTensor.matrices - - for (index in matrices.indices) { - val matrix = matrices[index] - val usv = Triple( - uTensors[index], - sTensorVectors[index], - vTensors[index] - ) - val matrixSize = matrix.shape.reduce { acc, i -> acc * i } - val curMatrix = DoubleTensor( - matrix.shape, - matrix.mutableBuffer.array() - .slice(matrix.bufferStart until matrix.bufferStart + matrixSize) - .toDoubleArray() - ) - svdHelper(curMatrix, usv, m, n, epsilon) - } - - return Triple(uTensor.transpose(), sTensor, vTensor.transpose()) - } - - 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, - * represented by a pair `eigenvalues to eigenvectors`. - * - * @param epsilon the permissible error when comparing tensors for equality - * and when the cosine approaches 1 in the SVD algorithm. - * @return a pair `eigenvalues to eigenvectors`. - */ - public fun StructureND.symEigSvd(epsilon: Double): Pair { - checkSymmetric(tensor, epsilon) - - fun MutableStructure2D.cleanSym(n: Int) { - for (i in 0 until n) { - for (j in 0 until n) { - if (i == j) { - this[i, j] = sign(this[i, j]) - } else { - this[i, j] = 0.0 - } - } - } - } - - val (u, s, v) = tensor.svd(epsilon) - val shp = s.shape + intArrayOf(1) - val utv = u.transpose() dot v - val n = s.shape.last() - for (matrix in utv.matrixSequence()) { - matrix.as2D().cleanSym(n) - } - - val eig = (utv dot s.view(shp)).view(s.shape) - return eig to v - } - - public fun StructureND.symEigJacobi(maxIteration: Int, epsilon: Double): Pair { - checkSymmetric(tensor, epsilon) - - val size = this.dimension - 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()) { - 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() - } - - return eigenvalues to eigenvectors - } - - private fun MutableStructure2D.jacobiHelper( - maxIteration: Int, - epsilon: Double - ): Pair, Structure2D> { - 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() - - // 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 n - 1) { - for (j in i + 1 until n) { - maxOffDiagonalElement = max(maxOffDiagonalElement, abs(matrix[i, j])) - } - } - return maxOffDiagonalElement - } - - 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) - a[k, l] = h + s * (g - h * tau) - } - - fun jacobiIteration( - a: BufferedTensor, - v: BufferedTensor, - d: MutableStructure1D, - z: MutableStructure1D, - ) { - 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])) { - 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 n) { - rotate(a, s, tau, ip, j, iq, j) - } - for (j in 0 until n) { - rotate(v, s, tau, j, ip, j, iq) - } - } - } - } - - 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 - } - } - - 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_) - } - - // TODO sort eigenvalues - return D to V.as2D() - } - - /** - * Computes the determinant of a square matrix input, or of each square matrix in a batched input - * using LU factorization algorithm. - * - * @param epsilon the error in the LU algorithm—permissible error when comparing the determinant of a matrix - * with zero. - * @return the determinant. - */ - public fun StructureND.detLU(epsilon: Double = 1e-9): DoubleTensor { - checkSquareMatrix(tensor.shape) - val luTensor = tensor.copy() - val pivotsTensor = tensor.setUpPivots() - - val n = shape.size - - val detTensorShape = IntArray(n - 1) { i -> shape[i] } - detTensorShape[n - 2] = 1 - val resBuffer = DoubleArray(detTensorShape.reduce(Int::times)) { 0.0 } - - val detTensor = DoubleTensor( - detTensorShape, - resBuffer - ) - - luTensor.matrixSequence().zip(pivotsTensor.vectorSequence()).forEachIndexed { index, (lu, pivots) -> - resBuffer[index] = if (luHelper(lu.as2D(), pivots.as1D(), epsilon)) - 0.0 else luMatrixDet(lu.as2D(), pivots.as1D()) - } - - return detTensor - } - - /** - * Computes the multiplicative inverse matrix of a square matrix input, or of each square matrix in a batched input - * using LU factorization algorithm. - * Given a square matrix `a`, return the matrix `aInv` satisfying - * `a dot aInv == aInv dot a == eye(a.shape[0])`. - * - * @param epsilon error in the LU algorithm—permissible error when comparing the determinant of a matrix with zero - * @return the multiplicative inverse of a matrix. - */ - public fun StructureND.invLU(epsilon: Double = 1e-9): DoubleTensor { - val (luTensor, pivotsTensor) = luFactor(epsilon) - val invTensor = luTensor.zeroesLike() - - val seq = luTensor.matrixSequence().zip(pivotsTensor.vectorSequence()).zip(invTensor.matrixSequence()) - for ((luP, invMatrix) in seq) { - val (lu, pivots) = luP - luMatrixInv(lu.as2D(), pivots.as1D(), invMatrix.as2D()) - } + override fun svd( + structureND: StructureND, + ): Triple, StructureND, StructureND> = + svdGolubKahan(structureND = structureND, epsilon = 1e-10) - return invTensor - } + override fun symEig(structureND: StructureND): Pair = + symEigJacobi(structureND = structureND, maxIteration = 50, epsilon = 1e-15) - /** - * LUP decomposition. - * - * Computes the LUP decomposition of a matrix or a batch of matrices. - * Given a tensor `input`, return tensors `Triple(P, L, U)` satisfying `P dot input == L dot U`, - * with `P` being a permutation matrix or batch of matrices, - * `L` being a lower triangular matrix or batch of matrices, - * `U` being an upper triangular matrix or batch of matrices. - * - * @param epsilon permissible error when comparing the determinant of a matrix with zero. - * @return triple of `P`, `L` and `U` tensors. - */ - public fun StructureND.lu(epsilon: Double = 1e-9): Triple { - val (lu, pivots) = tensor.luFactor(epsilon) - return luPivot(lu, pivots) + override fun solve(a: MutableStructure2D, b: MutableStructure2D): MutableStructure2D { + val aSvd = DoubleTensorAlgebra.svd(a) + val s = BroadcastDoubleTensorAlgebra.diagonalEmbedding(aSvd.second.map {1.0 / it}) + val aInverse = aSvd.third.dot(s).dot(aSvd.first.transposed()) + return aInverse.dot(b).as2D() } - - override fun StructureND.lu(): Triple = lu(1e-9) } -public val Double.Companion.tensorAlgebra: DoubleTensorAlgebra.Companion get() = DoubleTensorAlgebra -public val DoubleField.tensorAlgebra: DoubleTensorAlgebra.Companion get() = DoubleTensorAlgebra - - +public val Double.Companion.tensorAlgebra: DoubleTensorAlgebra get() = DoubleTensorAlgebra +public val DoubleField.tensorAlgebra: DoubleTensorAlgebra get() = DoubleTensorAlgebra \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensor.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensor.kt index e3d7c3d35..f028e2cbb 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensor.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensor.kt @@ -1,21 +1,95 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core -import space.kscience.kmath.structures.IntBuffer -import space.kscience.kmath.tensors.core.internal.array +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.structures.* /** * Default [BufferedTensor] implementation for [Int] values */ -public class IntTensor internal constructor( - shape: IntArray, - buffer: IntArray, - offset: Int = 0 -) : BufferedTensor(shape, IntBuffer(buffer), offset){ - public fun asDouble() : DoubleTensor = - DoubleTensor(shape, mutableBuffer.array().map{ it.toDouble()}.toDoubleArray(), bufferStart) +public class OffsetIntBuffer( + private val source: IntBuffer, + private val offset: Int, + override val size: Int, +) : MutableBuffer { + + init { + require(offset >= 0) { "Offset must be non-negative" } + require(size >= 0) { "Size must be non-negative" } + require(offset + size <= source.size) { "Maximum index must be inside source dimension" } + } + + override fun set(index: Int, value: Int) { + require(index in 0 until size) { "Index must be in [0, size)" } + source[index + offset] = value + } + + override fun get(index: Int): Int = source[index + offset] + + /** + * Copy only a part of buffer that belongs to this tensor + */ + override fun copy(): IntBuffer = source.array.copyOfRange(offset, offset + size).asBuffer() + + override fun iterator(): Iterator = iterator { + for (i in indices) { + yield(get(i)) + } + } + + override fun toString(): String = Buffer.toString(this) + + public fun view(addOffset: Int, newSize: Int = size - addOffset): OffsetIntBuffer = + OffsetIntBuffer(source, offset + addOffset, newSize) +} + +public fun OffsetIntBuffer.slice(range: IntRange): OffsetIntBuffer = view(range.first, range.last - range.first) + +/** + * Map only operable content of the offset buffer + */ +public inline fun OffsetIntBuffer.map(operation: (Int) -> Int): IntBuffer = + IntBuffer(size) { operation(get(it)) } + +public inline fun OffsetIntBuffer.zip( + other: OffsetIntBuffer, + operation: (l: Int, r: Int) -> Int, +): IntBuffer { + require(size == other.size) { "The sizes of zipped buffers must be the same" } + return IntBuffer(size) { operation(get(it), other[it]) } +} + +/** + * map in place + */ +public inline fun OffsetIntBuffer.mapInPlace(operation: (Int) -> Int) { + indices.forEach { set(it, operation(get(it))) } +} + +/** + * Default [BufferedTensor] implementation for [Int] values + */ +public class IntTensor( + shape: ShapeND, + override val source: OffsetIntBuffer, +) : BufferedTensor(shape) { + + init { + require(linearSize == source.size) { "Source buffer size must be equal tensor size" } + } + + public constructor(shape: ShapeND, buffer: IntBuffer) : this(shape, OffsetIntBuffer(buffer, 0, buffer.size)) + + @OptIn(PerformancePitfall::class) + override fun get(index: IntArray): Int = this.source[indices.offset(index)] + + @OptIn(PerformancePitfall::class) + override fun set(index: IntArray, value: Int) { + source[indices.offset(index)] = value + } } diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensorAlgebra.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensorAlgebra.kt new file mode 100644 index 000000000..d1cdc68d4 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/IntTensorAlgebra.kt @@ -0,0 +1,467 @@ +/* + * Copyright 2018-2022 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(PerformancePitfall::class) + +package space.kscience.kmath.tensors.core + +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.* +import space.kscience.kmath.operations.IntRing +import space.kscience.kmath.structures.* +import space.kscience.kmath.tensors.api.* +import space.kscience.kmath.tensors.core.internal.* +import kotlin.math.* + +/** + * Implementation of basic operations over double tensors and basic algebra operations on them. + */ +public open class IntTensorAlgebra : TensorAlgebra { + + public companion object : IntTensorAlgebra() + + + override val elementAlgebra: IntRing get() = IntRing + + + /** + * Applies the [transform] function to each element of the tensor and returns the resulting modified tensor. + * + * @param transform the function to be applied to each element of the tensor. + * @return the resulting tensor after applying the function. + */ + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun StructureND.map(transform: IntRing.(Int) -> Int): IntTensor { + val tensor = this.asIntTensor() + //TODO remove additional copy + val array = IntBuffer(tensor.source.size) { IntRing.transform(tensor.source[it]) } + return IntTensor( + tensor.shape, + array, + ) + } + + public inline fun Tensor.mapInPlace(operation: (Int) -> Int) { + if (this is IntTensor) { + source.mapInPlace(operation) + } else { + indices.forEach { set(it, operation(get(it))) } + } + } + + public inline fun Tensor.mapIndexedInPlace(operation: (IntArray, Int) -> Int) { + indices.forEach { set(it, operation(it, get(it))) } + } + + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun StructureND.mapIndexed(transform: IntRing.(index: IntArray, Int) -> Int): IntTensor { + val tensor = this.asIntTensor() + //TODO remove additional copy + val buffer = IntBuffer(tensor.source.size) { + IntRing.transform(tensor.indices.index(it), tensor.source[it]) + } + return IntTensor(tensor.shape, buffer) + } + + @Suppress("OVERRIDE_BY_INLINE") + final override inline fun zip( + left: StructureND, + right: StructureND, + transform: IntRing.(Int, Int) -> Int, + ): IntTensor { + checkShapesCompatible(left, right) + + val leftTensor = left.asIntTensor() + val rightTensor = right.asIntTensor() + val buffer = IntBuffer(leftTensor.source.size) { + IntRing.transform(leftTensor.source[it], rightTensor.source[it]) + } + return IntTensor(leftTensor.shape, buffer) + } + + + public inline fun StructureND.reduceElements(transform: (IntBuffer) -> Int): Int = + transform(asIntTensor().source.copy()) + //TODO do we need protective copy? + + override fun StructureND.valueOrNull(): Int? { + val dt = asIntTensor() + return if (dt.shape contentEquals ShapeND(1)) dt.source[0] else null + } + + override fun StructureND.value(): Int = valueOrNull() + ?: throw IllegalArgumentException("The tensor shape is $shape, but value method is allowed only for shape [1]") + + /** + * Constructs a tensor with the specified shape and data. + * + * @param shape the desired shape for the tensor. + * @param array one-dimensional data array. + * @return tensor with the [shape] shape and [array] data. + */ + public fun fromArray(shape: ShapeND, array: IntArray): IntTensor { + checkNotEmptyShape(shape) + check(array.isNotEmpty()) { "Illegal empty buffer provided" } + check(array.size == shape.linearSize) { + "Inconsistent shape ${shape} for buffer of size ${array.size} provided" + } + return IntTensor(shape, array.asBuffer()) + } + + /** + * Constructs a tensor with the specified shape and initializer. + * + * @param shape the desired shape for the tensor. + * @param initializer mapping tensor indices to values. + * @return tensor with the [shape] shape and data generated by the [initializer]. + */ + override fun structureND(shape: ShapeND, initializer: IntRing.(IntArray) -> Int): IntTensor = fromArray( + shape, + RowStrides(shape).asSequence().map { IntRing.initializer(it) }.toMutableList().toIntArray() + ) + + override fun Tensor.getTensor(i: Int): IntTensor { + val dt = asIntTensor() + val lastShape = shape.last(shape.size - 1) + val newShape = if (lastShape.isNotEmpty()) lastShape else ShapeND(1) + return IntTensor(newShape, dt.source.view(newShape.linearSize * i)) + } + + /** + * Creates a tensor of a given shape and fills all elements with a given value. + * + * @param value the value to fill the output tensor with. + * @param shape array of integers defining the shape of the output tensor. + * @return tensor with the [shape] shape and filled with [value]. + */ + public fun full(value: Int, shape: ShapeND): IntTensor { + checkNotEmptyShape(shape) + val buffer = IntBuffer(shape.linearSize) { value } + return IntTensor(shape, buffer) + } + + /** + * Returns a tensor with the same shape as `input` filled with [value]. + * + * @param value the value to fill the output tensor with. + * @return tensor with the `input` tensor shape and filled with [value]. + */ + public fun fullLike(structureND: StructureND<*>, value: Int): IntTensor { + val shape = structureND.shape + val buffer = IntBuffer(structureND.indices.linearSize) { value } + return IntTensor(shape, buffer) + } + + /** + * Returns a tensor filled with the scalar value `0`, with the shape defined by the variable argument [shape]. + * + * @param shape array of integers defining the shape of the output tensor. + * @return tensor filled with the scalar value `0`, with the [shape] shape. + */ + public fun zeros(shape: ShapeND): IntTensor = full(0, shape) + + /** + * Returns a tensor filled with the scalar value `0`, with the same shape as a given array. + * + * @return tensor filled with the scalar value `0`, with the same shape as `input` tensor. + */ + public fun zeroesLike(structureND: StructureND): IntTensor = fullLike(structureND.asIntTensor(), 0) + + /** + * Returns a tensor filled with the scalar value `1`, with the shape defined by the variable argument [shape]. + * + * @param shape array of integers defining the shape of the output tensor. + * @return tensor filled with the scalar value `1`, with the [shape] shape. + */ + public fun ones(shape: ShapeND): IntTensor = full(1, shape) + + /** + * Returns a tensor filled with the scalar value `1`, with the same shape as a given array. + * + * @return tensor filled with the scalar value `1`, with the same shape as `input` tensor. + */ + public fun onesLike(structureND: Tensor<*>): IntTensor = fullLike(structureND, 1) + + /** + * Returns a 2D tensor with shape ([n], [n]), with ones on the diagonal and zeros elsewhere. + * + * @param n the number of rows and columns + * @return a 2-D tensor with ones on the diagonal and zeros elsewhere. + */ + public fun eye(n: Int): IntTensor { + val shape = ShapeND(n, n) + val buffer = IntBuffer(n * n) { 0 } + val res = IntTensor(shape, buffer) + for (i in 0 until n) { + res[intArrayOf(i, i)] = 1 + } + return res + } + + override fun Int.plus(arg: StructureND): IntTensor = arg.map { this@plus + it } + + override fun StructureND.plus(arg: Int): IntTensor = map { it + arg } + + override fun StructureND.plus(arg: StructureND): IntTensor = zip(this, arg) { l, r -> l + r } + + override fun Tensor.plusAssign(value: Int) { + mapInPlace { it + value } + } + + override fun Tensor.plusAssign(arg: StructureND) { + checkShapesCompatible(asIntTensor(), arg.asIntTensor()) + mapIndexedInPlace { index, value -> + value + arg[index] + } + } + + override fun Int.minus(arg: StructureND): IntTensor = arg.map { this@minus - it } + + override fun StructureND.minus(arg: Int): IntTensor = map { it - arg } + + override fun StructureND.minus(arg: StructureND): IntTensor = zip(this, arg) { l, r -> l - r } + + override fun Tensor.minusAssign(value: Int) { + mapInPlace { it - value } + } + + override fun Tensor.minusAssign(arg: StructureND) { + checkShapesCompatible(this, arg) + mapIndexedInPlace { index, value -> value - arg[index] } + } + + override fun Int.times(arg: StructureND): IntTensor = arg.map { this@times * it } + + override fun StructureND.times(arg: Int): IntTensor = arg * asIntTensor() + + override fun StructureND.times(arg: StructureND): IntTensor = zip(this, arg) { l, r -> l * r } + + override fun Tensor.timesAssign(value: Int) { + mapInPlace { it * value } + } + + override fun Tensor.timesAssign(arg: StructureND) { + checkShapesCompatible(this, arg) + mapIndexedInPlace { index, value -> value * arg[index] } + } + + override fun StructureND.unaryMinus(): IntTensor = map { -it } + + override fun StructureND.transposed(i: Int, j: Int): Tensor { + val actualI = if (i >= 0) i else shape.size + i + val actualJ = if(j>=0) j else shape.size + j + return asIntTensor().permute( + shape.transposed(actualI, actualJ) + ) { originIndex -> + originIndex.copyOf().apply { + val ith = get(actualI) + val jth = get(actualJ) + set(actualI, jth) + set(actualJ, ith) + } + } +// // TODO change strides instead of changing content +// val dt = asIntTensor() +// val ii = dt.minusIndex(i) +// val jj = dt.minusIndex(j) +// checkTranspose(dt.dimension, ii, jj) +// val n = dt.linearSize +// val resBuffer = IntArray(n) +// +// val resShape = dt.shape.toArray() +// resShape[ii] = resShape[jj].also { resShape[jj] = resShape[ii] } +// +// val resTensor = IntTensor(Shape(resShape), resBuffer.asBuffer()) +// +// for (offset in 0 until n) { +// val oldMultiIndex = dt.indices.index(offset) +// val newMultiIndex = oldMultiIndex.copyOf() +// newMultiIndex[ii] = newMultiIndex[jj].also { newMultiIndex[jj] = newMultiIndex[ii] } +// +// val linearIndex = resTensor.indices.offset(newMultiIndex) +// resTensor.source[linearIndex] = dt.source[offset] +// } +// return resTensor + } + + override fun Tensor.view(shape: ShapeND): IntTensor { + checkView(asIntTensor(), shape) + return IntTensor(shape, asIntTensor().source) + } + + override fun Tensor.viewAs(other: StructureND): IntTensor = + view(other.shape) + + override fun StructureND.dot(other: StructureND): IntTensor { + TODO("not implemented for integers") + } + + override fun diagonalEmbedding( + diagonalEntries: StructureND, + offset: Int, + dim1: Int, + dim2: Int, + ): IntTensor { + val n = diagonalEntries.shape.size + val d1 = minusIndexFrom(n + 1, dim1) + val d2 = minusIndexFrom(n + 1, dim2) + + check(d1 != d2) { + "Diagonal dimensions cannot be identical $d1, $d2" + } + check(d1 <= n && d2 <= n) { + "Dimension out of range" + } + + var lessDim = d1 + var greaterDim = d2 + var realOffset = offset + if (lessDim > greaterDim) { + realOffset *= -1 + lessDim = greaterDim.also { greaterDim = lessDim } + } + + val resShape = diagonalEntries.shape.slice(0 until lessDim) + + intArrayOf(diagonalEntries.shape[n - 1] + abs(realOffset)) + + diagonalEntries.shape.slice(lessDim until greaterDim - 1) + + intArrayOf(diagonalEntries.shape[n - 1] + abs(realOffset)) + + diagonalEntries.shape.slice(greaterDim - 1 until n - 1) + val resTensor = zeros(resShape) + + for (i in 0 until diagonalEntries.asIntTensor().linearSize) { + val multiIndex = diagonalEntries.asIntTensor().indices.index(i) + + var offset1 = 0 + var offset2 = abs(realOffset) + if (realOffset < 0) { + offset1 = offset2.also { offset2 = offset1 } + } + val diagonalMultiIndex = multiIndex.slice(0 until lessDim).toIntArray() + + intArrayOf(multiIndex[n - 1] + offset1) + + multiIndex.slice(lessDim until greaterDim - 1).toIntArray() + + intArrayOf(multiIndex[n - 1] + offset2) + + multiIndex.slice(greaterDim - 1 until n - 1).toIntArray() + + resTensor[diagonalMultiIndex] = diagonalEntries[multiIndex] + } + + return resTensor.asIntTensor() + } + + /** + * Compares element-wise two int tensors + * + * @param other the tensor to compare with `input` tensor. + * @param epsilon permissible error when comparing two Int values. + * @return true if two tensors have the same shape and elements, false otherwise. + */ + public fun Tensor.eq(other: Tensor): Boolean = + asIntTensor().eq(other) { x, y -> x == y } + + private fun Tensor.eq( + other: Tensor, + eqFunction: (Int, Int) -> Boolean, + ): Boolean { + checkShapesCompatible(asIntTensor(), other) + val n = asIntTensor().linearSize + if (n != other.asIntTensor().linearSize) { + return false + } + for (i in 0 until n) { + if (!eqFunction(asIntTensor().source[i], other.asIntTensor().source[i])) { + return false + } + } + return true + } + + /** + * Concatenates a sequence of tensors with equal shapes along the first dimension. + * + * @param tensors the [List] of tensors with same shapes to concatenate + * @return tensor with concatenation result + */ + public fun stack(tensors: List>): IntTensor { + check(tensors.isNotEmpty()) { "List must have at least 1 element" } + val shape = tensors[0].shape + check(tensors.all { it.shape contentEquals shape }) { "Tensors must have same shapes" } + val resShape = ShapeND(tensors.size) + shape +// val resBuffer: List = tensors.flatMap { +// it.asIntTensor().source.array.drop(it.asIntTensor().bufferStart) +// .take(it.asIntTensor().linearSize) +// } + val resBuffer = tensors.map { it.asIntTensor().source }.concat() + return IntTensor(resShape, resBuffer) + } + + /** + * Builds tensor from rows of the input tensor. + * + * @param indices the [IntArray] of 1-dimensional indices + * @return tensor with rows corresponding to row by [indices] + */ + public fun Tensor.rowsByIndices(indices: IntArray): IntTensor = stack(indices.map { getTensor(it) }) + + private inline fun StructureND.foldDimToInt( + dim: Int, + keepDim: Boolean, + foldFunction: (IntArray) -> Int, + ): IntTensor { + check(dim < dimension) { "Dimension $dim out of range $dimension" } + val resShape = if (keepDim) { + shape.first(dim) + intArrayOf(1) + shape.last(dimension - dim - 1) + } else { + shape.first(dim) + shape.last(dimension - dim - 1) + } + val resNumElements = resShape.linearSize + val init = foldFunction(IntArray(1) { 0 }) + val resTensor = IntTensor( + resShape, + IntBuffer(resNumElements) { init } + ) + for (index in resTensor.indices) { + val prefix = index.take(dim).toIntArray() + val suffix = index.takeLast(dimension - dim - 1).toIntArray() + resTensor[index] = foldFunction(IntArray(shape[dim]) { i -> + asIntTensor()[prefix + intArrayOf(i) + suffix] + }) + } + return resTensor + } + + + override fun StructureND.sum(): Int = reduceElements { it.array.sum() } + + override fun StructureND.sum(dim: Int, keepDim: Boolean): IntTensor = + foldDimToInt(dim, keepDim) { x -> x.sum() } + + override fun StructureND.min(): Int = reduceElements { it.array.min() } + + override fun StructureND.min(dim: Int, keepDim: Boolean): IntTensor = + foldDimToInt(dim, keepDim) { x -> x.minOrNull()!! } + + override fun StructureND.argMin(dim: Int, keepDim: Boolean): Tensor = foldDimToInt(dim, keepDim) { x -> + x.withIndex().minBy { it.value }.index + } + + override fun StructureND.max(): Int = reduceElements { it.array.max() } + + override fun StructureND.max(dim: Int, keepDim: Boolean): IntTensor = + foldDimToInt(dim, keepDim) { x -> x.max() } + + + override fun StructureND.argMax(dim: Int, keepDim: Boolean): IntTensor = + foldDimToInt(dim, keepDim) { x -> + x.withIndex().maxBy { it.value }.index + } + + public fun StructureND.mean(): Double = sum().toDouble() / indices.linearSize +} + +public val Int.Companion.tensorAlgebra: IntTensorAlgebra get() = IntTensorAlgebra +public val IntRing.tensorAlgebra: IntTensorAlgebra get() = IntTensorAlgebra + + diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/LevenbergMarquardtAlgorithm.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/LevenbergMarquardtAlgorithm.kt new file mode 100644 index 000000000..3cb485d7d --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/LevenbergMarquardtAlgorithm.kt @@ -0,0 +1,589 @@ +/* + * Copyright 2018-2023 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.tensors.core + +import space.kscience.kmath.linear.transpose +import space.kscience.kmath.nd.* +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.div +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.dot +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.minus +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.times +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.transposed +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.plus +import kotlin.math.max +import kotlin.math.min +import kotlin.math.pow +import kotlin.reflect.KFunction3 + +/** + * Type of convergence achieved as a result of executing the Levenberg-Marquardt algorithm. + * + * InGradient: gradient convergence achieved + * (max(J^T W dy) < epsilon1, + * where J - Jacobi matrix (dy^/dp) for the current approximation y^, + * W - weight matrix from input, dy = (y - y^(p))). + * InParameters: convergence in parameters achieved + * (max(h_i / p_i) < epsilon2, + * where h_i - offset for parameter p_i on the current iteration). + * InReducedChiSquare: chi-squared convergence achieved + * (chi squared value divided by (m - n + 1) < epsilon2, + * where n - number of parameters, m - amount of points). + * NoConvergence: the maximum number of iterations has been reached without reaching any convergence. + */ +public enum class TypeOfConvergence { + InGradient, + InParameters, + InReducedChiSquare, + NoConvergence +} + +/** + * The data obtained as a result of the execution of the Levenberg-Marquardt algorithm. + * + * iterations: number of completed iterations. + * funcCalls: the number of evaluations of the input function during execution. + * resultChiSq: chi squared value on final parameters. + * resultLambda: final lambda parameter used to calculate the offset. + * resultParameters: final parameters. + * typeOfConvergence: type of convergence. + */ +public data class LMResultInfo ( + var iterations:Int, + var funcCalls: Int, + var resultChiSq: Double, + var resultLambda: Double, + var resultParameters: MutableStructure2D, + var typeOfConvergence: TypeOfConvergence, +) + +/** + * Input data for the Levenberg-Marquardt function. + * + * func: function of n independent variables x, m parameters an example number, + * rotating a vector of n values y, in which each of the y_i is calculated at its x_i with the given parameters. + * startParameters: starting parameters. + * independentVariables: independent variables, for each of which the real value is known. + * realValues: real values obtained with given independent variables but unknown parameters. + * weight: measurement error for realValues (denominator in each term of sum of weighted squared errors). + * pDelta: delta when calculating the derivative with respect to parameters. + * minParameters: the lower bound of parameter values. + * maxParameters: upper limit of parameter values. + * maxIterations: maximum allowable number of iterations. + * epsilons: epsilon1 - convergence tolerance for gradient, + * epsilon2 - convergence tolerance for parameters, + * epsilon3 - convergence tolerance for reduced chi-square, + * epsilon4 - determines acceptance of a step. + * lambdas: lambda0 - starting lambda value for parameter offset count, + * lambdaUp - factor for increasing lambda, + * lambdaDown - factor for decreasing lambda. + * updateType: 1: Levenberg-Marquardt lambda update, + * 2: Quadratic update, + * 3: Nielsen's lambda update equations. + * nargin: a value that determines which options to use by default + * (<5 - use weight by default, <6 - use pDelta by default, <7 - use minParameters by default, + * <8 - use maxParameters by default, <9 - use updateType by default). + * exampleNumber: a parameter for a function with which you can choose its behavior. + */ +public data class LMInput ( + var func: (MutableStructure2D, MutableStructure2D, Int) -> (MutableStructure2D), + var startParameters: MutableStructure2D, + var independentVariables: MutableStructure2D, + var realValues: MutableStructure2D, + var weight: Double, + var pDelta: MutableStructure2D, + var minParameters: MutableStructure2D, + var maxParameters: MutableStructure2D, + var maxIterations: Int, + var epsilons: DoubleArray, + var lambdas: DoubleArray, + var updateType: Int, + var nargin: Int, + var exampleNumber: Int +) + + +/** + * Levenberg-Marquardt optimization. + * + * An optimization method that iteratively searches for the optimal function parameters + * that best describe the dataset. The 'input' is the function being optimized, a set of real data + * (calculated with independent variables, but with an unknown set of parameters), a set of + * independent variables, and variables for adjusting the algorithm, described in the documentation for the LMInput class. + * The function returns number of completed iterations, the number of evaluations of the input function during execution, + * chi squared value on final parameters, final lambda parameter used to calculate the offset, final parameters + * and type of convergence in the 'output'. + * + * @receiver the `input`. + * @return the 'output'. + */ +public fun DoubleTensorAlgebra.levenbergMarquardt(inputData: LMInput): LMResultInfo { + val resultInfo = LMResultInfo(0, 0, 0.0, + 0.0, inputData.startParameters, TypeOfConvergence.NoConvergence) + + val eps = 2.2204e-16 + + val settings = LMSettings(0, 0, inputData.exampleNumber) + settings.funcCalls = 0 // running count of function evaluations + + var p = inputData.startParameters + val t = inputData.independentVariables + + val Npar = length(p) // number of parameters + val Npnt = length(inputData.realValues) // number of data points + var pOld = zeros(ShapeND(intArrayOf(Npar, 1))).as2D() // previous set of parameters + var yOld = zeros(ShapeND(intArrayOf(Npnt, 1))).as2D() // previous model, y_old = y_hat(t;p_old) + var X2 = 1e-3 / eps // a really big initial Chi-sq value + var X2Old = 1e-3 / eps // a really big initial Chi-sq value + var J = zeros(ShapeND(intArrayOf(Npnt, Npar))).as2D() // Jacobian matrix + val DoF = Npnt - Npar // statistical degrees of freedom + + var weight = fromArray(ShapeND(intArrayOf(1, 1)), doubleArrayOf(inputData.weight)).as2D() + if (inputData.nargin < 5) { + weight = fromArray(ShapeND(intArrayOf(1, 1)), doubleArrayOf((inputData.realValues.transpose().dot(inputData.realValues)).as1D()[0])).as2D() + } + + var dp = inputData.pDelta + if (inputData.nargin < 6) { + dp = fromArray(ShapeND(intArrayOf(1, 1)), doubleArrayOf(0.001)).as2D() + } + + var minParameters = inputData.minParameters + if (inputData.nargin < 7) { + minParameters = p + minParameters.abs() + minParameters = minParameters.div(-100.0).as2D() + } + + var maxParameters = inputData.maxParameters + if (inputData.nargin < 8) { + maxParameters = p + maxParameters.abs() + maxParameters = maxParameters.div(100.0).as2D() + } + + var maxIterations = inputData.maxIterations + var epsilon1 = inputData.epsilons[0] + var epsilon2 = inputData.epsilons[1] + var epsilon3 = inputData.epsilons[2] + var epsilon4 = inputData.epsilons[3] + var lambda0 = inputData.lambdas[0] + var lambdaUpFac = inputData.lambdas[1] + var lambdaDnFac = inputData.lambdas[2] + var updateType = inputData.updateType + + if (inputData.nargin < 9) { + maxIterations = 10 * Npar + epsilon1 = 1e-3 + epsilon2 = 1e-3 + epsilon3 = 1e-1 + epsilon4 = 1e-1 + lambda0 = 1e-2 + lambdaUpFac = 11.0 + lambdaDnFac = 9.0 + updateType = 1 + } + + minParameters = makeColumn(minParameters) + maxParameters = makeColumn(maxParameters) + + if (length(makeColumn(dp)) == 1) { + dp = ones(ShapeND(intArrayOf(Npar, 1))).div(1 / dp[0, 0]).as2D() + } + + var stop = false // termination flag + + if (weight.shape.component1() == 1 || variance(weight) == 0.0) { // identical weights vector + weight = ones(ShapeND(intArrayOf(Npnt, 1))).div(1 / kotlin.math.abs(weight[0, 0])).as2D() + } + else { + weight = makeColumn(weight) + weight.abs() + } + + // initialize Jacobian with finite difference calculation + var lmMatxAns = lmMatx(inputData.func, t, pOld, yOld, 1, J, p, inputData.realValues, weight, dp, settings) + var JtWJ = lmMatxAns[0] + var JtWdy = lmMatxAns[1] + X2 = lmMatxAns[2][0, 0] + var yHat = lmMatxAns[3] + J = lmMatxAns[4] + + if ( abs(JtWdy).max() < epsilon1 ) { + stop = true + } + + var lambda = 1.0 + var nu = 1 + + if (updateType == 1) { + lambda = lambda0 // Marquardt: init'l lambda + } + else { + lambda = lambda0 * (makeColumnFromDiagonal(JtWJ)).max() + nu = 2 + } + + X2Old = X2 // previous value of X2 + + var h: DoubleTensor + + while (!stop && settings.iteration <= maxIterations) { + settings.iteration += 1 + + // incremental change in parameters + h = if (updateType == 1) { // Marquardt + val solve = solve(JtWJ.plus(makeMatrixWithDiagonal(makeColumnFromDiagonal(JtWJ)).div(1 / lambda)).as2D(), JtWdy) + solve.asDoubleTensor() + } else { // Quadratic and Nielsen + val solve = solve(JtWJ.plus(lmEye(Npar).div(1 / lambda)).as2D(), JtWdy) + solve.asDoubleTensor() + } + + var pTry = (p + h).as2D() // update the [idx] elements + pTry = smallestElementComparison(largestElementComparison(minParameters, pTry.as2D()), maxParameters) // apply constraints + + var deltaY = inputData.realValues.minus(evaluateFunction(inputData.func, t, pTry, inputData.exampleNumber)) // residual error using p_try + + for (i in 0 until deltaY.shape.component1()) { // floating point error; break + for (j in 0 until deltaY.shape.component2()) { + if (deltaY[i, j] == Double.POSITIVE_INFINITY || deltaY[i, j] == Double.NEGATIVE_INFINITY) { + stop = true + break + } + } + } + + settings.funcCalls += 1 + + val tmp = deltaY.times(weight) + var X2Try = deltaY.as2D().transpose().dot(tmp) // Chi-squared error criteria + + val alpha = 1.0 + if (updateType == 2) { // Quadratic + // One step of quadratic line update in the h direction for minimum X2 + val alpha = JtWdy.transpose().dot(h) / ((X2Try.minus(X2)).div(2.0).plus(2 * JtWdy.transpose().dot(h))) + h = h.dot(alpha) + pTry = p.plus(h).as2D() // update only [idx] elements + pTry = smallestElementComparison(largestElementComparison(minParameters, pTry), maxParameters) // apply constraints + + deltaY = inputData.realValues.minus(evaluateFunction(inputData.func, t, pTry, inputData.exampleNumber)) // residual error using p_try + settings.funcCalls += 1 + + X2Try = deltaY.as2D().transpose().dot(deltaY.times(weight)) // Chi-squared error criteria + } + + val rho = when (updateType) { // Nielsen + 1 -> { + val tmp = h.transposed() + .dot(makeMatrixWithDiagonal(makeColumnFromDiagonal(JtWJ)).div(1 / lambda).dot(h).plus(JtWdy)) + X2.minus(X2Try).as2D()[0, 0] / abs(tmp.as2D()).as2D()[0, 0] + } + else -> { + val tmp = h.transposed().dot(h.div(1 / lambda).plus(JtWdy)) + X2.minus(X2Try).as2D()[0, 0] / abs(tmp.as2D()).as2D()[0, 0] + } + } + + if (rho > epsilon4) { // it IS significantly better + val dX2 = X2.minus(X2Old) + X2Old = X2 + pOld = p.copyToTensor().as2D() + yOld = yHat.copyToTensor().as2D() + p = makeColumn(pTry) // accept p_try + + lmMatxAns = lmMatx(inputData.func, t, pOld, yOld, dX2.toInt(), J, p, inputData.realValues, weight, dp, settings) + // decrease lambda ==> Gauss-Newton method + JtWJ = lmMatxAns[0] + JtWdy = lmMatxAns[1] + X2 = lmMatxAns[2][0, 0] + yHat = lmMatxAns[3] + J = lmMatxAns[4] + + lambda = when (updateType) { + 1 -> { // Levenberg + max(lambda / lambdaDnFac, 1e-7); + } + + 2 -> { // Quadratic + max(lambda / (1 + alpha), 1e-7); + } + + else -> { // Nielsen + nu = 2 + lambda * max(1.0 / 3, 1 - (2 * rho - 1).pow(3)) + } + } + } else { // it IS NOT better + X2 = X2Old // do not accept p_try + if (settings.iteration % (2 * Npar) == 0) { // rank-1 update of Jacobian + lmMatxAns = lmMatx(inputData.func, t, pOld, yOld, -1, J, p, inputData.realValues, weight, dp, settings) + JtWJ = lmMatxAns[0] + JtWdy = lmMatxAns[1] + yHat = lmMatxAns[3] + J = lmMatxAns[4] + } + + // increase lambda ==> gradient descent method + lambda = when (updateType) { + 1 -> { // Levenberg + min(lambda * lambdaUpFac, 1e7) + } + + 2 -> { // Quadratic + lambda + kotlin.math.abs(((X2Try.as2D()[0, 0] - X2) / 2) / alpha) + } + + else -> { // Nielsen + nu *= 2 + lambda * (nu / 2) + } + } + } + + val chiSq = X2 / DoF + resultInfo.iterations = settings.iteration + resultInfo.funcCalls = settings.funcCalls + resultInfo.resultChiSq = chiSq + resultInfo.resultLambda = lambda + resultInfo.resultParameters = p + + + if (abs(JtWdy).max() < epsilon1 && settings.iteration > 2) { + resultInfo.typeOfConvergence = TypeOfConvergence.InGradient + stop = true + } + if ((abs(h.as2D()).div(abs(p) + 1e-12)).max() < epsilon2 && settings.iteration > 2) { + resultInfo.typeOfConvergence = TypeOfConvergence.InParameters + stop = true + } + if (X2 / DoF < epsilon3 && settings.iteration > 2) { + resultInfo.typeOfConvergence = TypeOfConvergence.InReducedChiSquare + stop = true + } + if (settings.iteration == maxIterations) { + resultInfo.typeOfConvergence = TypeOfConvergence.NoConvergence + stop = true + } + } + return resultInfo +} + +private data class LMSettings ( + var iteration:Int, + var funcCalls: Int, + var exampleNumber:Int +) + +/* matrix -> column of all elements */ +private fun makeColumn(tensor: MutableStructure2D): MutableStructure2D { + val shape = intArrayOf(tensor.shape.component1() * tensor.shape.component2(), 1) + val buffer = DoubleArray(tensor.shape.component1() * tensor.shape.component2()) + for (i in 0 until tensor.shape.component1()) { + for (j in 0 until tensor.shape.component2()) { + buffer[i * tensor.shape.component2() + j] = tensor[i, j] + } + } + return BroadcastDoubleTensorAlgebra.fromArray(ShapeND(shape), buffer).as2D() +} + +/* column length */ +private fun length(column: MutableStructure2D) : Int { + return column.shape.component1() +} + +private fun MutableStructure2D.abs() { + for (i in 0 until this.shape.component1()) { + for (j in 0 until this.shape.component2()) { + this[i, j] = kotlin.math.abs(this[i, j]) + } + } +} + +private fun abs(input: MutableStructure2D): MutableStructure2D { + val tensor = BroadcastDoubleTensorAlgebra.ones( + ShapeND( + intArrayOf( + input.shape.component1(), + input.shape.component2() + ) + ) + ).as2D() + for (i in 0 until tensor.shape.component1()) { + for (j in 0 until tensor.shape.component2()) { + tensor[i, j] = kotlin.math.abs(input[i, j]) + } + } + return tensor +} + +private fun makeColumnFromDiagonal(input: MutableStructure2D): MutableStructure2D { + val tensor = BroadcastDoubleTensorAlgebra.ones(ShapeND(intArrayOf(input.shape.component1(), 1))).as2D() + for (i in 0 until tensor.shape.component1()) { + tensor[i, 0] = input[i, i] + } + return tensor +} + +private fun makeMatrixWithDiagonal(column: MutableStructure2D): MutableStructure2D { + val size = column.shape.component1() + val tensor = BroadcastDoubleTensorAlgebra.zeros(ShapeND(intArrayOf(size, size))).as2D() + for (i in 0 until size) { + tensor[i, i] = column[i, 0] + } + return tensor +} + +private fun lmEye(size: Int): MutableStructure2D { + val column = BroadcastDoubleTensorAlgebra.ones(ShapeND(intArrayOf(size, 1))).as2D() + return makeMatrixWithDiagonal(column) +} + +private fun largestElementComparison(a: MutableStructure2D, b: MutableStructure2D): MutableStructure2D { + val aSizeX = a.shape.component1() + val aSizeY = a.shape.component2() + val bSizeX = b.shape.component1() + val bSizeY = b.shape.component2() + val tensor = BroadcastDoubleTensorAlgebra.zeros(ShapeND(intArrayOf(max(aSizeX, bSizeX), max(aSizeY, bSizeY)))).as2D() + for (i in 0 until tensor.shape.component1()) { + for (j in 0 until tensor.shape.component2()) { + if (i < aSizeX && i < bSizeX && j < aSizeY && j < bSizeY) { + tensor[i, j] = max(a[i, j], b[i, j]) + } + else if (i < aSizeX && j < aSizeY) { + tensor[i, j] = a[i, j] + } + else { + tensor[i, j] = b[i, j] + } + } + } + return tensor +} + +private fun smallestElementComparison(a: MutableStructure2D, b: MutableStructure2D): MutableStructure2D { + val aSizeX = a.shape.component1() + val aSizeY = a.shape.component2() + val bSizeX = b.shape.component1() + val bSizeY = b.shape.component2() + val tensor = BroadcastDoubleTensorAlgebra.zeros(ShapeND(intArrayOf(max(aSizeX, bSizeX), max(aSizeY, bSizeY)))).as2D() + for (i in 0 until tensor.shape.component1()) { + for (j in 0 until tensor.shape.component2()) { + if (i < aSizeX && i < bSizeX && j < aSizeY && j < bSizeY) { + tensor[i, j] = min(a[i, j], b[i, j]) + } + else if (i < aSizeX && j < aSizeY) { + tensor[i, j] = a[i, j] + } + else { + tensor[i, j] = b[i, j] + } + } + } + return tensor +} + +private fun getZeroIndices(column: MutableStructure2D, epsilon: Double = 0.000001): MutableStructure2D? { + var idx = emptyArray() + for (i in 0 until column.shape.component1()) { + if (kotlin.math.abs(column[i, 0]) > epsilon) { + idx += (i + 1.0) + } + } + if (idx.isNotEmpty()) { + return BroadcastDoubleTensorAlgebra.fromArray(ShapeND(intArrayOf(idx.size, 1)), idx.toDoubleArray()).as2D() + } + return null +} + +private fun evaluateFunction(func: (MutableStructure2D, MutableStructure2D, Int) -> MutableStructure2D, + t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int) + : MutableStructure2D +{ + return func(t, p, exampleNumber) +} + +private fun lmMatx(func: (MutableStructure2D, MutableStructure2D, Int) -> MutableStructure2D, + t: MutableStructure2D, pOld: MutableStructure2D, yOld: MutableStructure2D, + dX2: Int, JInput: MutableStructure2D, p: MutableStructure2D, + yDat: MutableStructure2D, weight: MutableStructure2D, dp:MutableStructure2D, settings:LMSettings) : Array> +{ + // default: dp = 0.001 + val Npar = length(p) // number of parameters + + val yHat = evaluateFunction(func, t, p, settings.exampleNumber) // evaluate model using parameters 'p' + settings.funcCalls += 1 + + var J = JInput + + J = if (settings.iteration % (2 * Npar) == 0 || dX2 > 0) { + lmFdJ(func, t, p, yHat, dp, settings).as2D() // finite difference + } + else { + lmBroydenJ(pOld, yOld, J, p, yHat).as2D() // rank-1 update + } + + val deltaY = yDat.minus(yHat) + + val chiSq = deltaY.transposed().dot( deltaY.times(weight) ).as2D() + val JtWJ = J.transposed().dot ( J.times( weight.dot(BroadcastDoubleTensorAlgebra.ones(ShapeND(intArrayOf(1, Npar)))) ) ).as2D() + val JtWdy = J.transposed().dot( weight.times(deltaY) ).as2D() + + return arrayOf(JtWJ,JtWdy,chiSq,yHat,J) +} + +private fun lmBroydenJ(pOld: MutableStructure2D, yOld: MutableStructure2D, JInput: MutableStructure2D, + p: MutableStructure2D, y: MutableStructure2D): MutableStructure2D { + var J = JInput.copyToTensor() + + val h = p.minus(pOld) + val increase = y.minus(yOld).minus( J.dot(h) ).dot(h.transposed()).div( (h.transposed().dot(h)).as2D()[0, 0] ) + J = J.plus(increase) + + return J.as2D() +} + +private fun lmFdJ(func: (MutableStructure2D, MutableStructure2D, exampleNumber: Int) -> MutableStructure2D, + t: MutableStructure2D, p: MutableStructure2D, y: MutableStructure2D, + dp: MutableStructure2D, settings: LMSettings): MutableStructure2D { + // default: dp = 0.001 * ones(1,n) + + val m = length(y) // number of data points + val n = length(p) // number of parameters + + val ps = p.copyToTensor().as2D() + val J = BroadcastDoubleTensorAlgebra.zeros(ShapeND(intArrayOf(m, n))).as2D() // initialize Jacobian to Zero + val del = BroadcastDoubleTensorAlgebra.zeros(ShapeND(intArrayOf(n, 1))).as2D() + + for (j in 0 until n) { + + del[j, 0] = dp[j, 0] * (1 + kotlin.math.abs(p[j, 0])) // parameter perturbation + p[j, 0] = ps[j, 0] + del[j, 0] // perturb parameter p(j) + + val epsilon = 0.0000001 + if (kotlin.math.abs(del[j, 0]) > epsilon) { + val y1 = evaluateFunction(func, t, p, settings.exampleNumber) + settings.funcCalls += 1 + + if (dp[j, 0] < 0) { // backwards difference + for (i in 0 until J.shape.component1()) { + J[i, j] = (y1.as2D().minus(y).as2D())[i, 0] / del[j, 0] + } + } + else { + // Do tests for it + p[j, 0] = ps[j, 0] - del[j, 0] // central difference, additional func call + for (i in 0 until J.shape.component1()) { + J[i, j] = (y1.as2D().minus(evaluateFunction(func, t, p, settings.exampleNumber)).as2D())[i, 0] / (2 * del[j, 0]) + } + settings.funcCalls += 1 + } + } + + p[j, 0] = ps[j, 0] + } + + return J.as2D() +} diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/TensorLinearStructure.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/TensorLinearStructure.kt deleted file mode 100644 index 19eefc2f8..000000000 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/TensorLinearStructure.kt +++ /dev/null @@ -1,74 +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.tensors.core - -import space.kscience.kmath.nd.Strides -import kotlin.math.max - -/** - * This [Strides] implementation follows the last dimension first convention - * For more information: https://numpy.org/doc/stable/reference/generated/numpy.ndarray.strides.html - * - * @param shape the shape of the tensor. - */ -public class TensorLinearStructure(override val shape: IntArray) : Strides() { - override val strides: IntArray - get() = stridesFromShape(shape) - - override fun index(offset: Int): IntArray = - indexFromOffset(offset, strides, shape.size) - - override val linearSize: Int - get() = shape.reduce(Int::times) - - override fun equals(other: Any?): Boolean { - if (this === other) return true - if (other == null || this::class != other::class) return false - - other as TensorLinearStructure - - if (!shape.contentEquals(other.shape)) return false - - return true - } - - override fun hashCode(): Int { - return shape.contentHashCode() - } - - public companion object { - - public fun stridesFromShape(shape: IntArray): IntArray { - val nDim = shape.size - val res = IntArray(nDim) - if (nDim == 0) - return res - - var current = nDim - 1 - res[current] = 1 - - while (current > 0) { - res[current - 1] = max(1, shape[current]) * res[current] - current-- - } - return res - } - - public fun indexFromOffset(offset: Int, strides: IntArray, nDim: Int): IntArray { - val res = IntArray(nDim) - var current = offset - var strideIndex = 0 - - while (strideIndex < nDim) { - res[strideIndex] = (current / strides[strideIndex]) - current %= strides[strideIndex] - strideIndex++ - } - return res - } - } - -} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/broadcastUtils.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/broadcastUtils.kt index 9d37423e5..1e87e6620 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/broadcastUtils.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/broadcastUtils.kt @@ -1,17 +1,20 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core.internal +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.nd.* +import space.kscience.kmath.structures.asBuffer import space.kscience.kmath.tensors.core.DoubleTensor import kotlin.math.max internal fun multiIndexBroadCasting(tensor: DoubleTensor, resTensor: DoubleTensor, linearSize: Int) { for (linearIndex in 0 until linearSize) { val totalMultiIndex = resTensor.indices.index(linearIndex) - val curMultiIndex = tensor.shape.copyOf() + val curMultiIndex = tensor.shape.toArray() val offset = totalMultiIndex.size - curMultiIndex.size @@ -24,12 +27,12 @@ internal fun multiIndexBroadCasting(tensor: DoubleTensor, resTensor: DoubleTenso } val curLinearIndex = tensor.indices.offset(curMultiIndex) - resTensor.mutableBuffer.array()[linearIndex] = - tensor.mutableBuffer.array()[tensor.bufferStart + curLinearIndex] + resTensor.source[linearIndex] = + tensor.source[curLinearIndex] } } -internal fun broadcastShapes(vararg shapes: IntArray): IntArray { +internal fun broadcastShapes(shapes: List): ShapeND { var totalDim = 0 for (shape in shapes) { totalDim = max(totalDim, shape.size) @@ -54,16 +57,16 @@ internal fun broadcastShapes(vararg shapes: IntArray): IntArray { } } - return totalShape + return ShapeND(totalShape) } -internal fun broadcastTo(tensor: DoubleTensor, newShape: IntArray): DoubleTensor { +internal fun broadcastTo(tensor: DoubleTensor, newShape: ShapeND): DoubleTensor { require(tensor.shape.size <= newShape.size) { "Tensor is not compatible with the new shape" } - val n = newShape.reduce { acc, i -> acc * i } - val resTensor = DoubleTensor(newShape, DoubleArray(n)) + val n = newShape.linearSize + val resTensor = DoubleTensor(newShape, DoubleArray(n).asBuffer()) for (i in tensor.shape.indices) { val curDim = tensor.shape[i] @@ -78,11 +81,11 @@ internal fun broadcastTo(tensor: DoubleTensor, newShape: IntArray): DoubleTensor } internal fun broadcastTensors(vararg tensors: DoubleTensor): List { - val totalShape = broadcastShapes(*(tensors.map { it.shape }).toTypedArray()) - val n = totalShape.reduce { acc, i -> acc * i } + val totalShape = broadcastShapes(tensors.map { it.shape }) + val n = totalShape.linearSize return tensors.map { tensor -> - val resTensor = DoubleTensor(totalShape, DoubleArray(n)) + val resTensor = DoubleTensor(totalShape, DoubleArray(n).asBuffer()) multiIndexBroadCasting(tensor, resTensor, n) resTensor } @@ -99,24 +102,25 @@ internal fun broadcastOuterTensors(vararg tensors: DoubleTensor): List acc * i } + val totalShape = broadcastShapes(tensors.map { it.shape.slice(0..it.shape.size - 3) }) + val n = totalShape.linearSize return buildList { for (tensor in tensors) { - val matrixShape = tensor.shape.sliceArray(tensor.shape.size - 2 until tensor.shape.size).copyOf() + val matrixShape = tensor.shape.slice(tensor.shape.size - 2 until tensor.shape.size) val matrixSize = matrixShape[0] * matrixShape[1] - val matrix = DoubleTensor(matrixShape, DoubleArray(matrixSize)) + val matrix = DoubleTensor(matrixShape, DoubleArray(matrixSize).asBuffer()) - val outerTensor = DoubleTensor(totalShape, DoubleArray(n)) - val resTensor = DoubleTensor(totalShape + matrixShape, DoubleArray(n * matrixSize)) + val outerTensor = DoubleTensor(totalShape, DoubleArray(n).asBuffer()) + val resTensor = DoubleTensor(totalShape + matrixShape, DoubleArray(n * matrixSize).asBuffer()) for (linearIndex in 0 until n) { val totalMultiIndex = outerTensor.indices.index(linearIndex) - var curMultiIndex = tensor.shape.sliceArray(0..tensor.shape.size - 3).copyOf() + @OptIn(UnsafeKMathAPI::class) + var curMultiIndex = tensor.shape.slice(0..tensor.shape.size - 3).asArray() curMultiIndex = IntArray(totalMultiIndex.size - curMultiIndex.size) { 1 } + curMultiIndex - val newTensor = DoubleTensor(curMultiIndex + matrixShape, tensor.mutableBuffer.array()) + val newTensor = DoubleTensor(ShapeND(curMultiIndex) + matrixShape, tensor.source) for (i in curMultiIndex.indices) { if (curMultiIndex[i] != 1) { @@ -136,8 +140,8 @@ internal fun broadcastOuterTensors(vararg tensors: DoubleTensor): List 0) { "Illegal empty shape provided" } -internal fun checkEmptyDoubleBuffer(buffer: DoubleArray) = - check(buffer.isNotEmpty()) { - "Illegal empty buffer provided" - } +internal fun checkEmptyDoubleBuffer(buffer: DoubleArray) = check(buffer.isNotEmpty()) { + "Illegal empty buffer provided" +} -internal fun checkBufferShapeConsistency(shape: IntArray, buffer: DoubleArray) = - check(buffer.size == shape.reduce(Int::times)) { - "Inconsistent shape ${shape.toList()} for buffer of size ${buffer.size} provided" +internal fun checkBufferShapeConsistency(shape: ShapeND, buffer: DoubleArray) = + check(buffer.size == shape.linearSize) { + "Inconsistent shape $shape for buffer of size ${buffer.size} provided" } -internal fun checkShapesCompatible(a: StructureND, b: StructureND) = +@PublishedApi +internal fun checkShapesCompatible(a: StructureND, b: StructureND): Unit = check(a.shape contentEquals b.shape) { - "Incompatible shapes ${a.shape.toList()} and ${b.shape.toList()} " + "Incompatible shapes ${a.shape} and ${b.shape} " } internal fun checkTranspose(dim: Int, i: Int, j: Int) = @@ -36,10 +41,10 @@ internal fun checkTranspose(dim: Int, i: Int, j: Int) = "Cannot transpose $i to $j for a tensor of dim $dim" } -internal fun checkView(a: Tensor, shape: IntArray) = - check(a.shape.reduce(Int::times) == shape.reduce(Int::times)) +internal fun checkView(a: Tensor, shape: ShapeND) = + check(a.shape.linearSize == shape.linearSize) -internal fun checkSquareMatrix(shape: IntArray) { +internal fun checkSquareMatrix(shape: ShapeND) { val n = shape.size check(n >= 2) { "Expected tensor with 2 or more dimensions, got size $n instead" @@ -50,16 +55,15 @@ internal fun checkSquareMatrix(shape: IntArray) { } internal fun DoubleTensorAlgebra.checkSymmetric( - tensor: Tensor, epsilon: Double = 1e-6 -) = - check(tensor.eq(tensor.transpose(), epsilon)) { - "Tensor is not symmetric about the last 2 dimensions at precision $epsilon" - } + tensor: Tensor, epsilon: Double = 1e-6, +) = check(tensor.eq(tensor.transposed(), epsilon)) { + "Tensor is not symmetric about the last 2 dimensions at precision $epsilon" +} internal fun DoubleTensorAlgebra.checkPositiveDefinite(tensor: DoubleTensor, epsilon: Double = 1e-6) { checkSymmetric(tensor, epsilon) for (mat in tensor.matrixSequence()) - check(mat.asTensor().detLU().value() > 0.0) { - "Tensor contains matrices which are not positive definite ${mat.asTensor().detLU().value()}" + check(detLU(mat.asDoubleTensor()).value() > 0.0) { + "Tensor contains matrices which are not positive definite ${detLU(mat.asDoubleTensor()).value()}" } } \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/doubleTensorHelpers.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/doubleTensorHelpers.kt new file mode 100644 index 000000000..a293c8da3 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/doubleTensorHelpers.kt @@ -0,0 +1,186 @@ +/* + * Copyright 2018-2022 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.tensors.core.internal + +import space.kscience.kmath.nd.* +import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.structures.asBuffer +import space.kscience.kmath.structures.indices +import space.kscience.kmath.tensors.core.BroadcastDoubleTensorAlgebra.eye +import space.kscience.kmath.tensors.core.BufferedTensor +import space.kscience.kmath.tensors.core.DoubleTensor +import space.kscience.kmath.tensors.core.OffsetDoubleBuffer +import space.kscience.kmath.tensors.core.copyToTensor +import kotlin.math.abs +import kotlin.math.max +import kotlin.math.sqrt + + +internal fun MutableStructure2D.jacobiHelper( + maxIteration: Int, + epsilon: Double, +): Pair> { + val n = rowNum + val A_ = copyToTensor() + val V = eye(n) + val D = DoubleBuffer(n) { get(it, it) } + val B = DoubleBuffer(n) { get(it, it) } + val Z = DoubleBuffer(n) { 0.0 } + + // assume that buffered tensor is square matrix + operator fun DoubleTensor.get(i: Int, j: Int): Double { + return source[i * shape[0] + j] + } + + operator fun BufferedTensor.set(i: Int, j: Int, value: Double) { + source[i * shape[0] + j] = value + } + + fun maxOffDiagonal(matrix: DoubleTensor): Double { + var maxOffDiagonalElement = 0.0 + 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: DoubleTensor, 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: DoubleTensor, + v: DoubleTensor, + d: DoubleBuffer, + z: DoubleBuffer, + ) { + 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])) { + 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 n) { + rotate(a, s, tau, ip, j, iq, j) + } + for (j in 0 until n) { + rotate(v, s, tau, j, ip, j, iq) + } + } + } + } + + fun updateDiagonal( + d: DoubleBuffer, + z: DoubleBuffer, + b: DoubleBuffer, + ) { + for (ip in 0 until d.size) { + b[ip] += z[ip] + d[ip] = b[ip] + z[ip] = 0.0 + } + } + + 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_) + } + + // TODO sort eigenvalues + return D to V.as2D() +} + +/** + * Concatenate a list of arrays + */ +internal fun List.concat(): DoubleBuffer { + val array = DoubleArray(sumOf { it.size }) + var pointer = 0 + while (pointer < array.size) { + for (bufferIndex in indices) { + val buffer = get(bufferIndex) + for (innerIndex in buffer.indices) { + array[pointer] = buffer[innerIndex] + pointer++ + } + } + } + return array.asBuffer() +} + +internal val DoubleTensor.vectors: List + get() { + val n = shape.size + val vectorOffset = shape[n - 1] + val vectorShape = ShapeND(shape.last()) + + return List(linearSize / vectorOffset) { index -> + val offset = index * vectorOffset + DoubleTensor(vectorShape, source.view(offset, vectorShape.first())) + } + } + + +internal fun DoubleTensor.vectorSequence(): Sequence = vectors.asSequence() + + +internal val DoubleTensor.matrices: List + get() { + val n = shape.size + check(n >= 2) { "Expected tensor with 2 or more dimensions, got size $n" } + val matrixOffset = shape[n - 1] * shape[n - 2] + val matrixShape = ShapeND(shape[n - 2], shape[n - 1]) + + val size = matrixShape.linearSize + + return List(linearSize / matrixOffset) { index -> + val offset = index * matrixOffset + DoubleTensor(matrixShape, source.view(offset, size)) + } + } + +internal fun DoubleTensor.matrixSequence(): Sequence = matrices.asSequence() \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/intTensorHelpers.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/intTensorHelpers.kt new file mode 100644 index 000000000..35f0bf324 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/intTensorHelpers.kt @@ -0,0 +1,66 @@ +/* + * Copyright 2018-2022 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.tensors.core.internal + +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.first +import space.kscience.kmath.nd.last +import space.kscience.kmath.operations.asSequence +import space.kscience.kmath.structures.IntBuffer +import space.kscience.kmath.structures.VirtualBuffer +import space.kscience.kmath.structures.asBuffer +import space.kscience.kmath.structures.indices +import space.kscience.kmath.tensors.core.IntTensor +import space.kscience.kmath.tensors.core.OffsetIntBuffer + +/** + * Concatenate a list of arrays + */ +internal fun List.concat(): IntBuffer { + val array = IntArray(sumOf { it.size }) + var pointer = 0 + while (pointer < array.size) { + for (bufferIndex in indices) { + val buffer = get(bufferIndex) + for (innerIndex in buffer.indices) { + array[pointer] = buffer[innerIndex] + pointer++ + } + } + } + return array.asBuffer() +} + + +internal fun IntTensor.vectors(): VirtualBuffer { + val n = shape.size + val vectorOffset = shape[n - 1] + val vectorShape = shape.last(1) + + return VirtualBuffer(linearSize / vectorOffset) { index -> + val offset = index * vectorOffset + IntTensor(vectorShape, source.view(offset, vectorShape.first())) + } +} + + +internal fun IntTensor.vectorSequence(): Sequence = vectors().asSequence() + + +internal val IntTensor.matrices: VirtualBuffer + get(){ + val n = shape.size + check(n >= 2) { "Expected tensor with 2 or more dimensions, got size $n" } + val matrixOffset = shape[n - 1] * shape[n - 2] + val matrixShape = ShapeND(shape[n - 2], shape[n - 1]) + + return VirtualBuffer(linearSize / matrixOffset) { index -> + val offset = index * matrixOffset + IntTensor(matrixShape, source.view(offset)) + } + } + +internal fun IntTensor.matrixSequence(): Sequence = matrices.asSequence() \ No newline at end of file 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 aba6167ce..086c69e49 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 @@ -1,79 +1,36 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core.internal -import space.kscience.kmath.nd.MutableStructure1D -import space.kscience.kmath.nd.MutableStructure2D -import space.kscience.kmath.nd.as1D -import space.kscience.kmath.nd.as2D -import space.kscience.kmath.operations.asSequence +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.invoke -import space.kscience.kmath.structures.VirtualBuffer -import space.kscience.kmath.tensors.core.BufferedTensor -import space.kscience.kmath.tensors.core.DoubleTensor -import space.kscience.kmath.tensors.core.DoubleTensorAlgebra -import space.kscience.kmath.tensors.core.IntTensor +import space.kscience.kmath.structures.* +import space.kscience.kmath.tensors.core.* import kotlin.math.abs +import kotlin.math.max import kotlin.math.min import kotlin.math.sqrt -internal val BufferedTensor.vectors: VirtualBuffer> - get() { - val n = shape.size - val vectorOffset = shape[n - 1] - val vectorShape = intArrayOf(shape.last()) - - return VirtualBuffer(numElements / vectorOffset) { index -> - val offset = index * vectorOffset - BufferedTensor(vectorShape, mutableBuffer, bufferStart + offset) - } - } - - -internal fun BufferedTensor.vectorSequence(): Sequence> = vectors.asSequence() - -/** - * A random access alternative to [matrixSequence] - */ -internal val BufferedTensor.matrices: VirtualBuffer> - get() { - val n = shape.size - check(n >= 2) { "Expected tensor with 2 or more dimensions, got size $n" } - val matrixOffset = shape[n - 1] * shape[n - 2] - val matrixShape = intArrayOf(shape[n - 2], shape[n - 1]) - - return VirtualBuffer(numElements / matrixOffset) { index -> - val offset = index * matrixOffset - BufferedTensor(matrixShape, mutableBuffer, bufferStart + offset) - } - } - -internal fun BufferedTensor.matrixSequence(): Sequence> = matrices.asSequence() - internal fun dotTo( 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 + val aBuffer = a.source + val bBuffer = b.source + val resBuffer = res.source for (i in 0 until l) { for (j in 0 until n) { var curr = 0.0 for (k in 0 until m) { - curr += aBuffer[aStart + i * m + k] * bBuffer[bStart + k * n + j] + curr += aBuffer[i * m + k] * bBuffer[k * n + j] } - resBuffer[resStart + i * n + j] = curr + resBuffer[i * n + j] = curr } } } @@ -129,29 +86,29 @@ internal fun luHelper( return false } -internal fun BufferedTensor.setUpPivots(): IntTensor { +internal fun StructureND.setUpPivots(): IntTensor { val n = this.shape.size val m = this.shape.last() val pivotsShape = IntArray(n - 1) { i -> this.shape[i] } pivotsShape[n - 2] = m + 1 return IntTensor( - pivotsShape, - IntArray(pivotsShape.reduce(Int::times)) { 0 } + ShapeND(pivotsShape), + IntBuffer(pivotsShape.reduce(Int::times)) { 0 } ) } internal fun DoubleTensorAlgebra.computeLU( - tensor: DoubleTensor, + tensor: StructureND, epsilon: Double, ): Pair? { checkSquareMatrix(tensor.shape) - val luTensor = tensor.copy() + val luTensor = tensor.copyToTensor() val pivotsTensor = tensor.setUpPivots() for ((lu, pivots) in luTensor.matrixSequence().zip(pivotsTensor.vectorSequence())) - if (luHelper(lu.as2D(), pivots.as1D(), epsilon)) + if (luHelper(lu.asDoubleTensor2D(), pivots.as1D(), epsilon)) return null return Pair(luTensor, pivotsTensor) @@ -252,23 +209,23 @@ internal fun DoubleTensorAlgebra.qrHelper( ) { checkSquareMatrix(matrix.shape) val n = matrix.shape[0] - val qM = q.as2D() - val matrixT = matrix.transpose(0, 1) - val qT = q.transpose(0, 1) + val qM = q.asDoubleTensor2D() + val matrixT = matrix.transposed(0, 1) + val qT = q.transposed(0, 1) for (j in 0 until n) { - val v = matrixT[j] - val vv = v.as1D() + val v = matrixT.getTensor(j) + val vv = v.asDoubleBuffer() if (j > 0) { for (i in 0 until j) { - r[i, j] = (qT[i] dot matrixT[j]).value() + r[i, j] = (qT.getTensor(i) dot matrixT.getTensor(j)).value() for (k in 0 until n) { - val qTi = qT[i].as1D() + val qTi = qT.getTensor(i).asDoubleBuffer() vv[k] = vv[k] - r[i, j] * qTi[k] } } } - r[j, j] = DoubleTensorAlgebra { (v dot v).sqrt().value() } + r[j, j] = DoubleTensorAlgebra { sqrt((v dot v)).value() } for (i in 0 until n) { qM[i, j] = vv[i] / r[j, j] } @@ -280,18 +237,18 @@ internal fun DoubleTensorAlgebra.svd1d(a: DoubleTensor, epsilon: Double = 1e-10) var v: DoubleTensor val b: DoubleTensor if (n > m) { - b = a.transpose(0, 1).dot(a) - v = DoubleTensor(intArrayOf(m), getRandomUnitVector(m, 0)) + b = a.transposed(0, 1).dot(a) + v = DoubleTensor(ShapeND(m), DoubleBuffer.randomUnitVector(m, 0)) } else { - b = a.dot(a.transpose(0, 1)) - v = DoubleTensor(intArrayOf(n), getRandomUnitVector(n, 0)) + b = a.dot(a.transposed(0, 1)) + v = DoubleTensor(ShapeND(n), DoubleBuffer.randomUnitVector(n, 0)) } var lastV: DoubleTensor while (true) { lastV = v v = b.dot(lastV) - val norm = DoubleTensorAlgebra { (v dot v).sqrt().value() } + val norm = DoubleTensorAlgebra { sqrt((v dot v)).value() } v = v.times(1.0 / norm) if (abs(v.dot(lastV).value()) > 1 - epsilon) { return v @@ -308,15 +265,15 @@ internal fun DoubleTensorAlgebra.svdHelper( val (matrixU, matrixS, matrixV) = USV for (k in 0 until min(n, m)) { - var a = matrix.copy() + var a = matrix.copyToTensor() for ((singularValue, u, v) in res.slice(0 until k)) { val outerProduct = DoubleArray(u.shape[0] * v.shape[0]) for (i in 0 until u.shape[0]) { for (j in 0 until v.shape[0]) { - outerProduct[i * v.shape[0] + j] = u[i].value() * v[j].value() + outerProduct[i * v.shape[0] + j] = u.getTensor(i).value() * v.getTensor(j).value() } } - a = a - singularValue.times(DoubleTensor(intArrayOf(u.shape[0], v.shape[0]), outerProduct)) + a = a - singularValue.times(DoubleTensor(ShapeND(u.shape[0], v.shape[0]), outerProduct.asBuffer())) } var v: DoubleTensor var u: DoubleTensor @@ -324,12 +281,12 @@ internal fun DoubleTensorAlgebra.svdHelper( if (n > m) { v = svd1d(a, epsilon) u = matrix.dot(v) - norm = DoubleTensorAlgebra { (u dot u).sqrt().value() } + norm = DoubleTensorAlgebra { sqrt((u dot u)).value() } u = u.times(1.0 / norm) } else { u = svd1d(a, epsilon) - v = matrix.transpose(0, 1).dot(u) - norm = DoubleTensorAlgebra { (v dot v).sqrt().value() } + v = matrix.transposed(0, 1).dot(u) + norm = DoubleTensorAlgebra { sqrt((v dot v)).value() } v = v.times(1.0 / norm) } @@ -337,15 +294,311 @@ internal fun DoubleTensorAlgebra.svdHelper( } val s = res.map { it.first }.toDoubleArray() - val uBuffer = res.map { it.second }.flatMap { it.mutableBuffer.array().toList() }.toDoubleArray() - val vBuffer = res.map { it.third }.flatMap { it.mutableBuffer.array().toList() }.toDoubleArray() + val uBuffer = res.map { it.second.source }.concat() + val vBuffer = res.map { it.third.source }.concat() for (i in uBuffer.indices) { - matrixU.mutableBuffer.array()[matrixU.bufferStart + i] = uBuffer[i] + matrixU.source[i] = uBuffer[i] } for (i in s.indices) { - matrixS.mutableBuffer.array()[matrixS.bufferStart + i] = s[i] + matrixS.source[i] = s[i] } for (i in vBuffer.indices) { - matrixV.mutableBuffer.array()[matrixV.bufferStart + i] = vBuffer[i] + matrixV.source[i] = vBuffer[i] } } + +private fun pythag(a: Double, b: Double): Double { + val at: Double = abs(a) + val bt: Double = abs(b) + val ct: Double + val result: Double + if (at > bt) { + ct = bt / at + result = at * sqrt(1.0 + ct * ct) + } else if (bt > 0.0) { + ct = at / bt + result = bt * sqrt(1.0 + ct * ct) + } else result = 0.0 + return result +} + +private fun SIGN(a: Double, b: Double): Double { + if (b >= 0.0) + return abs(a) + else + return -abs(a) +} + +internal fun MutableStructure2D.svdGolubKahanHelper(u: MutableStructure2D, w: BufferedTensor, + v: MutableStructure2D, iterations: Int, epsilon: Double) { + val shape = this.shape + val m = shape.component1() + val n = shape.component2() + var f = 0.0 + val rv1 = DoubleArray(n) + var s = 0.0 + var scale = 0.0 + var anorm = 0.0 + var g = 0.0 + var l = 0 + + val wStart = 0 + val wBuffer = w.source + + for (i in 0 until n) { + /* left-hand reduction */ + l = i + 1 + rv1[i] = scale * g + g = 0.0 + s = 0.0 + scale = 0.0 + if (i < m) { + for (k in i until m) { + scale += abs(this[k, i]); + } + if (abs(scale) > epsilon) { + for (k in i until m) { + this[k, i] = (this[k, i] / scale) + s += this[k, i] * this[k, i] + } + f = this[i, i] + if (f >= 0) { + g = (-1) * abs(sqrt(s)) + } else { + g = abs(sqrt(s)) + } + val h = f * g - s + this[i, i] = f - g + if (i != n - 1) { + for (j in l until n) { + s = 0.0 + for (k in i until m) { + s += this[k, i] * this[k, j] + } + f = s / h + for (k in i until m) { + this[k, j] += f * this[k, i] + } + } + } + for (k in i until m) { + this[k, i] = this[k, i] * scale + } + } + } + + wBuffer[wStart + i] = scale * g + /* right-hand reduction */ + g = 0.0 + s = 0.0 + scale = 0.0 + if (i < m && i != n - 1) { + for (k in l until n) { + scale += abs(this[i, k]) + } + if (abs(scale) > epsilon) { + for (k in l until n) { + this[i, k] = this[i, k] / scale + s += this[i, k] * this[i, k] + } + f = this[i, l] + if (f >= 0) { + g = (-1) * abs(sqrt(s)) + } else { + g = abs(sqrt(s)) + } + val h = f * g - s + this[i, l] = f - g + for (k in l until n) { + rv1[k] = this[i, k] / h + } + if (i != m - 1) { + for (j in l until m) { + s = 0.0 + for (k in l until n) { + s += this[j, k] * this[i, k] + } + for (k in l until n) { + this[j, k] += s * rv1[k] + } + } + } + for (k in l until n) { + this[i, k] = this[i, k] * scale + } + } + } + anorm = max(anorm, (abs(wBuffer[wStart + i]) + abs(rv1[i]))); + } + + for (i in n - 1 downTo 0) { + if (i < n - 1) { + if (abs(g) > epsilon) { + for (j in l until n) { + v[j, i] = (this[i, j] / this[i, l]) / g + } + for (j in l until n) { + s = 0.0 + for (k in l until n) + s += this[i, k] * v[k, j] + for (k in l until n) + v[k, j] += s * v[k, i] + } + } + for (j in l until n) { + v[i, j] = 0.0 + v[j, i] = 0.0 + } + } + v[i, i] = 1.0 + g = rv1[i] + l = i + } + + for (i in min(n, m) - 1 downTo 0) { + l = i + 1 + g = wBuffer[wStart + i] + for (j in l until n) { + this[i, j] = 0.0 + } + if (abs(g) > epsilon) { + g = 1.0 / g + for (j in l until n) { + s = 0.0 + for (k in l until m) { + s += this[k, i] * this[k, j] + } + f = (s / this[i, i]) * g + for (k in i until m) { + this[k, j] += f * this[k, i] + } + } + for (j in i until m) { + this[j, i] *= g + } + } else { + for (j in i until m) { + this[j, i] = 0.0 + } + } + this[i, i] += 1.0 + } + + var flag = 0 + var nm = 0 + var c = 0.0 + var h = 0.0 + var y = 0.0 + var z = 0.0 + var x = 0.0 + for (k in n - 1 downTo 0) { + for (its in 1 until iterations) { + flag = 1 + for (newl in k downTo 0) { + nm = newl - 1 + if (abs(rv1[newl]) + anorm == anorm) { + flag = 0 + l = newl + break + } + if (abs(wBuffer[wStart + nm]) + anorm == anorm) { + l = newl + break + } + } + + if (flag != 0) { + c = 0.0 + s = 1.0 + for (i in l until k + 1) { + f = s * rv1[i] + rv1[i] = c * rv1[i] + if (abs(f) + anorm == anorm) { + break + } + g = wBuffer[wStart + i] + h = pythag(f, g) + wBuffer[wStart + i] = h + h = 1.0 / h + c = g * h + s = (-f) * h + for (j in 0 until m) { + y = this[j, nm] + z = this[j, i] + this[j, nm] = y * c + z * s + this[j, i] = z * c - y * s + } + } + } + + z = wBuffer[wStart + k] + if (l == k) { + if (z < 0.0) { + wBuffer[wStart + k] = -z + for (j in 0 until n) + v[j, k] = -v[j, k] + } + break + } + + x = wBuffer[wStart + l] + nm = k - 1 + y = wBuffer[wStart + nm] + g = rv1[nm] + h = rv1[k] + f = ((y - z) * (y + z) + (g - h) * (g + h)) / (2.0 * h * y) + g = pythag(f, 1.0) + f = ((x - z) * (x + z) + h * ((y / (f + SIGN(g, f))) - h)) / x + c = 1.0 + s = 1.0 + + var i = 0 + for (j in l until nm + 1) { + i = j + 1 + g = rv1[i] + y = wBuffer[wStart + i] + h = s * g + g = c * g + z = pythag(f, h) + rv1[j] = z + c = f / z + s = h / z + f = x * c + g * s + g = g * c - x * s + h = y * s + y *= c + + for (jj in 0 until n) { + x = v[jj, j]; + z = v[jj, i]; + v[jj, j] = x * c + z * s; + v[jj, i] = z * c - x * s; + } + z = pythag(f, h) + wBuffer[wStart + j] = z + if (abs(z) > epsilon) { + z = 1.0 / z + c = f * z + s = h * z + } + f = c * g + s * y + x = c * y - s * g + for (jj in 0 until m) { + y = this[jj, j] + z = this[jj, i] + this[jj, j] = y * c + z * s + this[jj, i] = z * c - y * s + } + } + rv1[l] = 0.0 + rv1[k] = f + wBuffer[wStart + k] = x + } + } + + for (i in 0 until n) { + for (j in 0 until m) { + u[j, i] = this[j, i] + } + } +} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/tensorCastsUtils.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/tensorCastsUtils.kt deleted file mode 100644 index a5cdb2f47..000000000 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/tensorCastsUtils.kt +++ /dev/null @@ -1,50 +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.tensors.core.internal - -import space.kscience.kmath.nd.MutableBufferND -import space.kscience.kmath.nd.StructureND -import space.kscience.kmath.structures.asMutableBuffer -import space.kscience.kmath.tensors.api.Tensor -import space.kscience.kmath.tensors.core.BufferedTensor -import space.kscience.kmath.tensors.core.DoubleTensor -import space.kscience.kmath.tensors.core.IntTensor -import space.kscience.kmath.tensors.core.TensorLinearStructure - -internal fun BufferedTensor.asTensor(): IntTensor = - IntTensor(this.shape, this.mutableBuffer.array(), this.bufferStart) - -internal fun BufferedTensor.asTensor(): DoubleTensor = - DoubleTensor(this.shape, this.mutableBuffer.array(), this.bufferStart) - -internal fun StructureND.copyToBufferedTensor(): BufferedTensor = - BufferedTensor( - this.shape, - TensorLinearStructure(this.shape).asSequence().map(this::get).toMutableList().asMutableBuffer(), 0 - ) - -internal fun StructureND.toBufferedTensor(): BufferedTensor = when (this) { - is BufferedTensor -> this - is MutableBufferND -> if (this.indices == TensorLinearStructure(this.shape)) { - BufferedTensor(this.shape, this.buffer, 0) - } else { - this.copyToBufferedTensor() - } - else -> this.copyToBufferedTensor() -} - -@PublishedApi -internal val StructureND.tensor: DoubleTensor - get() = when (this) { - is DoubleTensor -> this - else -> this.toBufferedTensor().asTensor() - } - -internal val Tensor.tensor: IntTensor - get() = when (this) { - is IntTensor -> this - else -> this.toBufferedTensor().asTensor() - } diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/utils.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/utils.kt index 85cc91b1d..2709ac474 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/utils.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/internal/utils.kt @@ -1,46 +1,31 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core.internal -import space.kscience.kmath.nd.as1D -import space.kscience.kmath.operations.toMutableList +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.asList +import space.kscience.kmath.nd.last +import space.kscience.kmath.operations.DoubleBufferOps.Companion.map +import space.kscience.kmath.random.RandomGenerator import space.kscience.kmath.samplers.GaussianSampler -import space.kscience.kmath.stat.RandomGenerator -import space.kscience.kmath.structures.* +import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.tensors.core.BufferedTensor import space.kscience.kmath.tensors.core.DoubleTensor import kotlin.math.* -/** - * Returns a reference to [IntArray] containing all the elements of this [Buffer] or copy the data. - */ -internal fun Buffer.array(): IntArray = when (this) { - is IntBuffer -> array - else -> this.toIntArray() -} - -/** - * Returns a reference to [DoubleArray] containing all the elements of this [Buffer] or copy the data. - */ -@PublishedApi -internal fun Buffer.array(): DoubleArray = when (this) { - is DoubleBuffer -> array - else -> this.toDoubleArray() -} - -internal fun getRandomNormals(n: Int, seed: Long): DoubleArray { +internal fun DoubleBuffer.Companion.randomNormals(n: Int, seed: Long): DoubleBuffer { val distribution = GaussianSampler(0.0, 1.0) val generator = RandomGenerator.default(seed) - return distribution.sample(generator).nextBufferBlocking(n).toDoubleArray() + return distribution.sample(generator).nextBufferBlocking(n) } -internal fun getRandomUnitVector(n: Int, seed: Long): DoubleArray { - val unnorm = getRandomNormals(n, seed) - val norm = sqrt(unnorm.sumOf { it * it }) - return unnorm.map { it / norm }.toDoubleArray() +internal fun DoubleBuffer.Companion.randomUnitVector(n: Int, seed: Long): DoubleBuffer { + val unnorm: DoubleBuffer = randomNormals(n, seed) + val norm = sqrt(unnorm.array.sumOf { it * it }) + return unnorm.map { it / norm } } internal fun minusIndexFrom(n: Int, i: Int): Int = if (i >= 0) i else { @@ -71,6 +56,7 @@ internal fun format(value: Double, digits: Int = 4): String = buildString { append("e+") append(order) } + else -> { append('e') append(order) @@ -82,7 +68,8 @@ internal fun format(value: Double, digits: Int = 4): String = buildString { repeat(fLength - res.length) { append(' ') } } -internal fun DoubleTensor.toPrettyString(): String = buildString { +@OptIn(PerformancePitfall::class) +public fun DoubleTensor.toPrettyString(): String = buildString { var offset = 0 val shape = this@toPrettyString.shape val linearStructure = this@toPrettyString.indices @@ -100,14 +87,14 @@ internal fun DoubleTensor.toPrettyString(): String = buildString { charOffset += 1 } - val values = vector.as1D().toMutableList().map(::format) + val values = vector.elements().map { format(it.second) } values.joinTo(this, separator = ", ") append(']') charOffset -= 1 - index.reversed().zip(shape.reversed()).drop(1).forEach { (ind, maxInd) -> + index.reversed().zip(shape.asList().reversed()).drop(1).forEach { (ind, maxInd) -> if (ind != maxInd - 1) { return@forEach } @@ -116,7 +103,7 @@ internal fun DoubleTensor.toPrettyString(): String = buildString { } offset += vectorSize - if (this@toPrettyString.numElements == offset) { + if (this@toPrettyString.indices.linearSize == offset) { break } diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorAlgebraExtensions.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorAlgebraExtensions.kt index d8e8df31e..e2b7c23e6 100644 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorAlgebraExtensions.kt +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorAlgebraExtensions.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -7,13 +7,16 @@ package space.kscience.kmath.tensors.core -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.Shape +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.ShapeND import kotlin.jvm.JvmName @JvmName("varArgOne") -public fun DoubleTensorAlgebra.one(vararg shape: Int): DoubleTensor = ones(intArrayOf(*shape)) -public fun DoubleTensorAlgebra.one(shape: Shape): DoubleTensor = ones(shape) +public fun DoubleTensorAlgebra.one(vararg shape: Int): DoubleTensor = ones(ShapeND(shape)) + +public fun DoubleTensorAlgebra.one(shape: ShapeND): DoubleTensor = ones(shape) + @JvmName("varArgZero") -public fun DoubleTensorAlgebra.zero(vararg shape: Int): DoubleTensor = zeros(intArrayOf(*shape)) -public fun DoubleTensorAlgebra.zero(shape: Shape): DoubleTensor = zeros(shape) \ No newline at end of file +public fun DoubleTensorAlgebra.zero(vararg shape: Int): DoubleTensor = zeros(ShapeND(shape)) + +public fun DoubleTensorAlgebra.zero(shape: ShapeND): DoubleTensor = zeros(shape) diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorCasts.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorCasts.kt deleted file mode 100644 index 5dc8114dd..000000000 --- a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorCasts.kt +++ /dev/null @@ -1,38 +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.tensors.core - -import space.kscience.kmath.tensors.api.Tensor -import space.kscience.kmath.tensors.core.internal.tensor - -/** - * Casts [Tensor] of [Double] to [DoubleTensor] - */ -public fun Tensor.toDoubleTensor(): DoubleTensor = this.tensor - -/** - * Casts [Tensor] of [Int] to [IntTensor] - */ -public fun Tensor.toIntTensor(): IntTensor = this.tensor - -/** - * Returns a copy-protected [DoubleArray] of tensor elements - */ -public fun DoubleTensor.copyArray(): DoubleArray { - //TODO use ArrayCopy - return DoubleArray(numElements) { i -> - mutableBuffer[bufferStart + i] - } -} - -/** - * Returns a copy-protected [IntArray] of tensor elements - */ -public fun IntTensor.copyArray(): IntArray { - return IntArray(numElements) { i -> - mutableBuffer[bufferStart + i] - } -} diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorOps.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorOps.kt new file mode 100644 index 000000000..88ffb0bfe --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorOps.kt @@ -0,0 +1,400 @@ +/* + * Copyright 2018-2022 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.tensors.core + +import space.kscience.kmath.nd.* +import space.kscience.kmath.operations.covariance +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.tensors.api.Tensor +import space.kscience.kmath.tensors.core.internal.* +import kotlin.math.min +import kotlin.math.sign + + +/** + * Returns a tensor of random numbers drawn from normal distributions with `0.0` mean and `1.0` standard deviation. + * + * @param shape the desired shape for the output tensor. + * @param seed the random seed of the pseudo-random number generator. + * @return tensor of a given shape filled with numbers from the normal distribution + * with `0.0` mean and `1.0` standard deviation. + */ +public fun DoubleTensorAlgebra.randomNormal(shape: ShapeND, seed: Long = 0): DoubleTensor = + fromBuffer(shape, DoubleBuffer.randomNormals(shape.linearSize, seed)) + +/** + * Returns a tensor with the same shape as `input` of random numbers drawn from normal distributions + * with `0.0` mean and `1.0` standard deviation. + * + * @receiver the `input`. + * @param seed the random seed of the pseudo-random number generator. + * @return a tensor with the same shape as `input` filled with numbers from the normal distribution + * with `0.0` mean and `1.0` standard deviation. + */ +public fun DoubleTensorAlgebra.randomNormalLike(structure: WithShape, seed: Long = 0): DoubleTensor = + DoubleTensor(structure.shape, DoubleBuffer.randomNormals(structure.shape.linearSize, seed)) + +/** + * Concatenates a sequence of tensors with equal shapes along the first dimension. + * + * @param tensors the [List] of tensors with same shapes to concatenate + * @return tensor with concatenation result + */ +public fun stack(tensors: List>): DoubleTensor { + check(tensors.isNotEmpty()) { "List must have at least 1 element" } + val shape = tensors[0].shape + check(tensors.all { it.shape contentEquals shape }) { "Tensors must have same shapes" } + val resShape = ShapeND(tensors.size) + shape +// val resBuffer: List = tensors.flatMap { +// it.asDoubleTensor().source.array.drop(it.asDoubleTensor().bufferStart) +// .take(it.asDoubleTensor().linearSize) +// } + val resBuffer = tensors.map { it.asDoubleTensor().source }.concat() + return DoubleTensor(resShape, resBuffer) +} + +/** + * Computes the LU factorization of a matrix or batches of matrices `input`. + * Returns a tuple containing the LU factorization and pivots of `input`. + * + * @param epsilon permissible error when comparing the determinant of a matrix with zero default is 1e-9 + * @return pair of `factorization` and `pivots`. + * The `factorization` has the shape ``(*, m, n)``, where``(*, m, n)`` is the shape of the `input` tensor. + * The `pivots` has the shape ``(∗, min(m, n))``. `pivots` stores all the intermediate transpositions of rows. + */ +public fun DoubleTensorAlgebra.luFactor( + structureND: StructureND, + epsilon: Double = 1e-9, +): Pair = + computeLU(structureND, epsilon) + ?: throw IllegalArgumentException("Tensor contains matrices which are singular at precision $epsilon") + + +/** + * Unpacks the data and pivots from a LU factorization of a tensor. + * Given a tensor [luTensor], return tensors `Triple(P, L, U)` satisfying `P dot luTensor = L dot U`, + * with `P` being a permutation matrix or batch of matrices, + * `L` being a lower triangular matrix or batch of matrices, + * `U` being an upper triangular matrix or batch of matrices. + * + * @param luTensor the packed LU factorization data + * @param pivotsTensor the packed LU factorization pivots + * @return triple of `P`, `L` and `U` tensors + */ +public fun DoubleTensorAlgebra.luPivot( + luTensor: StructureND, + pivotsTensor: Tensor, +): Triple { + checkSquareMatrix(luTensor.shape) + check( + luTensor.shape.first(luTensor.shape.size - 2) contentEquals pivotsTensor.shape.first(pivotsTensor.shape.size - 1) || + luTensor.shape.last() == pivotsTensor.shape.last() - 1 + ) { "Inappropriate shapes of input tensors" } + + val n = luTensor.shape.last() + val pTensor = zeroesLike(luTensor) + pTensor + .matrixSequence() + .zip(pivotsTensor.asIntTensor().vectorSequence()) + .forEach { (p, pivot) -> pivInit(p.asDoubleTensor2D(), pivot.as1D(), n) } + + val lTensor = zeroesLike(luTensor) + val uTensor = zeroesLike(luTensor) + + lTensor.matrixSequence() + .zip(uTensor.matrixSequence()) + .zip(luTensor.asDoubleTensor().matrixSequence()) + .forEach { (pairLU, lu) -> + val (l, u) = pairLU + luPivotHelper(l.asDoubleTensor2D(), u.asDoubleTensor2D(), lu.asDoubleTensor2D(), n) + } + + return Triple(pTensor, lTensor, uTensor) +} + + +/** + * LUP decomposition. + * + * Computes the LUP decomposition of a matrix or a batch of matrices. + * Given a tensor `input`, return tensors `Triple(P, L, U)` satisfying `P dot input == L dot U`, + * with `P` being a permutation matrix or batch of matrices, + * `L` being a lower triangular matrix or batch of matrices, + * `U` being an upper triangular matrix or batch of matrices. + * + * @param epsilon permissible error when comparing the determinant of a matrix with zero. + * @return triple of `P`, `L` and `U` tensors. + */ +public fun DoubleTensorAlgebra.lu( + structureND: StructureND, + epsilon: Double = 1e-9, +): Triple { + val (lu, pivots) = luFactor(structureND, epsilon) + return luPivot(lu, pivots) +} + + +/** + * QR decomposition. + * + * Computes the QR decomposition of a matrix or a batch of matrices, and returns a pair `Q to R` of tensors. + * Given a tensor `input`, return tensors `Q to R` satisfying `input == Q dot R`, + * with `Q` being an orthogonal matrix or batch of orthogonal matrices + * and `R` being an upper triangular matrix or batch of upper triangular matrices. + * + * @receiver the `input`. + * @param epsilon the permissible error when comparing tensors for equality. The default is 1e-6 + * Used when checking the positive definiteness of the input matrix or matrices. + * @return a pair of `Q` and `R` tensors. + */ +public fun DoubleTensorAlgebra.cholesky(structureND: StructureND, epsilon: Double = 1e-6): DoubleTensor { + checkSquareMatrix(structureND.shape) + checkPositiveDefinite(structureND.asDoubleTensor(), epsilon) + + val n = structureND.shape.last() + val lTensor = zeroesLike(structureND) + + for ((a, l) in structureND.asDoubleTensor().matrixSequence().zip(lTensor.matrixSequence())) + for (i in 0 until n) choleskyHelper(a.asDoubleTensor2D(), l.asDoubleTensor2D(), n) + + return lTensor +} + + +/** + * Singular Value Decomposition. + * + * Computes the singular value decomposition of either a matrix or batch of matrices `input`. + * The singular value decomposition is represented as a triple `Triple(U, S, V)`, + * such that `input == U dot diagonalEmbedding(S) dot V.transpose()`. + * If `input` is a batch of tensors, then U, S, and Vh are also batched with the same batch dimensions as `input. + * + * @receiver the `input`. + * @param epsilon permissible error when calculating the dot product of vectors + * i.e., the precision with which the cosine approaches 1 in an iterative algorithm. + * @return a triple `Triple(U, S, V)`. + */ +public fun DoubleTensorAlgebra.svd( + structureND: StructureND, + epsilon: Double, +): Triple, StructureND, StructureND> { + val size = structureND.dimension + val commonShape = structureND.shape.slice(0 until size - 2) + val (n, m) = structureND.shape.slice(size - 2 until size) + val uTensor = zeros(commonShape + ShapeND(min(n, m), n)) + val sTensor = zeros(commonShape + ShapeND(min(n, m))) + val vTensor = zeros(commonShape + ShapeND(min(n, m), m)) + + val matrices = structureND.asDoubleTensor().matrices + val uTensors = uTensor.matrices + val sTensorVectors = sTensor.vectors + val vTensors = vTensor.matrices + + for (index in matrices.indices) { + val matrix = matrices[index] + val usv = Triple( + uTensors[index], + sTensorVectors[index], + vTensors[index] + ) + val matrixSize = matrix.shape.linearSize + val curMatrix = DoubleTensor( + matrix.shape, + matrix.source.view(0, matrixSize) + ) + svdHelper(curMatrix, usv, m, n, epsilon) + } + + return Triple(uTensor.transposed(), sTensor, vTensor.transposed()) +} + +public fun DoubleTensorAlgebra.svdGolubKahan( + structureND: StructureND, + iterations: Int = 30, epsilon: Double = 1e-10 +): Triple { + val size = structureND.dimension + val commonShape = structureND.shape.slice(0 until size - 2) + val (n, m) = structureND.shape.slice(size - 2 until size) + val uTensor = zeros(commonShape + intArrayOf(n, m)) + val sTensor = zeros(commonShape + intArrayOf(m)) + val vTensor = zeros(commonShape + intArrayOf(m, m)) + + val matrices = structureND.asDoubleTensor().matrices + val uTensors = uTensor.matrices + val sTensorVectors = sTensor.vectors + val vTensors = vTensor.matrices + + for (index in matrices.indices) { + val matrix = matrices[index] + val matrixSize = matrix.shape.linearSize + val curMatrix = DoubleTensor( + matrix.shape, + matrix.source.view(0, matrixSize).copy() + ) + curMatrix.as2D().svdGolubKahanHelper(uTensors[index].as2D(), sTensorVectors[index], vTensors[index].as2D(), + iterations, epsilon) + } + + return Triple(uTensor, sTensor, vTensor) +} + +/** + * Returns eigenvalues and eigenvectors of a real symmetric matrix input or a batch of real symmetric matrices, + * represented by a pair `eigenvalues to eigenvectors`. + * + * @param epsilon the permissible error when comparing tensors for equality + * and when the cosine approaches 1 in the SVD algorithm. + * @return a pair `eigenvalues to eigenvectors`. + */ +public fun DoubleTensorAlgebra.symEigSvd( + structureND: StructureND, + epsilon: Double, +): Pair> { + //TODO optimize conversion + checkSymmetric(structureND.asDoubleTensor(), epsilon) + + fun MutableStructure2D.cleanSym(n: Int) { + for (i in 0 until n) { + for (j in 0 until n) { + if (i == j) { + this[i, j] = sign(this[i, j]) + } else { + this[i, j] = 0.0 + } + } + } + } + + val (u, s, v) = svd(structureND, epsilon) + val shp = s.shape + intArrayOf(1) + val utv = u.transposed() matmul v + val n = s.shape.last() + for (matrix in utv.matrixSequence()) { + matrix.asDoubleTensor2D().cleanSym(n) + } + + val eig = (utv dot s.asDoubleTensor().view(shp)).view(s.shape) + return eig to v +} + +public fun DoubleTensorAlgebra.symEigJacobi( + structureND: StructureND, + maxIteration: Int, + epsilon: Double, +): Pair { + //TODO optimize conversion + checkSymmetric(structureND.asDoubleTensor(), epsilon) + + val size = structureND.dimension + val eigenvectors = zeros(structureND.shape) + val eigenvalues = zeros(structureND.shape.slice(0 until size - 1)) + + var eigenvalueStart = 0 + var eigenvectorStart = 0 + for (matrix in structureND.asDoubleTensor().matrixSequence()) { + val matrix2D = matrix.asDoubleTensor2D() + val (d, v) = matrix2D.jacobiHelper(maxIteration, epsilon) + + for (i in 0 until matrix2D.rowNum) { + for (j in 0 until matrix2D.colNum) { + eigenvectors.source[eigenvectorStart + i * matrix2D.rowNum + j] = v[i, j] + } + } + + for (i in 0 until matrix2D.rowNum) { + eigenvalues.source[eigenvalueStart + i] = d[i] + } + + eigenvalueStart += structureND.shape.last() + eigenvectorStart += structureND.shape.last() * structureND.shape.last() + } + + return eigenvalues to eigenvectors +} + +/** + * Computes the determinant of a square matrix input, or of each square matrix in a batched input + * using LU factorization algorithm. + * + * @param epsilon the error in the LU algorithm—permissible error when comparing the determinant of a matrix + * with zero. + * @return the determinant. + */ +public fun DoubleTensorAlgebra.detLU(structureND: StructureND, epsilon: Double = 1e-9): DoubleTensor { + checkSquareMatrix(structureND.shape) + //TODO check for unnecessary copies + val luTensor = structureND.copyToTensor() + val pivotsTensor = structureND.setUpPivots() + + val n = structureND.shape.size + + val detTensorShape = ShapeND(IntArray(n - 1) { i -> structureND.shape[i] }.apply { + set(n - 2, 1) + }) + + val resBuffer = DoubleBuffer(detTensorShape.linearSize) { 0.0 } + + val detTensor = DoubleTensor( + detTensorShape, + resBuffer + ) + + luTensor.matrixSequence().zip(pivotsTensor.vectorSequence()).forEachIndexed { index, (lu, pivots) -> + resBuffer[index] = if (luHelper(lu.asDoubleTensor2D(), pivots.as1D(), epsilon)) + 0.0 else luMatrixDet(lu.asDoubleTensor2D(), pivots.as1D()) + } + + return detTensor +} + +/** + * Computes the multiplicative inverse matrix of a square matrix input, or of each square matrix in a batched input + * using LU factorization algorithm. + * Given a square matrix `a`, return the matrix `aInv` satisfying + * `a dot aInv == aInv dot a == eye(a.shape[0])`. + * + * @param epsilon error in the LU algorithm—permissible error when comparing the determinant of a matrix with zero + * @return the multiplicative inverse of a matrix. + */ +public fun DoubleTensorAlgebra.invLU(structureND: StructureND, epsilon: Double = 1e-9): DoubleTensor { + val (luTensor, pivotsTensor) = luFactor(structureND, epsilon) + val invTensor = zeroesLike(luTensor) + + //TODO replace sequence with a cycle + val seq = luTensor.matrixSequence().zip(pivotsTensor.vectorSequence()).zip(invTensor.matrixSequence()) + for ((luP, invMatrix) in seq) { + val (lu, pivots) = luP + luMatrixInv(lu.asDoubleTensor2D(), pivots.as1D(), invMatrix.asDoubleTensor2D()) + } + + return invTensor +} + +/** + * Returns the covariance matrix `M` of given vectors. + * + * `M[i, j]` contains covariance of `i`-th and `j`-th given vectors + * + * @param vectors the [List] of 1-dimensional tensors with same shape + * @return `M`. + */ +public fun DoubleTensorAlgebra.covariance(vectors: List>): DoubleTensor { + check(vectors.isNotEmpty()) { "List must have at least 1 element" } + val n = vectors.size + val m = vectors[0].size + check(vectors.all { it.size == m }) { "Vectors must have same shapes" } + val resTensor = DoubleTensor( + ShapeND(n, n), + DoubleBuffer(n * n) { 0.0 } + ) + for (i in 0 until n) { + for (j in 0 until n) { + resTensor[intArrayOf(i, j)] = bufferAlgebra.covariance(vectors[i], vectors[j]) + } + } + return resTensor +} \ No newline at end of file diff --git a/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorTransform.kt b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorTransform.kt new file mode 100644 index 000000000..3b0d15400 --- /dev/null +++ b/kmath-tensors/src/commonMain/kotlin/space/kscience/kmath/tensors/core/tensorTransform.kt @@ -0,0 +1,63 @@ +/* + * Copyright 2018-2022 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.tensors.core + +import space.kscience.kmath.nd.* +import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.structures.asBuffer +import space.kscience.kmath.tensors.api.Tensor + + +/** + * Create a mutable copy of given [StructureND]. + */ +public fun StructureND.copyToTensor(): DoubleTensor = if (this is DoubleTensor) { + DoubleTensor(shape, source.copy()) +} else if (this is DoubleBufferND && indices is RowStrides) { + DoubleTensor(shape, buffer.copy()) +} else { + DoubleTensor( + shape, + RowStrides(this.shape).map(this::getDouble).toDoubleArray().asBuffer(), + ) +} + +public fun StructureND.toDoubleTensor(): DoubleTensor { + return if (this is IntTensor) { + DoubleTensor( + shape, + DoubleBuffer(linearSize) { source[it].toDouble() } + ) + } else { + val tensor = DoubleTensorAlgebra.zeroesLike(this) + indices.forEach { + tensor[it] = getInt(it).toDouble() + } + return tensor + } +} + +/** + * Transforms [StructureND] of [Double] to [DoubleTensor]. Zero copy if possible, but is not guaranteed + */ +public fun StructureND.asDoubleTensor(): DoubleTensor = if (this is DoubleTensor) { + this +} else if (this is DoubleBufferND && indices is RowStrides) { + DoubleTensor(shape, buffer) +} else { + copyToTensor() +} + +/** + * Casts [Tensor] of [Int] to [IntTensor] + */ +public fun StructureND.asIntTensor(): IntTensor = when (this) { + is IntTensor -> this + else -> IntTensor( + shape, + RowStrides(shape).map(this::getInt).toIntArray().asBuffer() + ) +} \ No newline at end of file diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestBroadcasting.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestBroadcasting.kt index 6788ae792..73aed8a7b 100644 --- a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestBroadcasting.kt +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestBroadcasting.kt @@ -1,12 +1,17 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.contentEquals import space.kscience.kmath.operations.invoke -import space.kscience.kmath.tensors.core.internal.* +import space.kscience.kmath.tensors.core.internal.broadcastOuterTensors +import space.kscience.kmath.tensors.core.internal.broadcastShapes +import space.kscience.kmath.tensors.core.internal.broadcastTensors +import space.kscience.kmath.tensors.core.internal.broadcastTo import kotlin.test.Test import kotlin.test.assertTrue @@ -16,95 +21,95 @@ internal class TestBroadcasting { fun testBroadcastShapes() = DoubleTensorAlgebra { assertTrue( broadcastShapes( - intArrayOf(2, 3), intArrayOf(1, 3), intArrayOf(1, 1, 1) - ) contentEquals intArrayOf(1, 2, 3) + listOf(ShapeND(2, 3), ShapeND(1, 3), ShapeND(1, 1, 1)) + ) contentEquals ShapeND(1, 2, 3) ) assertTrue( broadcastShapes( - intArrayOf(6, 7), intArrayOf(5, 6, 1), intArrayOf(7), intArrayOf(5, 1, 7) - ) contentEquals intArrayOf(5, 6, 7) + listOf(ShapeND(6, 7), ShapeND(5, 6, 1), ShapeND(7), ShapeND(5, 1, 7)) + ) contentEquals ShapeND(5, 6, 7) ) } @Test fun testBroadcastTo() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor2 = fromArray(intArrayOf(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) val res = broadcastTo(tensor2, tensor1.shape) - assertTrue(res.shape contentEquals intArrayOf(2, 3)) - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(10.0, 20.0, 30.0, 10.0, 20.0, 30.0)) + assertTrue(res.shape contentEquals ShapeND(2, 3)) + assertTrue(res.source contentEquals doubleArrayOf(10.0, 20.0, 30.0, 10.0, 20.0, 30.0)) } @Test fun testBroadcastTensors() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor2 = fromArray(intArrayOf(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) - val tensor3 = fromArray(intArrayOf(1, 1, 1), doubleArrayOf(500.0)) + val tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor3 = fromArray(ShapeND(1, 1, 1), doubleArrayOf(500.0)) val res = broadcastTensors(tensor1, tensor2, tensor3) - assertTrue(res[0].shape contentEquals intArrayOf(1, 2, 3)) - assertTrue(res[1].shape contentEquals intArrayOf(1, 2, 3)) - assertTrue(res[2].shape contentEquals intArrayOf(1, 2, 3)) + assertTrue(res[0].shape contentEquals ShapeND(1, 2, 3)) + assertTrue(res[1].shape contentEquals ShapeND(1, 2, 3)) + assertTrue(res[2].shape contentEquals ShapeND(1, 2, 3)) - assertTrue(res[0].mutableBuffer.array() contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - assertTrue(res[1].mutableBuffer.array() contentEquals doubleArrayOf(10.0, 20.0, 30.0, 10.0, 20.0, 30.0)) - assertTrue(res[2].mutableBuffer.array() contentEquals doubleArrayOf(500.0, 500.0, 500.0, 500.0, 500.0, 500.0)) + assertTrue(res[0].source contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + assertTrue(res[1].source contentEquals doubleArrayOf(10.0, 20.0, 30.0, 10.0, 20.0, 30.0)) + assertTrue(res[2].source contentEquals doubleArrayOf(500.0, 500.0, 500.0, 500.0, 500.0, 500.0)) } @Test fun testBroadcastOuterTensors() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor2 = fromArray(intArrayOf(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) - val tensor3 = fromArray(intArrayOf(1, 1, 1), doubleArrayOf(500.0)) + val tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor3 = fromArray(ShapeND(1, 1, 1), doubleArrayOf(500.0)) val res = broadcastOuterTensors(tensor1, tensor2, tensor3) - assertTrue(res[0].shape contentEquals intArrayOf(1, 2, 3)) - assertTrue(res[1].shape contentEquals intArrayOf(1, 1, 3)) - assertTrue(res[2].shape contentEquals intArrayOf(1, 1, 1)) + assertTrue(res[0].shape contentEquals ShapeND(1, 2, 3)) + assertTrue(res[1].shape contentEquals ShapeND(1, 1, 3)) + assertTrue(res[2].shape contentEquals ShapeND(1, 1, 1)) - assertTrue(res[0].mutableBuffer.array() contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - assertTrue(res[1].mutableBuffer.array() contentEquals doubleArrayOf(10.0, 20.0, 30.0)) - assertTrue(res[2].mutableBuffer.array() contentEquals doubleArrayOf(500.0)) + assertTrue(res[0].source contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + assertTrue(res[1].source contentEquals doubleArrayOf(10.0, 20.0, 30.0)) + assertTrue(res[2].source contentEquals doubleArrayOf(500.0)) } @Test fun testBroadcastOuterTensorsShapes() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 1, 3, 2, 3), DoubleArray(2 * 1 * 3 * 2 * 3) {0.0}) - val tensor2 = fromArray(intArrayOf(4, 2, 5, 1, 3, 3), DoubleArray(4 * 2 * 5 * 1 * 3 * 3) {0.0}) - val tensor3 = fromArray(intArrayOf(1, 1), doubleArrayOf(500.0)) + val tensor1 = fromArray(ShapeND(2, 1, 3, 2, 3), DoubleArray(2 * 1 * 3 * 2 * 3) { 0.0 }) + val tensor2 = fromArray(ShapeND(4, 2, 5, 1, 3, 3), DoubleArray(4 * 2 * 5 * 1 * 3 * 3) { 0.0 }) + val tensor3 = fromArray(ShapeND(1, 1), doubleArrayOf(500.0)) val res = broadcastOuterTensors(tensor1, tensor2, tensor3) - assertTrue(res[0].shape contentEquals intArrayOf(4, 2, 5, 3, 2, 3)) - assertTrue(res[1].shape contentEquals intArrayOf(4, 2, 5, 3, 3, 3)) - assertTrue(res[2].shape contentEquals intArrayOf(4, 2, 5, 3, 1, 1)) + assertTrue(res[0].shape contentEquals ShapeND(4, 2, 5, 3, 2, 3)) + assertTrue(res[1].shape contentEquals ShapeND(4, 2, 5, 3, 3, 3)) + assertTrue(res[2].shape contentEquals ShapeND(4, 2, 5, 3, 1, 1)) } @Test fun testMinusTensor() = BroadcastDoubleTensorAlgebra.invoke { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor2 = fromArray(intArrayOf(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) - val tensor3 = fromArray(intArrayOf(1, 1, 1), doubleArrayOf(500.0)) + val tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(1, 3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor3 = fromArray(ShapeND(1, 1, 1), doubleArrayOf(500.0)) val tensor21 = tensor2 - tensor1 val tensor31 = tensor3 - tensor1 val tensor32 = tensor3 - tensor2 - assertTrue(tensor21.shape contentEquals intArrayOf(2, 3)) - assertTrue(tensor21.mutableBuffer.array() contentEquals doubleArrayOf(9.0, 18.0, 27.0, 6.0, 15.0, 24.0)) + assertTrue(tensor21.shape contentEquals ShapeND(2, 3)) + assertTrue(tensor21.source contentEquals doubleArrayOf(9.0, 18.0, 27.0, 6.0, 15.0, 24.0)) - assertTrue(tensor31.shape contentEquals intArrayOf(1, 2, 3)) + assertTrue(tensor31.shape contentEquals ShapeND(1, 2, 3)) assertTrue( - tensor31.mutableBuffer.array() + tensor31.source contentEquals doubleArrayOf(499.0, 498.0, 497.0, 496.0, 495.0, 494.0) ) - assertTrue(tensor32.shape contentEquals intArrayOf(1, 1, 3)) - assertTrue(tensor32.mutableBuffer.array() contentEquals doubleArrayOf(490.0, 480.0, 470.0)) + assertTrue(tensor32.shape contentEquals ShapeND(1, 1, 3)) + assertTrue(tensor32.source contentEquals doubleArrayOf(490.0, 480.0, 470.0)) } } diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleAnalyticTensorAlgebra.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleAnalyticTensorAlgebra.kt index 1e21379b4..e4c2c40ea 100644 --- a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleAnalyticTensorAlgebra.kt +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleAnalyticTensorAlgebra.kt @@ -1,18 +1,20 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core +import space.kscience.kmath.nd.ShapeND import space.kscience.kmath.operations.invoke +import space.kscience.kmath.structures.asBuffer import kotlin.math.* import kotlin.test.Test import kotlin.test.assertTrue internal class TestDoubleAnalyticTensorAlgebra { - val shape = intArrayOf(2, 1, 3, 2) + val shape = ShapeND(2, 1, 3, 2) val buffer = doubleArrayOf( 27.1, 20.0, 19.84, 23.123, 3.0, 2.0, @@ -20,144 +22,160 @@ internal class TestDoubleAnalyticTensorAlgebra { 3.23, 133.7, 25.3, 100.3, 11.0, 12.012 ) - val tensor = DoubleTensor(shape, buffer) + val tensor = DoubleTensor(shape, buffer.asBuffer()) fun DoubleArray.fmap(transform: (Double) -> Double): DoubleArray { return this.map(transform).toDoubleArray() } fun expectedTensor(transform: (Double) -> Double): DoubleTensor { - return DoubleTensor(shape, buffer.fmap(transform)) + return DoubleTensor(shape, buffer.fmap(transform).asBuffer()) } @Test fun testExp() = DoubleTensorAlgebra { - assertTrue { tensor.exp() eq expectedTensor(::exp) } + assertTrue { exp(tensor) eq expectedTensor(::exp) } } @Test fun testLog() = DoubleTensorAlgebra { - assertTrue { tensor.ln() eq expectedTensor(::ln) } + assertTrue { ln(tensor) eq expectedTensor(::ln) } } @Test fun testSqrt() = DoubleTensorAlgebra { - assertTrue { tensor.sqrt() eq expectedTensor(::sqrt) } + assertTrue { sqrt(tensor) eq expectedTensor(::sqrt) } } @Test fun testCos() = DoubleTensorAlgebra { - assertTrue { tensor.cos() eq expectedTensor(::cos) } + assertTrue { cos(tensor) eq expectedTensor(::cos) } } @Test fun testCosh() = DoubleTensorAlgebra { - assertTrue { tensor.cosh() eq expectedTensor(::cosh) } + assertTrue { cosh(tensor) eq expectedTensor(::cosh) } } @Test fun testAcosh() = DoubleTensorAlgebra { - assertTrue { tensor.acosh() eq expectedTensor(::acosh) } + assertTrue { acosh(tensor) eq expectedTensor(::acosh) } } @Test fun testSin() = DoubleTensorAlgebra { - assertTrue { tensor.sin() eq expectedTensor(::sin) } + assertTrue { sin(tensor) eq expectedTensor(::sin) } } @Test fun testSinh() = DoubleTensorAlgebra { - assertTrue { tensor.sinh() eq expectedTensor(::sinh) } + assertTrue { sinh(tensor) eq expectedTensor(::sinh) } } @Test fun testAsinh() = DoubleTensorAlgebra { - assertTrue { tensor.asinh() eq expectedTensor(::asinh) } + assertTrue { asinh(tensor) eq expectedTensor(::asinh) } } @Test fun testTan() = DoubleTensorAlgebra { - assertTrue { tensor.tan() eq expectedTensor(::tan) } + assertTrue { tan(tensor) eq expectedTensor(::tan) } } @Test fun testAtan() = DoubleTensorAlgebra { - assertTrue { tensor.atan() eq expectedTensor(::atan) } + assertTrue { atan(tensor) eq expectedTensor(::atan) } } @Test fun testTanh() = DoubleTensorAlgebra { - assertTrue { tensor.tanh() eq expectedTensor(::tanh) } + assertTrue { tanh(tensor) eq expectedTensor(::tanh) } } @Test fun testCeil() = DoubleTensorAlgebra { - assertTrue { tensor.ceil() eq expectedTensor(::ceil) } + assertTrue { ceil(tensor) eq expectedTensor(::ceil) } } @Test fun testFloor() = DoubleTensorAlgebra { - assertTrue { tensor.floor() eq expectedTensor(::floor) } + assertTrue { floor(tensor) eq expectedTensor(::floor) } } - val shape2 = intArrayOf(2, 2) + val shape2 = ShapeND(2, 2) val buffer2 = doubleArrayOf( 1.0, 2.0, -3.0, 4.0 ) - val tensor2 = DoubleTensor(shape2, buffer2) + val tensor2 = DoubleTensor(shape2, buffer2.asBuffer()) @Test fun testMin() = DoubleTensorAlgebra { assertTrue { tensor2.min() == -3.0 } - assertTrue { tensor2.min(0, true) eq fromArray( - intArrayOf(1, 2), - doubleArrayOf(-3.0, 2.0) - )} - assertTrue { tensor2.min(1, false) eq fromArray( - intArrayOf(2), - doubleArrayOf(1.0, -3.0) - )} + assertTrue { + tensor2.min(0, true) eq fromArray( + ShapeND(1, 2), + doubleArrayOf(-3.0, 2.0) + ) + } + assertTrue { + tensor2.min(1, false) eq fromArray( + ShapeND(2), + doubleArrayOf(1.0, -3.0) + ) + } } @Test fun testMax() = DoubleTensorAlgebra { assertTrue { tensor2.max() == 4.0 } - assertTrue { tensor2.max(0, true) eq fromArray( - intArrayOf(1, 2), - doubleArrayOf(1.0, 4.0) - )} - assertTrue { tensor2.max(1, false) eq fromArray( - intArrayOf(2), - doubleArrayOf(2.0, 4.0) - )} + assertTrue { + tensor2.max(0, true) eq fromArray( + ShapeND(1, 2), + doubleArrayOf(1.0, 4.0) + ) + } + assertTrue { + tensor2.max(1, false) eq fromArray( + ShapeND(2), + doubleArrayOf(2.0, 4.0) + ) + } } @Test fun testSum() = DoubleTensorAlgebra { assertTrue { tensor2.sum() == 4.0 } - assertTrue { tensor2.sum(0, true) eq fromArray( - intArrayOf(1, 2), - doubleArrayOf(-2.0, 6.0) - )} - assertTrue { tensor2.sum(1, false) eq fromArray( - intArrayOf(2), - doubleArrayOf(3.0, 1.0) - )} + assertTrue { + tensor2.sum(0, true) eq fromArray( + ShapeND(1, 2), + doubleArrayOf(-2.0, 6.0) + ) + } + assertTrue { + tensor2.sum(1, false) eq fromArray( + ShapeND(2), + doubleArrayOf(3.0, 1.0) + ) + } } @Test fun testMean() = DoubleTensorAlgebra { - assertTrue { tensor2.mean() == 1.0 } - assertTrue { tensor2.mean(0, true) eq fromArray( - intArrayOf(1, 2), - doubleArrayOf(-1.0, 3.0) - )} - assertTrue { tensor2.mean(1, false) eq fromArray( - intArrayOf(2), - doubleArrayOf(1.5, 0.5) - )} + assertTrue { mean(tensor2) == 1.0 } + assertTrue { + mean(tensor2, 0, true) eq fromArray( + ShapeND(1, 2), + doubleArrayOf(-1.0, 3.0) + ) + } + assertTrue { + mean(tensor2, 1, false) eq fromArray( + ShapeND(2), + doubleArrayOf(1.5, 0.5) + ) + } } } diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleLinearOpsAlgebra.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleLinearOpsAlgebra.kt index e025d4b71..cbd7b9887 100644 --- a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleLinearOpsAlgebra.kt +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleLinearOpsAlgebra.kt @@ -1,12 +1,13 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.contentEquals import space.kscience.kmath.operations.invoke -import space.kscience.kmath.tensors.core.internal.array import space.kscience.kmath.tensors.core.internal.svd1d import kotlin.math.abs import kotlin.test.Test @@ -18,7 +19,7 @@ internal class TestDoubleLinearOpsTensorAlgebra { @Test fun testDetLU() = DoubleTensorAlgebra { val tensor = fromArray( - intArrayOf(2, 2, 2), + ShapeND(2, 2, 2), doubleArrayOf( 1.0, 3.0, 1.0, 2.0, @@ -28,13 +29,13 @@ internal class TestDoubleLinearOpsTensorAlgebra { ) val expectedTensor = fromArray( - intArrayOf(2, 1), + ShapeND(2, 1), doubleArrayOf( -1.0, -7.0 ) ) - val detTensor = tensor.detLU() + val detTensor = detLU(tensor) assertTrue(detTensor.eq(expectedTensor)) @@ -44,7 +45,7 @@ internal class TestDoubleLinearOpsTensorAlgebra { fun testDet() = DoubleTensorAlgebra { val expectedValue = 0.019827417 val m = fromArray( - intArrayOf(3, 3), doubleArrayOf( + ShapeND(3, 3), doubleArrayOf( 2.1843, 1.4391, -0.4845, 1.4391, 1.7772, 0.4055, -0.4845, 0.4055, 0.7519 @@ -58,7 +59,7 @@ internal class TestDoubleLinearOpsTensorAlgebra { fun testDetSingle() = DoubleTensorAlgebra { val expectedValue = 48.151623 val m = fromArray( - intArrayOf(1, 1), doubleArrayOf( + ShapeND(1, 1), doubleArrayOf( expectedValue ) ) @@ -69,7 +70,7 @@ internal class TestDoubleLinearOpsTensorAlgebra { @Test fun testInvLU() = DoubleTensorAlgebra { val tensor = fromArray( - intArrayOf(2, 2, 2), + ShapeND(2, 2, 2), doubleArrayOf( 1.0, 0.0, 0.0, 2.0, @@ -79,7 +80,7 @@ internal class TestDoubleLinearOpsTensorAlgebra { ) val expectedTensor = fromArray( - intArrayOf(2, 2, 2), doubleArrayOf( + ShapeND(2, 2, 2), doubleArrayOf( 1.0, 0.0, 0.0, 0.5, 0.0, 1.0, @@ -87,20 +88,20 @@ internal class TestDoubleLinearOpsTensorAlgebra { ) ) - val invTensor = tensor.invLU() + val invTensor = invLU(tensor) assertTrue(invTensor.eq(expectedTensor)) } @Test fun testScalarProduct() = DoubleTensorAlgebra { - val a = fromArray(intArrayOf(3), doubleArrayOf(1.8, 2.5, 6.8)) - val b = fromArray(intArrayOf(3), doubleArrayOf(5.5, 2.6, 6.4)) + val a = fromArray(ShapeND(3), doubleArrayOf(1.8, 2.5, 6.8)) + val b = fromArray(ShapeND(3), doubleArrayOf(5.5, 2.6, 6.4)) assertEquals(a.dot(b).value(), 59.92) } @Test fun testQR() = DoubleTensorAlgebra { - val shape = intArrayOf(2, 2, 2) + val shape = ShapeND(2, 2, 2) val buffer = doubleArrayOf( 1.0, 3.0, 1.0, 2.0, @@ -110,18 +111,18 @@ internal class TestDoubleLinearOpsTensorAlgebra { val tensor = fromArray(shape, buffer) - val (q, r) = tensor.qr() + val (q, r) = qr(tensor) assertTrue { q.shape contentEquals shape } assertTrue { r.shape contentEquals shape } - assertTrue((q dot r).eq(tensor)) + assertTrue((q matmul r).eq(tensor)) } @Test fun testLU() = DoubleTensorAlgebra { - val shape = intArrayOf(2, 2, 2) + val shape = ShapeND(2, 2, 2) val buffer = doubleArrayOf( 1.0, 3.0, 1.0, 2.0, @@ -130,57 +131,57 @@ internal class TestDoubleLinearOpsTensorAlgebra { ) val tensor = fromArray(shape, buffer) - val (p, l, u) = tensor.lu() + val (p, l, u) = lu(tensor) assertTrue { p.shape contentEquals shape } assertTrue { l.shape contentEquals shape } assertTrue { u.shape contentEquals shape } - assertTrue((p dot tensor).eq(l dot u)) + assertTrue((p matmul tensor).eq(l matmul u)) } @Test fun testCholesky() = DoubleTensorAlgebra { - val tensor = randomNormal(intArrayOf(2, 5, 5), 0) - val sigma = (tensor dot tensor.transpose()) + diagonalEmbedding( - fromArray(intArrayOf(2, 5), DoubleArray(10) { 0.1 }) + val tensor = randomNormal(ShapeND(2, 5, 5), 0) + val sigma = (tensor matmul tensor.transposed()) + diagonalEmbedding( + fromArray(ShapeND(2, 5), DoubleArray(10) { 0.1 }) ) - val low = sigma.cholesky() - val sigmChol = low dot low.transpose() + val low = cholesky(sigma) + val sigmChol = low matmul low.transposed() assertTrue(sigma.eq(sigmChol)) } @Test fun testSVD1D() = DoubleTensorAlgebra { - val tensor2 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) val res = svd1d(tensor2) - assertTrue(res.shape contentEquals intArrayOf(2)) - assertTrue { abs(abs(res.mutableBuffer.array()[res.bufferStart]) - 0.386) < 0.01 } - assertTrue { abs(abs(res.mutableBuffer.array()[res.bufferStart + 1]) - 0.922) < 0.01 } + assertTrue(res.shape contentEquals ShapeND(2)) + assertTrue { abs(abs(res.source[0]) - 0.386) < 0.01 } + assertTrue { abs(abs(res.source[1]) - 0.922) < 0.01 } } @Test - fun testSVD() = DoubleTensorAlgebra{ - testSVDFor(fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0))) - testSVDFor(fromArray(intArrayOf(2, 2), doubleArrayOf(-1.0, 0.0, 239.0, 238.0))) + fun testSVD() = DoubleTensorAlgebra { + testSVDFor(fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0))) + testSVDFor(fromArray(ShapeND(2, 2), doubleArrayOf(-1.0, 0.0, 239.0, 238.0))) } @Test fun testBatchedSVD() = DoubleTensorAlgebra { - val tensor = randomNormal(intArrayOf(2, 5, 3), 0) - val (tensorU, tensorS, tensorV) = tensor.svd() - val tensorSVD = tensorU dot (diagonalEmbedding(tensorS) dot tensorV.transpose()) + val tensor = randomNormal(ShapeND(2, 5, 3), 0) + val (tensorU, tensorS, tensorV) = svd(tensor) + val tensorSVD = tensorU matmul (diagonalEmbedding(tensorS) matmul tensorV.transposed()) assertTrue(tensor.eq(tensorSVD)) } @Test fun testBatchedSymEig() = DoubleTensorAlgebra { - val tensor = randomNormal(shape = intArrayOf(2, 3, 3), 0) - val tensorSigma = tensor + tensor.transpose() - val (tensorS, tensorV) = tensorSigma.symEig() - val tensorSigmaCalc = tensorV dot (diagonalEmbedding(tensorS) dot tensorV.transpose()) + val tensor = randomNormal(shape = ShapeND(2, 3, 3), 0) + val tensorSigma = tensor + tensor.transposed() + val (tensorS, tensorV) = symEig(tensorSigma) + val tensorSigmaCalc = tensorV matmul (diagonalEmbedding(tensorS) matmul tensorV.transposed()) assertTrue(tensorSigma.eq(tensorSigmaCalc)) } @@ -189,12 +190,12 @@ internal class TestDoubleLinearOpsTensorAlgebra { private fun DoubleTensorAlgebra.testSVDFor(tensor: DoubleTensor, epsilon: Double = 1e-10) { - val svd = tensor.svd() + val svd = svd(tensor) val tensorSVD = svd.first .dot( diagonalEmbedding(svd.second) - .dot(svd.third.transpose()) + .dot(svd.third.transposed()) ) assertTrue(tensor.eq(tensorSVD, epsilon)) diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensor.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensor.kt index d808637c7..811fc1117 100644 --- a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensor.kt +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestDoubleTensor.kt @@ -1,52 +1,49 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DefaultStrides -import space.kscience.kmath.nd.MutableBufferND -import space.kscience.kmath.nd.as1D -import space.kscience.kmath.nd.as2D +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.invoke import space.kscience.kmath.structures.DoubleBuffer import space.kscience.kmath.structures.toDoubleArray -import space.kscience.kmath.tensors.core.internal.array -import space.kscience.kmath.tensors.core.internal.asTensor import space.kscience.kmath.tensors.core.internal.matrixSequence -import space.kscience.kmath.tensors.core.internal.toBufferedTensor +import space.kscience.kmath.testutils.assertBufferEquals import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue +@OptIn(PerformancePitfall::class) internal class TestDoubleTensor { @Test fun testValue() = DoubleTensorAlgebra { val value = 12.5 - val tensor = fromArray(intArrayOf(1), doubleArrayOf(value)) + val tensor = fromArray(ShapeND(1), doubleArrayOf(value)) assertEquals(tensor.value(), value) } @OptIn(PerformancePitfall::class) @Test fun testStrides() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(2, 2), doubleArrayOf(3.5, 5.8, 58.4, 2.4)) + val tensor = fromArray(ShapeND(2, 2), doubleArrayOf(3.5, 5.8, 58.4, 2.4)) assertEquals(tensor[intArrayOf(0, 1)], 5.8) assertTrue( - tensor.elements().map { it.second }.toList().toDoubleArray() contentEquals tensor.mutableBuffer.toDoubleArray() + tensor.elements().map { it.second }.toList() + .toDoubleArray() contentEquals tensor.source.toDoubleArray() ) } @Test fun testGet() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(1, 2, 2), doubleArrayOf(3.5, 5.8, 58.4, 2.4)) - val matrix = tensor[0].as2D() + val tensor = fromArray(ShapeND(1, 2, 2), doubleArrayOf(3.5, 5.8, 58.4, 2.4)) + val matrix = tensor.getTensor(0).asDoubleTensor2D() assertEquals(matrix[0, 1], 5.8) - val vector = tensor[0][1].as1D() + val vector = tensor.getTensor(0, 1).as1D() assertEquals(vector[0], 58.4) matrix[0, 1] = 77.89 @@ -56,9 +53,9 @@ internal class TestDoubleTensor { assertEquals(tensor[intArrayOf(0, 1, 0)], 109.56) tensor.matrixSequence().forEach { - val a = it.asTensor() - val secondRow = a[1].as1D() - val secondColumn = a.transpose(0, 1)[1].as1D() + val a = it.asDoubleTensor() + val secondRow = a.getTensor(1).asDoubleBuffer() + val secondColumn = a.transposed(0, 1).getTensor(1).asDoubleBuffer() assertEquals(secondColumn[0], 77.89) assertEquals(secondRow[1], secondColumn[1]) } @@ -68,29 +65,46 @@ internal class TestDoubleTensor { fun testNoBufferProtocol() { // create buffer - val doubleArray = DoubleBuffer(doubleArrayOf(1.0, 2.0, 3.0)) + val doubleArray = DoubleBuffer(1.0, 2.0, 3.0) // create ND buffers, no data is copied - val ndArray = MutableBufferND(DefaultStrides(intArrayOf(3)), doubleArray) + val ndArray: MutableBufferND = DoubleBufferND(ColumnStrides(ShapeND(3)), doubleArray) // map to tensors - val bufferedTensorArray = ndArray.toBufferedTensor() // strides are flipped so data copied - val tensorArray = bufferedTensorArray.asTensor() // data not contiguous so copied again + val tensorArray = ndArray.asDoubleTensor() // Data is copied because of strides change. - val tensorArrayPublic = ndArray.toDoubleTensor() // public API, data copied twice - val sharedTensorArray = tensorArrayPublic.toDoubleTensor() // no data copied by matching type + //protective copy + val tensorArrayPublic = ndArray.copyToTensor() // public API, data copied twice + val sharedTensorArray = tensorArrayPublic.asDoubleTensor() // no data copied by matching type - assertTrue(tensorArray.mutableBuffer.array() contentEquals sharedTensorArray.mutableBuffer.array()) + assertTrue(tensorArray.source contentEquals sharedTensorArray.source) tensorArray[intArrayOf(0)] = 55.9 assertEquals(tensorArrayPublic[intArrayOf(0)], 1.0) - tensorArrayPublic[intArrayOf(0)] = 55.9 - assertEquals(sharedTensorArray[intArrayOf(0)], 55.9) - assertEquals(bufferedTensorArray[intArrayOf(0)], 1.0) + tensorArrayPublic[intArrayOf(0)] = 57.9 + assertEquals(sharedTensorArray[intArrayOf(0)], 57.9) + assertEquals(tensorArray[intArrayOf(0)], 55.9) - bufferedTensorArray[intArrayOf(0)] = 55.9 + tensorArray[intArrayOf(0)] = 55.9 assertEquals(ndArray[intArrayOf(0)], 1.0) + } + @Test + fun test2D() = with(DoubleTensorAlgebra) { + val tensor: DoubleTensor = structureND(ShapeND(3, 3)) { (i, j) -> (i - j).toDouble() } + //println(tensor.toPrettyString()) + val tensor2d = tensor.asDoubleTensor2D() + assertBufferEquals(DoubleBuffer(1.0, 0.0, -1.0), tensor2d.rows[1]) + assertBufferEquals(DoubleBuffer(-2.0, -1.0, 0.0), tensor2d.columns[2]) + } + + @Test + fun testMatrixIteration() = with(DoubleTensorAlgebra) { + val tensor = structureND(ShapeND(3, 3, 3, 3)) { index -> index.sum().toDouble() } + tensor.forEachMatrix { index, matrix -> + println(index.joinToString { it.toString() }) + println(matrix) + } } } 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 205ae2fee..7222fc7a6 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 @@ -1,14 +1,16 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.tensors.core +import space.kscience.kmath.nd.* import space.kscience.kmath.operations.invoke -import space.kscience.kmath.tensors.core.internal.array +import space.kscience.kmath.testutils.assertBufferEquals import kotlin.test.Test +import kotlin.test.assertEquals import kotlin.test.assertFalse import kotlin.test.assertTrue @@ -16,62 +18,62 @@ internal class TestDoubleTensorAlgebra { @Test fun testDoublePlus() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(2), doubleArrayOf(1.0, 2.0)) + val tensor = fromArray(ShapeND(2), doubleArrayOf(1.0, 2.0)) val res = 10.0 + tensor - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(11.0, 12.0)) + assertTrue(res.source contentEquals doubleArrayOf(11.0, 12.0)) } @Test fun testDoubleDiv() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(2), doubleArrayOf(2.0, 4.0)) - val res = 2.0/tensor - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(1.0, 0.5)) + val tensor = fromArray(ShapeND(2), doubleArrayOf(2.0, 4.0)) + val res = 2.0 / tensor + assertTrue(res.source contentEquals doubleArrayOf(1.0, 0.5)) } @Test fun testDivDouble() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(2), doubleArrayOf(10.0, 5.0)) + val tensor = fromArray(ShapeND(2), doubleArrayOf(10.0, 5.0)) val res = tensor / 2.5 - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(4.0, 2.0)) + assertTrue(res.source contentEquals doubleArrayOf(4.0, 2.0)) } @Test fun testTranspose1x1() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(1), doubleArrayOf(0.0)) - val res = tensor.transpose(0, 0) + val tensor = fromArray(ShapeND(1), doubleArrayOf(0.0)) + val res = tensor.transposed(0, 0) - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(0.0)) - assertTrue(res.shape contentEquals intArrayOf(1)) + assertTrue(res.asDoubleTensor().source contentEquals doubleArrayOf(0.0)) + assertTrue(res.shape contentEquals ShapeND(1)) } @Test fun testTranspose3x2() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(3, 2), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val res = tensor.transpose(1, 0) + val tensor = fromArray(ShapeND(3, 2), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val res = tensor.transposed(1, 0) - assertTrue(res.mutableBuffer.array() contentEquals doubleArrayOf(1.0, 3.0, 5.0, 2.0, 4.0, 6.0)) - assertTrue(res.shape contentEquals intArrayOf(2, 3)) + assertTrue(res.asDoubleTensor().source contentEquals doubleArrayOf(1.0, 3.0, 5.0, 2.0, 4.0, 6.0)) + assertTrue(res.shape contentEquals ShapeND(2, 3)) } @Test fun testTranspose1x2x3() = DoubleTensorAlgebra { - val tensor = fromArray(intArrayOf(1, 2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val res01 = tensor.transpose(0, 1) - val res02 = tensor.transpose(-3, 2) - val res12 = tensor.transpose() - - assertTrue(res01.shape contentEquals intArrayOf(2, 1, 3)) - assertTrue(res02.shape contentEquals intArrayOf(3, 2, 1)) - assertTrue(res12.shape contentEquals intArrayOf(1, 3, 2)) - - assertTrue(res01.mutableBuffer.array() contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - assertTrue(res02.mutableBuffer.array() contentEquals doubleArrayOf(1.0, 4.0, 2.0, 5.0, 3.0, 6.0)) - assertTrue(res12.mutableBuffer.array() contentEquals doubleArrayOf(1.0, 4.0, 2.0, 5.0, 3.0, 6.0)) + val tensor = fromArray(ShapeND(1, 2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val res01 = tensor.transposed(0, 1) + val res02 = tensor.transposed(-3, 2) + val res12 = tensor.transposed() + + assertTrue(res01.shape contentEquals ShapeND(2, 1, 3)) + assertTrue(res02.shape contentEquals ShapeND(3, 2, 1)) + assertTrue(res12.shape contentEquals ShapeND(1, 3, 2)) + + assertTrue(res01.asDoubleTensor().source contentEquals doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + assertTrue(res02.asDoubleTensor().source contentEquals doubleArrayOf(1.0, 4.0, 2.0, 5.0, 3.0, 6.0)) + assertTrue(res12.asDoubleTensor().source contentEquals doubleArrayOf(1.0, 4.0, 2.0, 5.0, 3.0, 6.0)) } @Test fun testLinearStructure() = DoubleTensorAlgebra { - val shape = intArrayOf(3) + val shape = ShapeND(3) val tensorA = full(value = -4.5, shape = shape) val tensorB = full(value = 10.9, shape = shape) val tensorC = full(value = 789.3, shape = shape) @@ -97,85 +99,110 @@ internal class TestDoubleTensorAlgebra { assignResult += tensorC assignResult += -39.4 - assertTrue(expected.mutableBuffer.array() contentEquals result.mutableBuffer.array()) - assertTrue(expected.mutableBuffer.array() contentEquals assignResult.mutableBuffer.array()) + assertBufferEquals(expected.source, result.source) + assertBufferEquals(expected.source, assignResult.source) } @Test fun testDot() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - 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 tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor11 = fromArray(ShapeND(3, 2), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor3 = fromArray(ShapeND(1, 1, 3), doubleArrayOf(-1.0, -2.0, -3.0)) + val tensor4 = fromArray(ShapeND(2, 3, 3), (1..18).map { it.toDouble() }.toDoubleArray()) + val tensor5 = fromArray(ShapeND(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)) - assertTrue(res12.shape contentEquals intArrayOf(2)) + assertTrue(res12.source contentEquals doubleArrayOf(140.0, 320.0)) + assertTrue(res12.shape contentEquals ShapeND(2)) - val res32 = tensor3.dot(tensor2) - assertTrue(res32.mutableBuffer.array() contentEquals doubleArrayOf(-140.0)) - assertTrue(res32.shape contentEquals intArrayOf(1, 1)) + val res32 = tensor3.matmul(tensor2) + assertTrue(res32.source contentEquals doubleArrayOf(-140.0)) + assertTrue(res32.shape contentEquals ShapeND(1, 1)) val res22 = tensor2.dot(tensor2) - assertTrue(res22.mutableBuffer.array() contentEquals doubleArrayOf(1400.0)) - assertTrue(res22.shape contentEquals intArrayOf(1)) + assertTrue(res22.source contentEquals doubleArrayOf(1400.0)) + assertTrue(res22.shape contentEquals ShapeND(1)) 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)) + assertTrue(res11.source contentEquals doubleArrayOf(22.0, 28.0, 49.0, 64.0)) + assertTrue(res11.shape contentEquals ShapeND(2, 2)) + + val res45 = tensor4.matmul(tensor5) + assertTrue( + res45.source 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 ShapeND(2, 3, 3)) } @Test fun testDiagonalEmbedding() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(3), doubleArrayOf(10.0, 20.0, 30.0)) - val tensor2 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor3 = zeros(intArrayOf(2, 3, 4, 5)) + val tensor1 = fromArray(ShapeND(3), doubleArrayOf(10.0, 20.0, 30.0)) + val tensor2 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor3 = zeros(ShapeND(2, 3, 4, 5)) - assertTrue(diagonalEmbedding(tensor3, 0, 3, 4).shape contentEquals - intArrayOf(2, 3, 4, 5, 5)) - assertTrue(diagonalEmbedding(tensor3, 1, 3, 4).shape contentEquals - intArrayOf(2, 3, 4, 6, 6)) - assertTrue(diagonalEmbedding(tensor3, 2, 0, 3).shape contentEquals - intArrayOf(7, 2, 3, 7, 4)) + assertTrue( + diagonalEmbedding(tensor3, 0, 3, 4).shape contentEquals + ShapeND(2, 3, 4, 5, 5) + ) + assertTrue( + diagonalEmbedding(tensor3, 1, 3, 4).shape contentEquals + ShapeND(2, 3, 4, 6, 6) + ) + assertTrue( + diagonalEmbedding(tensor3, 2, 0, 3).shape contentEquals + ShapeND(7, 2, 3, 7, 4) + ) val diagonal1 = diagonalEmbedding(tensor1, 0, 1, 0) - assertTrue(diagonal1.shape contentEquals intArrayOf(3, 3)) - assertTrue(diagonal1.mutableBuffer.array() contentEquals - doubleArrayOf(10.0, 0.0, 0.0, 0.0, 20.0, 0.0, 0.0, 0.0, 30.0)) + assertTrue(diagonal1.shape contentEquals ShapeND(3, 3)) + assertTrue( + diagonal1.source contentEquals + doubleArrayOf(10.0, 0.0, 0.0, 0.0, 20.0, 0.0, 0.0, 0.0, 30.0) + ) val diagonal1Offset = diagonalEmbedding(tensor1, 1, 1, 0) - assertTrue(diagonal1Offset.shape contentEquals intArrayOf(4, 4)) - assertTrue(diagonal1Offset.mutableBuffer.array() contentEquals - doubleArrayOf(0.0, 0.0, 0.0, 0.0, 10.0, 0.0, 0.0, 0.0, 0.0, 20.0, 0.0, 0.0, 0.0, 0.0, 30.0, 0.0)) + assertTrue(diagonal1Offset.shape contentEquals ShapeND(4, 4)) + assertTrue( + diagonal1Offset.source contentEquals + doubleArrayOf(0.0, 0.0, 0.0, 0.0, 10.0, 0.0, 0.0, 0.0, 0.0, 20.0, 0.0, 0.0, 0.0, 0.0, 30.0, 0.0) + ) val diagonal2 = diagonalEmbedding(tensor2, 1, 0, 2) - assertTrue(diagonal2.shape contentEquals intArrayOf(4, 2, 4)) - assertTrue(diagonal2.mutableBuffer.array() contentEquals - doubleArrayOf( - 0.0, 1.0, 0.0, 0.0, 0.0, 4.0, 0.0, 0.0, - 0.0, 0.0, 2.0, 0.0, 0.0, 0.0, 5.0, 0.0, - 0.0, 0.0, 0.0, 3.0, 0.0, 0.0, 0.0, 6.0, - 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0)) + assertTrue(diagonal2.shape contentEquals ShapeND(4, 2, 4)) + assertTrue( + diagonal2.source contentEquals + doubleArrayOf( + 0.0, 1.0, 0.0, 0.0, 0.0, 4.0, 0.0, 0.0, + 0.0, 0.0, 2.0, 0.0, 0.0, 0.0, 5.0, 0.0, + 0.0, 0.0, 0.0, 3.0, 0.0, 0.0, 0.0, 6.0, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + ) + ) } @Test fun testEq() = DoubleTensorAlgebra { - val tensor1 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor2 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) - val tensor3 = fromArray(intArrayOf(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 5.0)) + val tensor1 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor2 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 6.0)) + val tensor3 = fromArray(ShapeND(2, 3), doubleArrayOf(1.0, 2.0, 3.0, 4.0, 5.0, 5.0)) assertTrue(tensor1 eq tensor1) assertTrue(tensor1 eq tensor2) assertFalse(tensor1.eq(tensor3)) } + + @Test + fun testMap() = DoubleTensorAlgebra { + val tensor = one(5, 5, 5) + val l = tensor.getTensor(0).map { it + 1.0 } + val r = tensor.getTensor(1).map { it - 1.0 } + val res = l + r + assertTrue { ShapeND(5, 5) contentEquals res.shape } + assertEquals(2.0, res[4, 4]) + } } diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestLmAlgorithm.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestLmAlgorithm.kt new file mode 100644 index 000000000..4b031eb11 --- /dev/null +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/TestLmAlgorithm.kt @@ -0,0 +1,280 @@ +/* + * Copyright 2018-2023 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.tensors.core + +import space.kscience.kmath.nd.MutableStructure2D +import space.kscience.kmath.nd.ShapeND +import space.kscience.kmath.nd.as2D +import space.kscience.kmath.nd.component1 +import space.kscience.kmath.operations.invoke +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.max +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.plus +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.pow +import space.kscience.kmath.tensors.core.DoubleTensorAlgebra.Companion.times +import kotlin.math.roundToLong +import kotlin.test.Test +import kotlin.test.assertEquals + +class TestLmAlgorithm { + companion object { + fun funcEasyForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var yHat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(m, 1))) + + if (exampleNumber == 1) { + yHat = DoubleTensorAlgebra.exp((t.times(-1.0 / p[1, 0]))).times(p[0, 0]) + t.times(p[2, 0]).times( + DoubleTensorAlgebra.exp((t.times(-1.0 / p[3, 0]))) + ) + } + else if (exampleNumber == 2) { + val mt = t.max() + yHat = (t.times(1.0 / mt)).times(p[0, 0]) + + (t.times(1.0 / mt)).pow(2).times(p[1, 0]) + + (t.times(1.0 / mt)).pow(3).times(p[2, 0]) + + (t.times(1.0 / mt)).pow(4).times(p[3, 0]) + } + else if (exampleNumber == 3) { + yHat = DoubleTensorAlgebra.exp((t.times(-1.0 / p[1, 0]))) + .times(p[0, 0]) + DoubleTensorAlgebra.sin((t.times(1.0 / p[3, 0]))).times(p[2, 0]) + } + + return yHat.as2D() + } + + fun funcMiddleForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var yHat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf (m, 1))) + + val mt = t.max() + for(i in 0 until p.shape.component1()){ + yHat += (t.times(1.0 / mt)).times(p[i, 0]) + } + + for(i in 0 until 5){ + yHat = funcEasyForLm(yHat.as2D(), p, exampleNumber).asDoubleTensor() + } + + return yHat.as2D() + } + + fun funcDifficultForLm(t: MutableStructure2D, p: MutableStructure2D, exampleNumber: Int): MutableStructure2D { + val m = t.shape.component1() + var yHat = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf (m, 1))) + + val mt = t.max() + for(i in 0 until p.shape.component1()){ + yHat = yHat.plus( (t.times(1.0 / mt)).times(p[i, 0]) ) + } + + for(i in 0 until 4){ + yHat = funcEasyForLm((yHat.as2D() + t).as2D(), p, exampleNumber).asDoubleTensor() + } + + return yHat.as2D() + } + } + @Test + fun testLMEasy() = DoubleTensorAlgebra { + val lmMatxYDat = doubleArrayOf( + 19.6594, 18.6096, 17.6792, 17.2747, 16.3065, 17.1458, 16.0467, 16.7023, 15.7809, 15.9807, + 14.7620, 15.1128, 16.0973, 15.1934, 15.8636, 15.4763, 15.6860, 15.1895, 15.3495, 16.6054, + 16.2247, 15.9854, 16.1421, 17.0960, 16.7769, 17.1997, 17.2767, 17.5882, 17.5378, 16.7894, + 17.7648, 18.2512, 18.1581, 16.7037, 17.8475, 17.9081, 18.3067, 17.9632, 18.2817, 19.1427, + 18.8130, 18.5658, 18.0056, 18.4607, 18.5918, 18.2544, 18.3731, 18.7511, 19.3181, 17.3066, + 17.9632, 19.0513, 18.7528, 18.2928, 18.5967, 17.8567, 17.7859, 18.4016, 18.9423, 18.4959, + 17.8000, 18.4251, 17.7829, 17.4645, 17.5221, 17.3517, 17.4637, 17.7563, 16.8471, 17.4558, + 17.7447, 17.1487, 17.3183, 16.8312, 17.7551, 17.0942, 15.6093, 16.4163, 15.3755, 16.6725, + 16.2332, 16.2316, 16.2236, 16.5361, 15.3721, 15.3347, 15.5815, 15.6319, 14.4538, 14.6044, + 14.7665, 13.3718, 15.0587, 13.8320, 14.7873, 13.6824, 14.2579, 14.2154, 13.5818, 13.8157 + ) + + var exampleNumber = 1 + val p_init = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(5.0, 2.0, 0.2, 10.0) + ).as2D() + + var t = ones(ShapeND(intArrayOf(100, 1))).as2D() + for (i in 0 until 100) { + t[i, 0] = t[i, 0] * (i + 1) + } + + val yDat = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(100, 1)), lmMatxYDat + ).as2D() + + val weight = 4.0 + + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + + val pMin = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(-50.0, -20.0, -2.0, -100.0) + ).as2D() + + val pMax = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(50.0, 20.0, 2.0, 100.0) + ).as2D() + + val inputData = LMInput(::funcEasyForLm, p_init, t, yDat, weight, dp, pMin, pMax, 100, + doubleArrayOf(1e-3, 1e-3, 1e-1, 1e-1), doubleArrayOf(1e-2, 11.0, 9.0), 1, 10, exampleNumber) + + val result = levenbergMarquardt(inputData) + assertEquals(13, result.iterations) + assertEquals(31, result.funcCalls) + assertEquals(0.9131368192633, (result.resultChiSq * 1e13).roundToLong() / 1e13) + assertEquals(3.7790980 * 1e-7, (result.resultLambda * 1e13).roundToLong() / 1e13) + assertEquals(result.typeOfConvergence, TypeOfConvergence.InParameters) + val expectedParameters = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(20.527230909086, 9.833627103230, 0.997571256572, 50.174445822506) + ).as2D() + result.resultParameters = result.resultParameters.map { x -> (x * 1e12).toLong() / 1e12}.as2D() + val receivedParameters = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(4, 1)), doubleArrayOf(result.resultParameters[0, 0], result.resultParameters[1, 0], + result.resultParameters[2, 0], result.resultParameters[3, 0]) + ).as2D() + assertEquals(expectedParameters[0, 0], receivedParameters[0, 0]) + assertEquals(expectedParameters[1, 0], receivedParameters[1, 0]) + assertEquals(expectedParameters[2, 0], receivedParameters[2, 0]) + assertEquals(expectedParameters[3, 0], receivedParameters[3, 0]) + } + + @Test + fun TestLMMiddle() = DoubleTensorAlgebra { + val NData = 100 + val tExample = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + tExample[i, 0] = tExample[i, 0] * (i + 1) + } + + val Nparams = 20 + val pExample = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + pExample[i, 0] = pExample[i, 0] + i - 25 + } + + val exampleNumber = 1 + + val yHat = funcMiddleForLm(tExample, pExample, exampleNumber) + + val pInit = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + pInit[i, 0] = (pExample[i, 0] + 0.9) + } + + val t = tExample + val yDat = yHat + val weight = 1.0 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var pMin = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + pMin = pMin.div(1.0 / -50.0) + val pMax = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + pMin = pMin.div(1.0 / 50.0) + val opts = doubleArrayOf(3.0, 7000.0, 1e-5, 1e-5, 1e-5, 1e-5, 1e-5, 11.0, 9.0, 1.0) + + val inputData = LMInput(::funcMiddleForLm, + pInit.as2D(), + t, + yDat, + weight, + dp, + pMin.as2D(), + pMax.as2D(), + opts[1].toInt(), + doubleArrayOf(opts[2], opts[3], opts[4], opts[5]), + doubleArrayOf(opts[6], opts[7], opts[8]), + opts[9].toInt(), + 10, + 1) + + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + + assertEquals(46, result.iterations) + assertEquals(113, result.funcCalls) + assertEquals(0.000005977, (result.resultChiSq * 1e9).roundToLong() / 1e9) + assertEquals(1.0 * 1e-7, (result.resultLambda * 1e13).roundToLong() / 1e13) + assertEquals(result.typeOfConvergence, TypeOfConvergence.InReducedChiSquare) + val expectedParameters = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(Nparams, 1)), doubleArrayOf( -23.9717, -18.6686, -21.7971, + -20.9681, -22.086, -20.5859, -19.0384, -17.4957, -15.9991, -14.576, -13.2441, - + 12.0201, -10.9256, -9.9878, -9.2309, -8.6589, -8.2365, -7.8783, -7.4598, -6.8511)).as2D() + result.resultParameters = result.resultParameters.map { x -> (x * 1e4).roundToLong() / 1e4}.as2D() + val receivedParameters = zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + receivedParameters[i, 0] = result.resultParameters[i, 0] + assertEquals(expectedParameters[i, 0], result.resultParameters[i, 0]) + } + } + + @Test + fun TestLMDifficult() = DoubleTensorAlgebra { + val NData = 200 + var tExample = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(NData, 1))).as2D() + for (i in 0 until NData) { + tExample[i, 0] = tExample[i, 0] * (i + 1) - 104 + } + + val Nparams = 15 + var pExample = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + pExample[i, 0] = pExample[i, 0] + i - 25 + } + + val exampleNumber = 1 + + var yHat = funcDifficultForLm(tExample, pExample, exampleNumber) + + var pInit = DoubleTensorAlgebra.zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + pInit[i, 0] = (pExample[i, 0] + 0.9) + } + + var t = tExample + val yDat = yHat + val weight = 1.0 / Nparams * 1.0 - 0.085 + val dp = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(1, 1)), DoubleArray(1) { -0.01 } + ).as2D() + var pMin = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + pMin = pMin.div(1.0 / -50.0) + val pMax = DoubleTensorAlgebra.ones(ShapeND(intArrayOf(Nparams, 1))) + pMin = pMin.div(1.0 / 50.0) + val opts = doubleArrayOf(3.0, 7000.0, 1e-2, 1e-3, 1e-2, 1e-2, 1e-2, 11.0, 9.0, 1.0) + + val inputData = LMInput(::funcDifficultForLm, + pInit.as2D(), + t, + yDat, + weight, + dp, + pMin.as2D(), + pMax.as2D(), + opts[1].toInt(), + doubleArrayOf(opts[2], opts[3], opts[4], opts[5]), + doubleArrayOf(opts[6], opts[7], opts[8]), + opts[9].toInt(), + 10, + 1) + + val result = DoubleTensorAlgebra.levenbergMarquardt(inputData) + + assertEquals(2375, result.iterations) + assertEquals(4858, result.funcCalls) + assertEquals(5.14347, (result.resultLambda * 1e5).roundToLong() / 1e5) + assertEquals(result.typeOfConvergence, TypeOfConvergence.InParameters) + val expectedParameters = BroadcastDoubleTensorAlgebra.fromArray( + ShapeND(intArrayOf(Nparams, 1)), doubleArrayOf(-23.6412, -16.7402, -21.5705, -21.0464, + -17.2852, -17.2959, -17.298, 0.9999, -17.2885, -17.3008, -17.2941, -17.2923, -17.2976, -17.3028, -17.2891)).as2D() + result.resultParameters = result.resultParameters.map { x -> (x * 1e4).roundToLong() / 1e4}.as2D() + val receivedParameters = zeros(ShapeND(intArrayOf(Nparams, 1))).as2D() + for (i in 0 until Nparams) { + receivedParameters[i, 0] = result.resultParameters[i, 0] + assertEquals(expectedParameters[i, 0], result.resultParameters[i, 0]) + } + } +} \ No newline at end of file diff --git a/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/offsetBufferEquality.kt b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/offsetBufferEquality.kt new file mode 100644 index 000000000..e9fc7fb9c --- /dev/null +++ b/kmath-tensors/src/commonTest/kotlin/space/kscience/kmath/tensors/core/offsetBufferEquality.kt @@ -0,0 +1,24 @@ +/* + * Copyright 2018-2022 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.tensors.core + +import space.kscience.kmath.structures.Buffer +import space.kscience.kmath.structures.DoubleBuffer +import space.kscience.kmath.structures.indices +import kotlin.jvm.JvmName + + +/** + * Simplified [DoubleBuffer] to array comparison + */ +public fun OffsetDoubleBuffer.contentEquals(vararg doubles: Double): Boolean = indices.all { get(it) == doubles[it] } + +@JvmName("contentEqualsArray") +public infix fun OffsetDoubleBuffer.contentEquals(otherArray: DoubleArray): Boolean = contentEquals(*otherArray) + +@JvmName("contentEqualsBuffer") +public infix fun OffsetDoubleBuffer.contentEquals(otherBuffer: Buffer): Boolean = + indices.all { get(it) == otherBuffer[it] } \ No newline at end of file diff --git a/kmath-trajectory/README.md b/kmath-trajectory/README.md deleted file mode 100644 index ac2930b04..000000000 --- a/kmath-trajectory/README.md +++ /dev/null @@ -1,34 +0,0 @@ -# kmath-trajectory - - - - -## Artifact: - -The Maven coordinates of this project are `space.kscience:kmath-trajectory:0.3.1-dev-1`. - -**Gradle Groovy:** -```groovy -repositories { - maven { url 'https://repo.kotlin.link' } - mavenCentral() -} - -dependencies { - implementation 'space.kscience:kmath-trajectory:0.3.1-dev-1' -} -``` -**Gradle Kotlin DSL:** -```kotlin -repositories { - maven("https://repo.kotlin.link") - mavenCentral() -} - -dependencies { - implementation("space.kscience:kmath-trajectory:0.3.1-dev-1") -} -``` - -## Contributors -Erik Schouten (github: @ESchouten, email: erik-schouten@hotmail.nl) diff --git a/kmath-trajectory/build.gradle.kts b/kmath-trajectory/build.gradle.kts deleted file mode 100644 index db80be02a..000000000 --- a/kmath-trajectory/build.gradle.kts +++ /dev/null @@ -1,17 +0,0 @@ -plugins { - kotlin("multiplatform") - id("ru.mipt.npm.gradle.common") - id("ru.mipt.npm.gradle.native") -} - -kotlin.sourceSets.commonMain { - dependencies { - api(projects.kmath.kmathGeometry) - } -} - -readme { - description = "Path and trajectory optimization" - maturity = ru.mipt.npm.gradle.Maturity.PROTOTYPE - propertyByTemplate("artifact", rootProject.file("docs/templates/ARTIFACT-TEMPLATE.md")) -} diff --git a/kmath-trajectory/docs/README-TEMPLATE.md b/kmath-trajectory/docs/README-TEMPLATE.md deleted file mode 100644 index eb8e4a0c0..000000000 --- a/kmath-trajectory/docs/README-TEMPLATE.md +++ /dev/null @@ -1,13 +0,0 @@ -# kmath-trajectory - - -${features} - -${artifact} - -## Author -Erik Schouten - -Github: ESchouten - -Email: erik-schouten@hotmail.nl diff --git a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/DubinsPath.kt b/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/DubinsPath.kt deleted file mode 100644 index 134342b33..000000000 --- a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/DubinsPath.kt +++ /dev/null @@ -1,193 +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.trajectory - -import space.kscience.kmath.geometry.Circle2D -import space.kscience.kmath.geometry.Euclidean2DSpace.distanceTo -import space.kscience.kmath.geometry.Vector2D -import kotlin.math.PI -import kotlin.math.acos -import kotlin.math.cos -import kotlin.math.sin - -internal fun Pose2D.getLeftCircle(radius: Double): Circle2D = getTangentCircles(radius).first - -internal fun Pose2D.getRightCircle(radius: Double): Circle2D = getTangentCircles(radius).second - -internal fun Pose2D.getTangentCircles(radius: Double): Pair { - val dX = radius * cos(theta) - val dY = radius * sin(theta) - return Circle2D(Vector2D(x - dX, y + dY), radius) to Circle2D(Vector2D(x + dX, y - dY), radius) -} - -internal fun leftOuterTangent(a: Circle2D, b: Circle2D): StraightSegment = outerTangent(a, b, ArcSegment.Direction.LEFT) - -internal fun rightOuterTangent(a: Circle2D, b: Circle2D): StraightSegment = outerTangent(a, b, - ArcSegment.Direction.RIGHT -) - -private fun outerTangent(a: Circle2D, b: Circle2D, side: ArcSegment.Direction): StraightSegment { - val centers = StraightSegment(a.center, b.center) - val p1 = when (side) { - ArcSegment.Direction.LEFT -> Vector2D( - a.center.x - a.radius * cos(centers.theta), - a.center.y + a.radius * sin(centers.theta) - ) - ArcSegment.Direction.RIGHT -> Vector2D( - a.center.x + a.radius * cos(centers.theta), - a.center.y - a.radius * sin(centers.theta) - ) - } - return StraightSegment( - p1, - Vector2D(p1.x + (centers.end.x - centers.start.x), p1.y + (centers.end.y - centers.start.y)) - ) -} - -internal fun leftInnerTangent(base: Circle2D, direction: Circle2D): StraightSegment? = - innerTangent(base, direction, ArcSegment.Direction.LEFT) - -internal fun rightInnerTangent(base: Circle2D, direction: Circle2D): StraightSegment? = - innerTangent(base, direction, ArcSegment.Direction.RIGHT) - -private fun innerTangent(base: Circle2D, direction: Circle2D, side: ArcSegment.Direction): StraightSegment? { - val centers = StraightSegment(base.center, direction.center) - if (centers.length < base.radius * 2) return null - val angle = theta( - when (side) { - ArcSegment.Direction.LEFT -> centers.theta + acos(base.radius * 2 / centers.length) - ArcSegment.Direction.RIGHT -> centers.theta - acos(base.radius * 2 / centers.length) - } - ) - val dX = base.radius * sin(angle) - val dY = base.radius * cos(angle) - val p1 = Vector2D(base.center.x + dX, base.center.y + dY) - val p2 = Vector2D(direction.center.x - dX, direction.center.y - dY) - return StraightSegment(p1, p2) -} - -internal fun theta(theta: Double): Double = (theta + (2 * PI)) % (2 * PI) - -public class DubinsPath( - public val a: ArcSegment, - public val b: Trajectory, - public val c: ArcSegment, -) : CompositeTrajectory(listOf(a,b,c)) { - - public val type: TYPE = TYPE.valueOf( - arrayOf( - a.direction.name[0], - if (b is ArcSegment) b.direction.name[0] else 'S', - c.direction.name[0] - ).toCharArray().concatToString() - ) - - public enum class TYPE { - RLR, LRL, RSR, LSL, RSL, LSR - } - - public companion object { - public fun all( - start: Pose2D, - end: Pose2D, - turningRadius: Double, - ): List = listOfNotNull( - rlr(start, end, turningRadius), - lrl(start, end, turningRadius), - rsr(start, end, turningRadius), - lsl(start, end, turningRadius), - rsl(start, end, turningRadius), - lsr(start, end, turningRadius) - ) - - public fun shortest(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath = - all(start, end, turningRadius).minBy { it.length } - - public fun rlr(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath? { - val c1 = start.getRightCircle(turningRadius) - val c2 = end.getRightCircle(turningRadius) - val centers = StraightSegment(c1.center, c2.center) - if (centers.length > turningRadius * 4) return null - - var theta = theta(centers.theta - acos(centers.length / (turningRadius * 4))) - var dX = turningRadius * sin(theta) - var dY = turningRadius * cos(theta) - val p = Vector2D(c1.center.x + dX * 2, c1.center.y + dY * 2) - val e = Circle2D(p, turningRadius) - val p1 = Vector2D(c1.center.x + dX, c1.center.y + dY) - theta = theta(centers.theta + acos(centers.length / (turningRadius * 4))) - dX = turningRadius * sin(theta) - dY = turningRadius * cos(theta) - val p2 = Vector2D(e.center.x + dX, e.center.y + dY) - val a1 = ArcSegment.of(c1.center, start, p1, ArcSegment.Direction.RIGHT) - val a2 = ArcSegment.of(e.center, p1, p2, ArcSegment.Direction.LEFT) - val a3 = ArcSegment.of(c2.center, p2, end, ArcSegment.Direction.RIGHT) - return DubinsPath(a1, a2, a3) - } - - public fun lrl(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath? { - val c1 = start.getLeftCircle(turningRadius) - val c2 = end.getLeftCircle(turningRadius) - val centers = StraightSegment(c1.center, c2.center) - if (centers.length > turningRadius * 4) return null - - var theta = theta(centers.theta + acos(centers.length / (turningRadius * 4))) - var dX = turningRadius * sin(theta) - var dY = turningRadius * cos(theta) - val p = Vector2D(c1.center.x + dX * 2, c1.center.y + dY * 2) - val e = Circle2D(p, turningRadius) - val p1 = Vector2D(c1.center.x + dX, c1.center.y + dY) - theta = theta(centers.theta - acos(centers.length / (turningRadius * 4))) - dX = turningRadius * sin(theta) - dY = turningRadius * cos(theta) - val p2 = Vector2D(e.center.x + dX, e.center.y + dY) - val a1 = ArcSegment.of(c1.center, start, p1, ArcSegment.Direction.LEFT) - val a2 = ArcSegment.of(e.center, p1, p2, ArcSegment.Direction.RIGHT) - val a3 = ArcSegment.of(c2.center, p2, end, ArcSegment.Direction.LEFT) - return DubinsPath(a1, a2, a3) - } - - public fun rsr(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath { - val c1 = start.getRightCircle(turningRadius) - val c2 = end.getRightCircle(turningRadius) - val s = leftOuterTangent(c1, c2) - val a1 = ArcSegment.of(c1.center, start, s.start, ArcSegment.Direction.RIGHT) - val a3 = ArcSegment.of(c2.center, s.end, end, ArcSegment.Direction.RIGHT) - return DubinsPath(a1, s, a3) - } - - public fun lsl(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath { - val c1 = start.getLeftCircle(turningRadius) - val c2 = end.getLeftCircle(turningRadius) - val s = rightOuterTangent(c1, c2) - val a1 = ArcSegment.of(c1.center, start, s.start, ArcSegment.Direction.LEFT) - val a3 = ArcSegment.of(c2.center, s.end, end, ArcSegment.Direction.LEFT) - return DubinsPath(a1, s, a3) - } - - public fun rsl(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath? { - val c1 = start.getRightCircle(turningRadius) - val c2 = end.getLeftCircle(turningRadius) - val s = rightInnerTangent(c1, c2) - if (s == null || c1.center.distanceTo(c2.center) < turningRadius * 2) return null - - val a1 = ArcSegment.of(c1.center, start, s.start, ArcSegment.Direction.RIGHT) - val a3 = ArcSegment.of(c2.center, s.end, end, ArcSegment.Direction.LEFT) - return DubinsPath(a1, s, a3) - } - - public fun lsr(start: Pose2D, end: Pose2D, turningRadius: Double): DubinsPath? { - val c1 = start.getLeftCircle(turningRadius) - val c2 = end.getRightCircle(turningRadius) - val s = leftInnerTangent(c1, c2) - if (s == null || c1.center.distanceTo(c2.center) < turningRadius * 2) return null - - val a1 = ArcSegment.of(c1.center, start, s.start, ArcSegment.Direction.LEFT) - val a3 = ArcSegment.of(c2.center, s.end, end, ArcSegment.Direction.RIGHT) - return DubinsPath(a1, s, a3) - } - } -} \ No newline at end of file diff --git a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Pose2D.kt b/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Pose2D.kt deleted file mode 100644 index 1f7c4a52e..000000000 --- a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Pose2D.kt +++ /dev/null @@ -1,33 +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.trajectory - -import space.kscience.kmath.geometry.Vector -import space.kscience.kmath.geometry.Vector2D -import kotlin.math.atan2 - -/** - * Combination of [Vector] and its view angle - */ -public interface Pose2D: Vector2D{ - public val coordinate: Vector2D - public val theta: Double -} - -public class PhaseVector2D( - override val coordinate: Vector2D, - public val velocity: Vector2D -): Pose2D, Vector2D by coordinate{ - override val theta: Double get() = atan2(velocity.y, velocity.x) -} - -internal class Pose2DImpl( - override val coordinate: Vector2D, - override val theta: Double -) : Pose2D, Vector2D by coordinate - - -public fun Pose2D(coordinate: Vector2D, theta: Double): Pose2D = Pose2DImpl(coordinate, theta) \ No newline at end of file diff --git a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Trajectory.kt b/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Trajectory.kt deleted file mode 100644 index 2e97d43b0..000000000 --- a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/Trajectory.kt +++ /dev/null @@ -1,96 +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.trajectory - -import space.kscience.kmath.geometry.Circle2D -import space.kscience.kmath.geometry.Euclidean2DSpace.distanceTo -import space.kscience.kmath.geometry.Vector2D -import space.kscience.kmath.geometry.circumference -import kotlin.math.PI -import kotlin.math.atan2 - -public sealed interface Trajectory { - public val length: Double -} - -/** - * Straight path segment. The order of start and end defines the direction - */ -public data class StraightSegment( - internal val start: Vector2D, - internal val end: Vector2D, -) : Trajectory { - override val length: Double get() = start.distanceTo(end) - - internal val theta: Double get() = theta(atan2(end.x - start.x, end.y - start.y)) -} - -/** - * An arc segment - */ -public data class ArcSegment( - public val circle: Circle2D, - public val start: Pose2D, - public val end: Pose2D, -) : Trajectory { - - public enum class Direction { - LEFT, RIGHT - } - - override val length: Double by lazy { - val angle: Double = theta( - if (direction == Direction.LEFT) { - start.theta - end.theta - } else { - end.theta - start.theta - } - ) - val proportion = angle / (2 * PI) - circle.circumference * proportion - } - - internal val direction: Direction by lazy { - if (start.y < circle.center.y) { - if (start.theta > PI) Direction.RIGHT else Direction.LEFT - } else if (start.y > circle.center.y) { - if (start.theta < PI) Direction.RIGHT else Direction.LEFT - } else { - if (start.theta == 0.0) { - if (start.x < circle.center.x) Direction.RIGHT else Direction.LEFT - } else { - if (start.x > circle.center.x) Direction.RIGHT else Direction.LEFT - } - } - } - - public companion object { - public fun of(center: Vector2D, start: Vector2D, end: Vector2D, direction: Direction): ArcSegment { - fun calculatePose( - vector: Vector2D, - theta: Double, - direction: Direction, - ): Pose2D = Pose2D( - vector, - when (direction) { - Direction.LEFT -> theta(theta - PI / 2) - Direction.RIGHT -> theta(theta + PI / 2) - } - ) - - val s1 = StraightSegment(center, start) - val s2 = StraightSegment(center, end) - val pose1 = calculatePose(start, s1.theta, direction) - val pose2 = calculatePose(end, s2.theta, direction) - return ArcSegment(Circle2D(center, s1.length), pose1, pose2) - } - } -} - -public open class CompositeTrajectory(public val segments: Collection) : Trajectory { - override val length: Double get() = segments.sumOf { it.length } -} - diff --git a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/TrajectoryCost.kt b/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/TrajectoryCost.kt deleted file mode 100644 index 170851c43..000000000 --- a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/TrajectoryCost.kt +++ /dev/null @@ -1,14 +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.trajectory - -public fun interface TrajectoryCost { - public fun estimate(trajectory: Trajectory): Double - - public companion object{ - public val length: TrajectoryCost = TrajectoryCost { it.length } - } -} \ No newline at end of file diff --git a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/route.kt b/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/route.kt deleted file mode 100644 index f67ab124d..000000000 --- a/kmath-trajectory/src/commonMain/kotlin/space/kscience/kmath/trajectory/route.kt +++ /dev/null @@ -1,16 +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.trajectory - -public fun interface MaxCurvature { - public fun compute(startPoint: PhaseVector2D): Double -} - -public fun DubinsPath.Companion.shortest( - start: PhaseVector2D, - end: PhaseVector2D, - computer: MaxCurvature, -): DubinsPath = shortest(start, end, computer.compute(start)) diff --git a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/Math.kt b/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/Math.kt deleted file mode 100644 index 7ee68bd92..000000000 --- a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/Math.kt +++ /dev/null @@ -1,24 +0,0 @@ -package space.kscience.kmath.trajectory - -import space.kscience.kmath.geometry.Vector2D -import kotlin.math.PI -import kotlin.math.abs -import kotlin.math.sin - -const val maxFloatDelta = 0.000001 - -fun Double.radiansToDegrees() = this * 180 / PI - -fun Double.equalFloat(other: Double) = abs(this - other) < maxFloatDelta -fun Pose2D.equalsFloat(other: Pose2D) = x.equalFloat(other.x) && y.equalFloat(other.y) && theta.equalFloat(other.theta) - -fun StraightSegment.inverse() = StraightSegment(end, start) -fun StraightSegment.shift(shift: Int, width: Double): StraightSegment { - val dX = width * sin(inverse().theta) - val dY = width * sin(theta) - - return StraightSegment( - Vector2D(start.x - dX * shift, start.y - dY * shift), - Vector2D(end.x - dX * shift, end.y - dY * shift) - ) -} diff --git a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/dubins/DubinsTests.kt b/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/dubins/DubinsTests.kt deleted file mode 100644 index 09375a400..000000000 --- a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/dubins/DubinsTests.kt +++ /dev/null @@ -1,60 +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.trajectory.dubins - -import space.kscience.kmath.geometry.Euclidean2DSpace.distanceTo -import space.kscience.kmath.geometry.Vector2D -import space.kscience.kmath.trajectory.* -import kotlin.test.Test -import kotlin.test.assertNotNull -import kotlin.test.assertTrue - - -class DubinsTests { - - @Test - fun dubinsTest() { - val straight = StraightSegment(Vector2D(0.0, 0.0), Vector2D(100.0, 100.0)) - val lineP1 = straight.shift(1, 10.0).inverse() - - val start = Pose2D(straight.end, straight.theta) - val end = Pose2D(lineP1.start, lineP1.theta) - val radius = 2.0 - val dubins = DubinsPath.all(start, end, radius) - - val absoluteDistance = start.distanceTo(end) - println("Absolute distance: $absoluteDistance") - - val expectedLengths = mapOf( - DubinsPath.TYPE.RLR to 13.067681939031397, - DubinsPath.TYPE.RSR to 12.28318530717957, - DubinsPath.TYPE.LSL to 32.84955592153878, - DubinsPath.TYPE.RSL to 23.37758938854081, - DubinsPath.TYPE.LSR to 23.37758938854081 - ) - - expectedLengths.forEach { - val path = dubins.find { p -> p.type === it.key } - assertNotNull(path, "Path ${it.key} not found") - println("${it.key}: ${path.length}") - assertTrue(it.value.equalFloat(path.length)) - - assertTrue(start.equalsFloat(path.a.start)) - assertTrue(end.equalsFloat(path.c.end)) - - // Not working, theta double precision inaccuracy - if (path.b is ArcSegment) { - val b = path.b as ArcSegment - assertTrue(path.a.end.equalsFloat(b.start)) - assertTrue(path.c.start.equalsFloat(b.end)) - } else if (path.b is StraightSegment) { - val b = path.b as StraightSegment - assertTrue(path.a.end.equalsFloat(Pose2D(b.start, b.theta))) - assertTrue(path.c.start.equalsFloat(Pose2D(b.end, b.theta))) - } - } - } -} diff --git a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/ArcTests.kt b/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/ArcTests.kt deleted file mode 100644 index c66fa201b..000000000 --- a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/ArcTests.kt +++ /dev/null @@ -1,21 +0,0 @@ -package space.kscience.kmath.trajectory.segments - -import space.kscience.kmath.geometry.Circle2D -import space.kscience.kmath.geometry.Vector2D -import space.kscience.kmath.geometry.circumference -import space.kscience.kmath.trajectory.ArcSegment -import space.kscience.kmath.trajectory.radiansToDegrees -import kotlin.test.Test -import kotlin.test.assertEquals - -class ArcTests { - - @Test - fun arcTest() { - val circle = Circle2D(Vector2D(0.0, 0.0), 2.0) - val arc = ArcSegment.of(circle.center, Vector2D(-2.0, 0.0), Vector2D(0.0, 2.0), ArcSegment.Direction.RIGHT) - assertEquals(circle.circumference / 4, arc.length, 1.0) - assertEquals(0.0, arc.start.theta.radiansToDegrees()) - assertEquals(90.0, arc.end.theta.radiansToDegrees()) - } -} diff --git a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/CircleTests.kt b/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/CircleTests.kt deleted file mode 100644 index 5170c1db5..000000000 --- a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/CircleTests.kt +++ /dev/null @@ -1,25 +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.trajectory.segments - -import space.kscience.kmath.geometry.Circle2D -import space.kscience.kmath.geometry.Vector2D -import space.kscience.kmath.geometry.circumference -import space.kscience.kmath.trajectory.maxFloatDelta -import kotlin.test.Test -import kotlin.test.assertEquals - -class CircleTests { - - @Test - fun arcTest() { - val center = Vector2D(0.0, 0.0) - val radius = 2.0 - val expectedCircumference = 12.56637 - val circle = Circle2D(center, radius) - assertEquals(expectedCircumference, circle.circumference, maxFloatDelta) - } -} diff --git a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/LineTests.kt b/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/LineTests.kt deleted file mode 100644 index 11eaa0fb3..000000000 --- a/kmath-trajectory/src/commonTest/kotlin/space/kscience/kmath/trajectory/segments/LineTests.kt +++ /dev/null @@ -1,33 +0,0 @@ -package space.kscience.kmath.trajectory.segments - -import space.kscience.kmath.geometry.Euclidean2DSpace -import space.kscience.kmath.geometry.Vector2D -import space.kscience.kmath.trajectory.StraightSegment -import space.kscience.kmath.trajectory.radiansToDegrees -import kotlin.math.pow -import kotlin.math.sqrt -import kotlin.test.Test -import kotlin.test.assertEquals - -class LineTests { - - @Test - fun lineTest() { - val straight = StraightSegment(Vector2D(0.0, 0.0), Vector2D(100.0, 100.0)) - assertEquals(sqrt(100.0.pow(2) + 100.0.pow(2)), straight.length) - assertEquals(45.0, straight.theta.radiansToDegrees()) - } - - @Test - fun lineAngleTest() { - //val zero = Vector2D(0.0, 0.0) - val north = StraightSegment(Euclidean2DSpace.zero, Vector2D(0.0, 2.0)) - assertEquals(0.0, north.theta.radiansToDegrees()) - val east = StraightSegment(Euclidean2DSpace.zero, Vector2D(2.0, 0.0)) - assertEquals(90.0, east.theta.radiansToDegrees()) - val south = StraightSegment(Euclidean2DSpace.zero, Vector2D(0.0, -2.0)) - assertEquals(180.0, south.theta.radiansToDegrees()) - val west = StraightSegment(Euclidean2DSpace.zero, Vector2D(-2.0, 0.0)) - assertEquals(270.0, west.theta.radiansToDegrees()) - } -} diff --git a/kmath-viktor/README.md b/kmath-viktor/README.md index abff20427..8a781af4c 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.1-dev-1`. +The Maven coordinates of this project are `space.kscience:kmath-viktor:0.4.0-dev-1`. **Gradle Groovy:** ```groovy @@ -16,7 +16,7 @@ repositories { } dependencies { - implementation 'space.kscience:kmath-viktor:0.3.1-dev-1' + implementation 'space.kscience:kmath-viktor:0.4.0-dev-1' } ``` **Gradle Kotlin DSL:** @@ -27,6 +27,6 @@ repositories { } dependencies { - implementation("space.kscience:kmath-viktor:0.3.1-dev-1") + implementation("space.kscience:kmath-viktor:0.4.0-dev-1") } ``` diff --git a/kmath-viktor/api/kmath-viktor.api b/kmath-viktor/api/kmath-viktor.api index 3bb7c3b21..39ae1f84c 100644 --- a/kmath-viktor/api/kmath-viktor.api +++ b/kmath-viktor/api/kmath-viktor.api @@ -29,7 +29,7 @@ public class space/kscience/kmath/viktor/ViktorFieldND : space/kscience/kmath/vi 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 fun getShape-IIYLAfE ()[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; @@ -85,8 +85,8 @@ public class space/kscience/kmath/viktor/ViktorFieldOpsND : space/kscience/kmath 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 structureND-qL90JFI ([ILkotlin/jvm/functions/Function2;)Lspace/kscience/kmath/nd/StructureND; + public fun structureND-qL90JFI ([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; @@ -112,7 +112,7 @@ public final class space/kscience/kmath/viktor/ViktorStructureND : space/kscienc public fun get ([I)Ljava/lang/Double; public synthetic fun get ([I)Ljava/lang/Object; public final fun getF64Buffer ()Lorg/jetbrains/bio/viktor/F64Array; - public fun getShape ()[I + public fun getShape-IIYLAfE ()[I public fun set ([ID)V public synthetic fun set ([ILjava/lang/Object;)V } diff --git a/kmath-viktor/build.gradle.kts b/kmath-viktor/build.gradle.kts index 2e932b441..7a135f316 100644 --- a/kmath-viktor/build.gradle.kts +++ b/kmath-viktor/build.gradle.kts @@ -1,15 +1,14 @@ plugins { - kotlin("jvm") - id("ru.mipt.npm.gradle.common") + id("space.kscience.gradle.jvm") } description = "Binding for https://github.com/JetBrains-Research/viktor" dependencies { api(project(":kmath-core")) - api("org.jetbrains.bio:viktor:1.1.0") + api("org.jetbrains.bio:viktor:1.2.0") } readme { - maturity = ru.mipt.npm.gradle.Maturity.DEVELOPMENT + maturity = space.kscience.gradle.Maturity.DEVELOPMENT } diff --git a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorBuffer.kt b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorBuffer.kt index 4eedcb5ee..52dc1e192 100644 --- a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorBuffer.kt +++ b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorBuffer.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -13,7 +13,7 @@ import space.kscience.kmath.structures.MutableBuffer @JvmInline public value class ViktorBuffer(public val flatArray: F64FlatArray) : MutableBuffer { override val size: Int - get() = flatArray.size + get() = flatArray.length override inline fun get(index: Int): Double = flatArray[index] 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 cecbc35b8..8c7d6d199 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 @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ @@ -8,8 +8,9 @@ package space.kscience.kmath.viktor import org.jetbrains.bio.viktor.F64Array -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.misc.UnstableKMathAPI +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.UnsafeKMathAPI +import space.kscience.kmath.UnstableKMathAPI import space.kscience.kmath.nd.* import space.kscience.kmath.operations.DoubleField import space.kscience.kmath.operations.ExtendedFieldOps @@ -31,32 +32,36 @@ public open class ViktorFieldOpsND : override val elementAlgebra: DoubleField get() = DoubleField - override fun structureND(shape: IntArray, initializer: DoubleField.(IntArray) -> Double): ViktorStructureND = - F64Array(*shape).apply { - DefaultStrides(shape).asSequence().forEach { index -> + @OptIn(UnsafeKMathAPI::class) + override fun structureND(shape: ShapeND, initializer: DoubleField.(IntArray) -> Double): ViktorStructureND = + F64Array(*shape.asArray()).apply { + ColumnStrides(shape).asSequence().forEach { index -> set(value = DoubleField.initializer(index), indices = index) } }.asStructure() override fun StructureND.unaryMinus(): StructureND = -1 * this + @OptIn(UnsafeKMathAPI::class) @PerformancePitfall override fun StructureND.map(transform: DoubleField.(Double) -> Double): ViktorStructureND = - F64Array(*shape).apply { - DefaultStrides(shape).asSequence().forEach { index -> + F64Array(*shape.asArray()).apply { + ColumnStrides(ShapeND(shape)).asSequence().forEach { index -> set(value = DoubleField.transform(this@map[index]), indices = index) } }.asStructure() + @OptIn(UnsafeKMathAPI::class) @PerformancePitfall override fun StructureND.mapIndexed( transform: DoubleField.(index: IntArray, Double) -> Double, - ): ViktorStructureND = F64Array(*shape).apply { - DefaultStrides(shape).asSequence().forEach { index -> + ): ViktorStructureND = F64Array(*shape.asArray()).apply { + ColumnStrides(ShapeND(shape)).asSequence().forEach { index -> set(value = DoubleField.transform(index, this@mapIndexed[index]), indices = index) } }.asStructure() + @OptIn(UnsafeKMathAPI::class) @PerformancePitfall override fun zip( left: StructureND, @@ -64,8 +69,8 @@ public open class ViktorFieldOpsND : transform: DoubleField.(Double, Double) -> Double, ): ViktorStructureND { require(left.shape.contentEquals(right.shape)) - return F64Array(*left.shape).apply { - DefaultStrides(left.shape).asSequence().forEach { index -> + return F64Array(*left.shape.asArray()).apply { + ColumnStrides(left.shape).asSequence().forEach { index -> set(value = DoubleField.transform(left[index], right[index]), indices = index) } }.asStructure() @@ -119,13 +124,17 @@ public val DoubleField.viktorAlgebra: ViktorFieldOpsND get() = ViktorFieldOpsND @OptIn(UnstableKMathAPI::class) public open class ViktorFieldND( - override val shape: Shape, + private val shapeAsArray: IntArray, ) : ViktorFieldOpsND(), FieldND, NumbersAddOps> { - override val zero: ViktorStructureND by lazy { F64Array.full(init = 0.0, shape = shape).asStructure() } - override val one: ViktorStructureND by lazy { F64Array.full(init = 1.0, shape = shape).asStructure() } + + override val shape: ShapeND = ShapeND(shapeAsArray) + + + override val zero: ViktorStructureND by lazy { F64Array.full(init = 0.0, shape = shapeAsArray).asStructure() } + override val one: ViktorStructureND by lazy { F64Array.full(init = 1.0, shape = shapeAsArray).asStructure() } override fun number(value: Number): ViktorStructureND = - F64Array.full(init = value.toDouble(), shape = shape).asStructure() + F64Array.full(init = value.toDouble(), shape = shapeAsArray).asStructure() } public fun DoubleField.viktorAlgebra(vararg shape: Int): ViktorFieldND = ViktorFieldND(shape) diff --git a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorStructureND.kt b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorStructureND.kt index 25ca3a10e..7c0c02086 100644 --- a/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorStructureND.kt +++ b/kmath-viktor/src/main/kotlin/space/kscience/kmath/viktor/ViktorStructureND.kt @@ -1,28 +1,31 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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.viktor import org.jetbrains.bio.viktor.F64Array -import space.kscience.kmath.misc.PerformancePitfall -import space.kscience.kmath.nd.DefaultStrides +import space.kscience.kmath.PerformancePitfall +import space.kscience.kmath.nd.ColumnStrides import space.kscience.kmath.nd.MutableStructureND +import space.kscience.kmath.nd.ShapeND @Suppress("OVERRIDE_BY_INLINE", "NOTHING_TO_INLINE") public class ViktorStructureND(public val f64Buffer: F64Array) : MutableStructureND { - override val shape: IntArray get() = f64Buffer.shape + override val shape: ShapeND get() = ShapeND(f64Buffer.shape) + @OptIn(PerformancePitfall::class) override inline fun get(index: IntArray): Double = f64Buffer.get(*index) + @OptIn(PerformancePitfall::class) override inline fun set(index: IntArray, value: Double) { f64Buffer.set(*index, value = value) } @PerformancePitfall override fun elements(): Sequence> = - DefaultStrides(shape).asSequence().map { it to get(it) } + ColumnStrides(shape).asSequence().map { it to get(it) } } public fun F64Array.asStructure(): ViktorStructureND = ViktorStructureND(this) diff --git a/settings.gradle.kts b/settings.gradle.kts index 829e59144..f158f3444 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -13,8 +13,8 @@ dependencyResolutionManagement { } versionCatalogs { - create("npmlibs") { - from("ru.mipt.npm:version-catalog:$toolsVersion") + create("spclibs") { + from("space.kscience:version-catalog:$toolsVersion") } } } @@ -26,7 +26,6 @@ include( ":kmath-core", ":kmath-coroutines", ":kmath-functions", - ":kmath-polynomial", ":kmath-histograms", ":kmath-commons", ":kmath-viktor", @@ -45,7 +44,6 @@ include( ":kmath-jupyter", ":kmath-symja", ":kmath-jafama", - ":kmath-trajectory", ":examples", ":benchmarks", ) diff --git a/test-utils/README.md b/test-utils/README.md new file mode 100644 index 000000000..6ff8b98e8 --- /dev/null +++ b/test-utils/README.md @@ -0,0 +1,4 @@ +# Module test-utils + + + diff --git a/test-utils/api/test-utils.api b/test-utils/api/test-utils.api new file mode 100644 index 000000000..fc812a9a6 --- /dev/null +++ b/test-utils/api/test-utils.api @@ -0,0 +1,32 @@ +public final class space/kscience/kmath/testutils/AssertsKt { + public static final fun assertBufferEquals (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;D)V + public static synthetic fun assertBufferEquals$default (Lspace/kscience/kmath/structures/Buffer;Lspace/kscience/kmath/structures/Buffer;DILjava/lang/Object;)V +} + +public final class space/kscience/kmath/testutils/BufferEqualityKt { + public static final fun contentEquals-2c9zdjM ([D[D)Z + public static final fun contentEqualsArray ([D[D)Z + public static final fun contentEqualsBuffer ([D[D)Z +} + +public final class space/kscience/kmath/testutils/FieldVerifier : space/kscience/kmath/testutils/RingVerifier { + public fun (Lspace/kscience/kmath/operations/Field;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Number;)V + public fun verify ()V +} + +public class space/kscience/kmath/testutils/RingVerifier : space/kscience/kmath/testutils/SpaceVerifier { + public fun (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Number;)V + public fun verify ()V +} + +public class space/kscience/kmath/testutils/SpaceVerifier : space/kscience/kmath/testutils/AlgebraicVerifier { + public fun (Lspace/kscience/kmath/operations/Ring;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;Ljava/lang/Number;)V + public final fun getA ()Ljava/lang/Object; + public synthetic fun getAlgebra ()Lspace/kscience/kmath/operations/Algebra; + public fun getAlgebra ()Lspace/kscience/kmath/operations/Ring; + public final fun getB ()Ljava/lang/Object; + public final fun getC ()Ljava/lang/Object; + public final fun getX ()Ljava/lang/Number; + public fun verify ()V +} + diff --git a/test-utils/build.gradle.kts b/test-utils/build.gradle.kts index 88c7ea9d0..b03059eaf 100644 --- a/test-utils/build.gradle.kts +++ b/test-utils/build.gradle.kts @@ -1,6 +1,12 @@ plugins { - id("ru.mipt.npm.gradle.mpp") - id("ru.mipt.npm.gradle.native") + id("space.kscience.gradle.mpp") +} + +kscience{ + jvm() + js() + native() + wasm() } kotlin.sourceSets { diff --git a/test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt b/test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt index ddd8fc3ea..261e74f5a 100644 --- a/test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt +++ b/test-utils/src/commonMain/kotlin/AlgebraicVerifier.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/test-utils/src/commonMain/kotlin/FieldVerifier.kt b/test-utils/src/commonMain/kotlin/FieldVerifier.kt index f4ca7506b..a03ca0a27 100644 --- a/test-utils/src/commonMain/kotlin/FieldVerifier.kt +++ b/test-utils/src/commonMain/kotlin/FieldVerifier.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/test-utils/src/commonMain/kotlin/RingVerifier.kt b/test-utils/src/commonMain/kotlin/RingVerifier.kt index 14606cb2c..c40075d93 100644 --- a/test-utils/src/commonMain/kotlin/RingVerifier.kt +++ b/test-utils/src/commonMain/kotlin/RingVerifier.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/test-utils/src/commonMain/kotlin/SpaceVerifier.kt b/test-utils/src/commonMain/kotlin/SpaceVerifier.kt index d761a3775..01c02997b 100644 --- a/test-utils/src/commonMain/kotlin/SpaceVerifier.kt +++ b/test-utils/src/commonMain/kotlin/SpaceVerifier.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/test-utils/src/commonMain/kotlin/asserts.kt b/test-utils/src/commonMain/kotlin/asserts.kt index 8e7d1ae23..8ddce517c 100644 --- a/test-utils/src/commonMain/kotlin/asserts.kt +++ b/test-utils/src/commonMain/kotlin/asserts.kt @@ -1,5 +1,5 @@ /* - * Copyright 2018-2021 KMath contributors. + * Copyright 2018-2022 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. */ diff --git a/test-utils/src/commonMain/kotlin/bufferEquality.kt b/test-utils/src/commonMain/kotlin/bufferEquality.kt new file mode 100644 index 000000000..9e4d9ec22 --- /dev/null +++ b/test-utils/src/commonMain/kotlin/bufferEquality.kt @@ -0,0 +1,20 @@ +/* + * Copyright 2018-2022 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.DoubleBuffer +import kotlin.jvm.JvmName + +/** + * Simplified [DoubleBuffer] to array comparison + */ +public fun DoubleBuffer.contentEquals(vararg doubles: Double): Boolean = array.contentEquals(doubles) + +@JvmName("contentEqualsArray") +public infix fun DoubleBuffer.contentEquals(otherArray: DoubleArray): Boolean = array.contentEquals(otherArray) + +@JvmName("contentEqualsBuffer") +public infix fun DoubleBuffer.contentEquals(otherBuffer: DoubleBuffer): Boolean = array.contentEquals(otherBuffer.array) \ No newline at end of file