Add exact arithmetic implementation and tests
- Introduced exact arithmetic with support for large integers and fractions in `exact.gd`, `big_integer.gd`, and `exact_value.gd`. - Implemented a comprehensive test suite in `test_exact_math.gd` to validate arithmetic operations against expected results. - Added a README in `math` directory to document the exact arithmetic system and its usage. - Ensured that all arithmetic operations maintain precision without floating-point errors, using a custom representation for large numbers. - Included methods for encoding and decoding exact values for serialization.
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
extends SceneTree
|
||||
const E = preload("res://world/owniverse/math/exact.gd")
|
||||
const Clock = preload("res://world/owniverse/simulation_time.gd")
|
||||
var checks: int = 0
|
||||
var failures: int = 0
|
||||
@@ -7,9 +8,9 @@ func _initialize() -> void:
|
||||
call_deferred("run")
|
||||
|
||||
func check(condition: bool, message: String) -> void:
|
||||
checks += 1
|
||||
if not condition:
|
||||
failures += 1
|
||||
checks = E.add(checks, 1)
|
||||
if (not condition):
|
||||
failures = E.add(failures, 1)
|
||||
push_error(message)
|
||||
|
||||
func fixture():
|
||||
@@ -18,16 +19,16 @@ func fixture():
|
||||
for id in global.OwniverseEntities:
|
||||
var entity = load("res://world/owniverse/owniverse_entity.gd").new(global.OwniverseEntities[id])
|
||||
world.catalog.entities[id] = entity
|
||||
world.state.amount[id] = 0.0
|
||||
world.state.stats.total_amount[id] = 0.0
|
||||
if entity.group_as != "":
|
||||
world.state.amount[entity.group_as] = 0.0
|
||||
world.state.stats.total_amount[entity.group_as] = 0.0
|
||||
world.state.amount[id] = 0
|
||||
world.state.stats.total_amount[id] = 0
|
||||
if E.ne(entity.group_as, ""):
|
||||
world.state.amount[entity.group_as] = 0
|
||||
world.state.stats.total_amount[entity.group_as] = 0
|
||||
world.catalog.entities["N"].life_product = {}
|
||||
world.catalog.entities["N"].product_per_year_type = "H"
|
||||
world.catalog.entities["N"].product_per_year_amount = 10.0
|
||||
world.catalog.entities["N"].auto = 0.0
|
||||
world.state.amount.N = 1.0
|
||||
world.catalog.entities["N"].product_per_year_amount = 10
|
||||
world.catalog.entities["N"].auto = 0
|
||||
world.state.amount.N = 1
|
||||
return world
|
||||
|
||||
func dispose(world) -> void:
|
||||
@@ -38,21 +39,21 @@ func dispose(world) -> void:
|
||||
func run() -> void:
|
||||
var world = fixture()
|
||||
world.evolution.initialize_life_batches()
|
||||
world.catalog.entities.N.cost = {"H": 2.0}
|
||||
world.catalog.entities.N.bind = {"S": 3.0}
|
||||
world.state.amount.H = 10.0
|
||||
world.state.amount.S = 0.0
|
||||
world.state.auto_resources = {"H": 10.0}
|
||||
world.state.batches.H = [{"amount": 10.0, "start_year": 1.0, "end_year": 2.0}]
|
||||
world.catalog.entities.N.cost = {"H": 2}
|
||||
world.catalog.entities.N.bind = {"S": 3}
|
||||
world.state.amount.H = 10
|
||||
world.state.amount.S = 0
|
||||
world.state.auto_resources = {"H": 10}
|
||||
world.state.batches.H = [{"amount": 10, "start_year": 1, "end_year": 2}]
|
||||
var before: Dictionary = world.state.duplicate(true)
|
||||
check(not world.production.try_production(world.state, world.catalog.entities.N, 1.0, true), "Binding failure rejects production")
|
||||
check(world.state == before, "Failure preserves costs, batches and budget")
|
||||
world.state.amount.S = 10.0
|
||||
check((not world.production.try_production(world.state, world.catalog.entities.N, 1, true)), "Binding failure rejects production")
|
||||
check(E.eq(world.state, before), "Failure preserves costs, batches and budget")
|
||||
world.state.amount.S = 10
|
||||
var old_batches: Array = world.state.batches.H
|
||||
check(world.production.try_production(world.state, world.catalog.entities.N, 2.0, true), "Funded production succeeds")
|
||||
check(world.state.amount.H == 6.0 and world.state.amount.S == 4.0, "Exact cost and binding")
|
||||
check(world.state.auto_resources.H == 6.0, "Exact automatic budget")
|
||||
check(old_batches[0].amount == 10.0 and world.state.batches.H[0].amount == 6.0, "Consumed batches isolated")
|
||||
print("Transaction: %d checks, %d failures" % [checks, failures])
|
||||
check(world.production.try_production(world.state, world.catalog.entities.N, 2, true), "Funded production succeeds")
|
||||
check((E.eq(world.state.amount.H, 6) and E.eq(world.state.amount.S, 4)), "Exact cost and binding")
|
||||
check(E.eq(world.state.auto_resources.H, 6), "Exact automatic budget")
|
||||
check((E.eq(old_batches[0].amount, 10) and E.eq(world.state.batches.H[0].amount, 6)), "Consumed batches isolated")
|
||||
print(("Transaction: %d checks, %d failures" % [checks, failures]))
|
||||
dispose(world)
|
||||
quit(1 if failures else 0)
|
||||
quit((1 if failures else 0))
|
||||
|
||||
Reference in New Issue
Block a user