diff --git a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo1.kt b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo1.kt index bbfea40..02a0ad0 100644 --- a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo1.kt +++ b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo1.kt @@ -48,11 +48,11 @@ data object Demo1 { suspend operator fun invoke(): Try { for (process in subProcesses) { when (val result = process()) { + is Ok -> {} + is Failed -> { return Failed(result.error) } - - else -> {} } } return ok diff --git a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo2.kt b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo2.kt index a9e7b3a..a069b02 100644 --- a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo2.kt +++ b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo2.kt @@ -74,11 +74,11 @@ data object Demo2 { suspend operator fun invoke(): Try { for (process in subProcesses) { when (val result = process()) { + is Ok -> {} + is Failed -> { return Failed(result.error) } - - else -> {} } } return ok diff --git a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo3.kt b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo3.kt index a615b55..732fb76 100644 --- a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo3.kt +++ b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo3.kt @@ -14,43 +14,39 @@ import fuookami.ospf.kotlin.core.frontend.model.mechanism.* import fuookami.ospf.kotlin.core.backend.plugins.scip.* data object Demo3 { - data class Product( - override val index: Int, - val minYield: Flt64 - ) : Indexed + data class Product(val minYield: Flt64) : AutoIndexed(Product::class) data class Material( - override val index: Int, val cost: Flt64, val yieldValue: Map - ) : Indexed + ) : AutoIndexed(Material::class) private val products = listOf( - Product(0, Flt64(15000.0)), - Product(1, Flt64(15000.0)), - Product(2, Flt64(10000.0)) + Product(Flt64(15000.0)), + Product(Flt64(15000.0)), + Product(Flt64(10000.0)) ) private val materials = listOf( Material( - 0, Flt64(115.0), mapOf( + Flt64(115.0), mapOf( products[0] to Flt64(30.0), products[1] to Flt64(10.0) ) ), Material( - 1, Flt64(97.0), mapOf( + Flt64(97.0), mapOf( products[0] to Flt64(15.0), products[2] to Flt64(20.0) ) ), Material( - 2, Flt64(82.0), mapOf( + Flt64(82.0), mapOf( products[1] to Flt64(25.0), products[2] to Flt64(15.0) ) ), Material( - 3, Flt64(76.0), mapOf( + Flt64(76.0), mapOf( products[0] to Flt64(15.0), products[1] to Flt64(15.0), products[2] to Flt64(15.0) @@ -77,11 +73,11 @@ data object Demo3 { suspend operator fun invoke(): Try { for (process in subProcesses) { when (val result = process()) { + is Ok -> {} + is Failed -> { return Failed(result.error) } - - else -> {} } } return ok diff --git a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo4.kt b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo4.kt index b54db06..c6fb3a7 100644 --- a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo4.kt +++ b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo4.kt @@ -1,10 +1,9 @@ package fuookami.ospf.kotlin.example.core_demo +import fuookami.ospf.kotlin.utils.math.* import fuookami.ospf.kotlin.utils.concept.* -import fuookami.ospf.kotlin.utils.error.* import fuookami.ospf.kotlin.utils.functional.* import fuookami.ospf.kotlin.utils.multi_array.* -import fuookami.ospf.kotlin.utils.math.* import fuookami.ospf.kotlin.core.frontend.variable.* import fuookami.ospf.kotlin.core.frontend.expression.monomial.* import fuookami.ospf.kotlin.core.frontend.expression.polynomial.* @@ -14,31 +13,27 @@ import fuookami.ospf.kotlin.core.frontend.model.mechanism.* import fuookami.ospf.kotlin.core.backend.plugins.scip.* data object Demo4 { - data class Material( - override val index: Int, - val available: Flt64 - ) : Indexed + data class Material(val available: Flt64) : AutoIndexed(Material::class) data class Product( - override val index: Int, val profit: Flt64, val maxYield: Flt64, val use: Map - ) : Indexed + ) : AutoIndexed(Product::class) private val materials = listOf( - Material(0, Flt64(24.0)), - Material(1, Flt64(8.0)) + Material(Flt64(24.0)), + Material(Flt64(8.0)) ) private val products = listOf( Product( - 0, Flt64(5.0), Flt64(3.0), mapOf( + Flt64(5.0), Flt64(3.0), mapOf( materials[0] to Flt64(6.0), materials[1] to Flt64(1.0), ) ), Product( - 1, Flt64(4.0), Flt64(2.0), mapOf( + Flt64(4.0), Flt64(2.0), mapOf( materials[0] to Flt64(4.0), materials[1] to Flt64(2.0), ) @@ -65,11 +60,11 @@ data object Demo4 { suspend operator fun invoke(): Try { for (process in subProcesses) { when (val result = process()) { + is Ok -> {} + is Failed -> { return Failed(result.error) } - - else -> {} } } return ok diff --git a/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo5.kt b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo5.kt new file mode 100644 index 0000000..feed1d4 --- /dev/null +++ b/examples/ospf-kotlin-example/src/main/fuookami/ospf/kotlin/example/core_demo/Demo5.kt @@ -0,0 +1,114 @@ +package fuookami.ospf.kotlin.example.core_demo + +import fuookami.ospf.kotlin.core.backend.plugins.scip.SCIPLinearSolver +import fuookami.ospf.kotlin.utils.concept.* +import fuookami.ospf.kotlin.utils.error.* +import fuookami.ospf.kotlin.utils.functional.* +import fuookami.ospf.kotlin.utils.multi_array.* +import fuookami.ospf.kotlin.utils.math.* +import fuookami.ospf.kotlin.core.frontend.variable.* +import fuookami.ospf.kotlin.core.frontend.expression.monomial.* +import fuookami.ospf.kotlin.core.frontend.expression.polynomial.* +import fuookami.ospf.kotlin.core.frontend.expression.symbol.* +import fuookami.ospf.kotlin.core.frontend.inequality.* +import fuookami.ospf.kotlin.core.frontend.model.mechanism.* + +data object Demo5 { + data class Cargo( + val weight: UInt64, + val value: UInt64 + ) : AutoIndexed(Cargo::class) + + private val cargos = listOf( + Cargo(UInt64(2U), UInt64(6U)), + Cargo(UInt64(2U), UInt64(3U)), + Cargo(UInt64(6U), UInt64(5U)), + Cargo(UInt64(5U), UInt64(4U)), + Cargo(UInt64(4U), UInt64(6U)) + ) + private val maxWeight = UInt64(10U) + + private lateinit var x: BinVariable1 + private lateinit var cargoWeight: LinearSymbol + private lateinit var cargoValue: LinearSymbol + + private val metaModel: LinearMetaModel = LinearMetaModel("demo5") + + private val subProcesses = listOf( + Demo5::initVariable, + Demo5::initSymbol, + Demo5::initObject, + Demo5::initConstraint, + Demo5::solve, + Demo5::analyzeSolution + ) + + suspend operator fun invoke(): Try { + for (process in subProcesses) { + when (val result = process()) { + is Ok -> {} + + is Failed -> { + return Failed(result.error) + } + } + } + return ok + } + + private suspend fun initVariable(): Try { + x = BinVariable1("x", Shape1(cargos.size)) + for (c in cargos) { + x[c].name = "${x.name}_${c.index}" + } + metaModel.addVars(x) + return ok + } + + private suspend fun initSymbol(): Try { + cargoValue = LinearExpressionSymbol(sum(cargos) { c -> c.value * x[c] }, "value") + metaModel.addSymbol(cargoValue) + + cargoWeight = LinearExpressionSymbol(sum(cargos) { c -> c.weight * x[c] }, "weight") + metaModel.addSymbol(cargoWeight) + return ok + } + + private suspend fun initObject(): Try { + metaModel.maximize(LinearPolynomial(cargoValue),"value") + return ok + } + + private suspend fun initConstraint(): Try { + metaModel.addConstraint( + cargoWeight leq maxWeight,"weight" + ) + return ok + } + + private suspend fun solve(): Try { + val solver = SCIPLinearSolver() + when (val ret = solver(metaModel)) { + is Ok -> { + metaModel.tokens.setSolution(ret.value.solution) + } + + is Failed -> { + return Failed(ret.error) + } + } + return ok + } + + private suspend fun analyzeSolution(): Try { + val ret = HashSet() + for (token in metaModel.tokens.tokens) { + if (token.result!! eq Flt64.one + && token.variable.belongsTo(x) + ) { + ret.add(cargos[token.variable.vectorView[0]]) + } + } + return ok + } +} diff --git a/examples/ospf-kotlin-example/src/test/fuookami/ospf/kotlin/example/CoreDemoTest.kt b/examples/ospf-kotlin-example/src/test/fuookami/ospf/kotlin/example/CoreDemoTest.kt index c078617..ebeeeb5 100644 --- a/examples/ospf-kotlin-example/src/test/fuookami/ospf/kotlin/example/CoreDemoTest.kt +++ b/examples/ospf-kotlin-example/src/test/fuookami/ospf/kotlin/example/CoreDemoTest.kt @@ -24,4 +24,9 @@ class CoreDemoTest { fun runDemo4() { assert(runBlocking { Demo4().ok }) } + + @Test + fun runDemo5() { + assert(runBlocking { Demo5().ok }) + } }