summaryrefslogtreecommitdiff
path: root/modeling/productions_math.py
diff options
context:
space:
mode:
Diffstat (limited to 'modeling/productions_math.py')
-rw-r--r--modeling/productions_math.py302
1 files changed, 302 insertions, 0 deletions
diff --git a/modeling/productions_math.py b/modeling/productions_math.py
new file mode 100644
index 0000000..475ed59
--- /dev/null
+++ b/modeling/productions_math.py
@@ -0,0 +1,302 @@
+#!/usr/bin/env python3
+
+import pyactr as actr
+
+Model = actr.ACTRModel()
+
+DM = Model.decmem
+g = Model.goal
+imaginal = Model.set_goal(name="imaginal", delay=0.2)
+
+actr.chunktype("number", ("number", "next", "ones", "tens", "hundreds"))
+actr.chunktype("math_goal", ("op", "task"))
+actr.chunktype(
+ "math_op",
+ (
+ "op",
+ "arg1",
+ "arg2",
+ "result",
+ "hundreds1",
+ "tens1",
+ "ones1",
+ "hundreds2",
+ "tens2",
+ "ones2",
+ "hundreds_ans",
+ "tens_ans",
+ "ones_ans",
+ "carry",
+ ),
+)
+
+g.add(actr.makechunk("", "math_goal", op="greater", task="calc"))
+imaginal.add(
+ actr.makechunk(
+ "",
+ "math_op",
+ op="greater",
+ arg1=5,
+ arg2=2,
+ ones1=5,
+ tens1=0,
+ hundreds1=0,
+ ones2=2,
+ tens2=0,
+ hundreds2=0,
+ )
+)
+
+
+# https://stackoverflow.com/a/39644726
+def get_digit(number, n):
+ return number // 10**n % 10
+
+
+# Add numbers 0-999 to decmem
+for i in range(0, 1000):
+ DM.add(
+ actr.makechunk(
+ f"number{str(i)}",
+ "number",
+ number=i,
+ next=i + 1,
+ ones=get_digit(i, 0),
+ tens=get_digit(i, 1),
+ hundreds=get_digit(i, 2),
+ )
+ )
+
+# Add comparison relations to single digit numbers
+for i in range(0, 10):
+ for j in range(0, 10):
+ DM.add(
+ actr.makechunk(
+ f"greater{i}{j}",
+ "math_op",
+ op="greater",
+ arg1=i,
+ arg2=j,
+ result=max(i, j),
+ )
+ )
+ DM.add(
+ actr.makechunk(
+ f"lesser{i}{j}",
+ "math_op",
+ op="lesser",
+ arg1=i,
+ arg2=j,
+ result=min(i, j),
+ )
+ )
+ DM.add(
+ actr.makechunk(
+ f"plus{i}{j}", "math_op", op="add", arg1=i, arg2=j, result=i + j
+ )
+ )
+
+
+def unwind_prod():
+ # Model.productionstring(
+ # name="init_math_op",
+ # string="""
+ # =g>
+ # isa math_op
+ # task None
+ # arg1 =num1
+ # arg2 =num2
+ # ==>
+ # +retrieval>
+ # isa number
+ # number =num1
+ # =g>
+ # task unwind_left
+ # """,
+ # )
+
+ Model.productionstring(
+ name="terminate_op",
+ string="""
+ =g>
+ isa math_op
+ task finished_op
+ =imaginal>
+ result =answer
+ ==>
+ ~g>""",
+ )
+
+
+def greater_than_prod():
+ # TODO: if two numbers are equal, extra effort to determine greater one?
+ prod_start = Model.productionstring(
+ name="greater_start",
+ string="""
+ =g>
+ isa math_goal
+ task calc
+ =imaginal>
+ isa math_op
+ op greater
+ hundreds1 =hun1
+ hundreds2 =hun1
+ tens1 =tens1
+ tens2 =tens1
+ ones1 =ones1
+ ones2 ~=ones1
+ ones2 =ones2
+ ==>
+ +retrieval>
+ isa math_op
+ op greater
+ arg1 =ones1
+ arg2 =ones2
+ """,
+ )
+ print(prod_start)
+
+ Model.productionstring(
+ name="greater_end",
+ string="""
+ =g>
+ isa math_goal
+ =imaginal>
+ op greater
+ =retrieval>
+ isa mat_op
+ op greater
+ result =ans
+ ==>
+ =imaginal>
+ isa math_op
+ result =ans
+ ~g>
+ """,
+ )
+
+
+def addition():
+ Model.productionstring(
+ name="start_add",
+ string="""
+ =goal>
+ isa math_goal
+ =imaginal>
+ op add
+ ones1 =num1
+ ones2 =num2
+ one_ans None
+ ==>
+ =imaginal>
+ isa math_op
+ one-ans busy
+ +retrieval>
+ isa math_op
+ op add
+ arg1 =num1
+ arg2 =num2
+ """,
+ )
+
+ Model.productionstring(
+ name="add_ones",
+ string="""
+ =goal>
+ isa math_goal
+ =imaginal>
+ isa math_op
+ op add
+ one-ans busy
+ ones1 =num1
+ ones2 =num2
+ =retrieval>
+ isa math_op
+ arg1 =num1
+ arg2 =num2
+ result =result
+ ==>
+ =goal>
+ isa math_goal
+ =imaginal>
+ ones_ans =result
+ carry busy
+ +retrieval>
+ isa math_op
+ op add
+ arg1 10
+ result =result
+ """,
+ )
+
+ Model.productionstring(
+ name="process_carry",
+ string="""
+ =goal>
+ isa math_goal
+ =imaginal>
+ isa math_op
+ op add
+ tens1 =num1
+ tens2 =num2
+ carry busy
+ ones_ans =ones
+ =retrieval>
+ isa math_op
+ op add
+ arg1 10
+ result =ones
+ arg2 =remainder
+ ==>
+ =goal>
+ isa math_goal
+ =imaginal>
+ isa math_op
+ op add
+ carry 1
+ tens_ans busy
+ one_ans =remainder
+ +retrieval>
+ isa math_op
+ op add
+ arg1 =num1
+ arg2 =num2
+ """,
+ )
+
+ Model.productionstring(
+ name="increment-sum",
+ string="""
+ =goal>
+ ISA add
+ sum =sum
+ count =count
+ - arg2 =count
+ =retrieval>
+ ISA number
+ number =sum
+ next =newsum
+ ==>
+ =goal>
+ ISA add
+ sum =newsum
+ +retrieval>
+ ISA number
+ number =count
+ """,
+ )
+
+
+# print(DM)
+
+# unwind_prod()
+greater_than_prod()
+
+# Model.goal.add(actr.makechunk("goal", "math_op", op="greater", arg1=5, arg2=9))
+print("g: ", g)
+print("imaginal: ", imaginal)
+x = Model.simulation()
+x.run()
+# print(list(DM))
+numbers = [x for x in list(DM) if x.typename != "number" and x.typename != "math_op"]
+# print(numbers)