func (state *State) FindApplications(pred uint16) []uint16 { opCode, argOne, argTwo := opcodes.GetComponents(pred) switch opCode { case opcodes.OnOpCode: return []uint16{ opcodes.StackOpCode | argOne | argTwo, // Stack(x,y) | Putdown(x) } case opcodes.HoldingOpCode: if argOne == argone.Blank { return []uint16{ opcodes.StackOpCode | state.findWhatIsBeingHeld() | argtwo.Floor, // Putdown(x) } } else { base := state.findWhatBlockIsOn(argOne) if base == argtwo.Blank { return []uint16{ opcodes.PickupOpCode | argOne, // Pickup(x) } } else { return []uint16{ opcodes.UnstackOpCode | argOne | base, // Unstack(x, ?) } } } case opcodes.ClearOpCode: top := state.findWhatIsOnBlock(argOne) return []uint16{ opcodes.UnstackOpCode | top | argOne>>6, // Unstack(?, x) } default: return nil } }
func (state *State) GetPreconditions(cmd uint16) []uint16 { opCode, argOne, argTwo := opcodes.GetComponents(cmd) switch opCode { case opcodes.StackOpCode: // Stack(x,y) if argTwo != argtwo.Floor { return []uint16{ opcodes.HoldingOpCode | argOne | argtwo.Blank, // Holding(x) opcodes.ClearOpCode | argTwo<<6, // Clear(y) } } else { return []uint16{ opcodes.HoldingOpCode | argOne | argtwo.Blank, // Holding(x) } } case opcodes.UnstackOpCode: // Unstack(x,y) return []uint16{ opcodes.OnOpCode | argOne | argTwo, // On(x,y) opcodes.ClearOpCode | argOne, // Clear(x) opcodes.HoldingOpCode | argone.Blank | argtwo.Blank, // Holding(nil) } case opcodes.PickupOpCode: // Pickup(x) return []uint16{ opcodes.ClearOpCode | argOne, // Clear(x) opcodes.OnOpCode | argOne | argtwo.Floor, // On(x, Floor) opcodes.HoldingOpCode | argone.Blank | argtwo.Blank, // Holding(nil) } default: return nil } }
func (state *State) findWhatIsBeingHeld() uint16 { for _, pred := range *state { opCode, argOne, _ := opcodes.GetComponents(pred) if opCode == opcodes.HoldingOpCode { return argOne } } return 0 }
func (state *State) findWhatBlockIsOn(block uint16) uint16 { for _, pred := range *state { opCode, argOne, argTwo := opcodes.GetComponents(pred) if opCode == opcodes.OnOpCode && argOne == block { return argTwo } } return argtwo.Blank }
func (stack *StripsStack) Print() { for i := len(*stack) - 1; i >= 0; i-- { for _, item := range (*stack)[i] { opCode, _, _ := opcodes.GetComponents(uint16(item)) if opCode == opcodes.OnOpCode || opCode == opcodes.StackOpCode || opCode == opcodes.UnstackOpCode { fmt.Printf("%s(%s, %s) ", opcodes.GetOpCode(item), argone.GetBlockLabel(item), argtwo.GetBlockLabel(item)) } else { fmt.Printf("%s(%s) ", opcodes.GetOpCode(item), argone.GetBlockLabel(item)) } } fmt.Println() } }
func (state *State) getApplications(cmd uint16) []uint16 { opCode, argOne, argTwo := opcodes.GetComponents(cmd) switch opCode { case opcodes.StackOpCode: return []uint16{ opcodes.HoldingOpCode, // Holding(nil) opcodes.OnOpCode | argOne | argTwo, // On(x,y) opcodes.ClearOpCode | argOne, // Clear(x) } case opcodes.UnstackOpCode: return []uint16{ opcodes.HoldingOpCode | argOne, // Holding(x) opcodes.ClearOpCode | argTwo<<6, // Clear(y) } case opcodes.PickupOpCode: return []uint16{ opcodes.HoldingOpCode | argOne, // Holding(x) } default: return nil } }