CyclopsMC / IntegratedDynamics

A Minecraft mod to take full and automated control of your appliances.
http://cyclopsmc.github.io/IntegratedDynamics/
MIT License
126 stars 59 forks source link

Improve format of variable card NBT data #211

Open josephcsible opened 6 years ago

josephcsible commented 6 years ago

The way we store NBT data for variable cards gets really long and unwieldy really fast, since it's JSON containing strings of JSON containing strings of JSON containing strings... As an example, here's the value of a variable card containing an operator that returns whether an integer is divisible by 3 or 7, but not both:

combined.conjunction:{operators:["combined.disjunction:{operators:[\"combined.pipe:{operators:[\\\"curry:{valueType:\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\",value:\\\\\\\"3\\\\\\\",baseOperator:\\\\\\\"combined.flip:{operators:[\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.integer.modulus.name\\\\\\\\\\\\\\\"]}\\\\\\\"}\\\",\\\"curry:{valueType:\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\",value:\\\\\\\"0\\\\\\\",baseOperator:\\\\\\\"operator.operators.integrateddynamics.relational.equals.name\\\\\\\"}\\\"]}\",\"combined.pipe:{operators:[\\\"curry:{valueType:\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\",value:\\\\\\\"7\\\\\\\",baseOperator:\\\\\\\"combined.flip:{operators:[\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.integer.modulus.name\\\\\\\\\\\\\\\"]}\\\\\\\"}\\\",\\\"curry:{valueType:\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\",value:\\\\\\\"0\\\\\\\",baseOperator:\\\\\\\"operator.operators.integrateddynamics.relational.equals.name\\\\\\\"}\\\"]}\"]}","combined.negation:{operators:[\"combined.conjunction:{operators:[\\\"combined.pipe:{operators:[\\\\\\\"curry:{valueType:\\\\\\\\\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\\\\\\\\\",value:\\\\\\\\\\\\\\\"3\\\\\\\\\\\\\\\",baseOperator:\\\\\\\\\\\\\\\"combined.flip:{operators:[\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.integer.modulus.name\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\"]}\\\\\\\\\\\\\\\"}\\\\\\\",\\\\\\\"curry:{valueType:\\\\\\\\\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\\\\\\\\\",value:\\\\\\\\\\\\\\\"0\\\\\\\\\\\\\\\",baseOperator:\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.relational.equals.name\\\\\\\\\\\\\\\"}\\\\\\\"]}\\\",\\\"combined.pipe:{operators:[\\\\\\\"curry:{valueType:\\\\\\\\\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\\\\\\\\\",value:\\\\\\\\\\\\\\\"7\\\\\\\\\\\\\\\",baseOperator:\\\\\\\\\\\\\\\"combined.flip:{operators:[\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.integer.modulus.name\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\"]}\\\\\\\\\\\\\\\"}\\\\\\\",\\\\\\\"curry:{valueType:\\\\\\\\\\\\\\\"valuetype.valuetypes.integrateddynamics.integer.name\\\\\\\\\\\\\\\",value:\\\\\\\\\\\\\\\"0\\\\\\\\\\\\\\\",baseOperator:\\\\\\\\\\\\\\\"operator.operators.integrateddynamics.relational.equals.name\\\\\\\\\\\\\\\"}\\\\\\\"]}\\\"]}\"]}"]}

(2,473 bytes!) I think it would be worth looking into a nicer way of storing this, perhaps something like this:

conj(disj(dot(apply(flip(modulus), 3), apply(equals, 0)), dot(apply(flip(modulus), 3), apply(equals, 0))), negate(conj(dot(apply(flip(modulus), 3), apply(equals, 0)), dot(apply(flip(modulus), 3), apply(equals, 0)))))

Or maybe a lambda-calculus approach (for pipe and flip, I'm using B = λxyz.x(yz) and C = λxyz.xzy):

.&&. (.||. (B (== 0) (C % 3)) (B (== 0) (C % 7))) (!. (.&&. (B (== 0) (C % 3)) (B (== 0) (C % 7))))

(EDIT: that's actually more like combinatory logic than lambda calculus, since Integrated Dynamics doesn't let players directly write their own functions)

(EDIT 2: thinking about it more, I like my second proposed format way better than my first.)

rubensworks commented 6 years ago

Does it actually cause any issues for players? Due to the complexity of ID, there's always a lot of room for optimization on all levels, so I have to pick my battles. I only focus on issues that actually cause problems or performance issues.

The string-based representation of variables has been a thing I've been wanting to improve for a while now, NBT-based serialization would already improve a lot. But I've been holding it off for more urgent issues.

josephcsible commented 6 years ago

I don't notice any real issues from this, so I guess it should take low priority for now.