| summaryrefslogtreecommitdiff |
diff options
| -rw-r--r-- | src/core/src/tonkadur/wyrd/v1/compiler/fate/v1/ComputationCompiler.java | 54 | ||||
| -rw-r--r-- | src/core/src/tonkadur/wyrd/v1/compiler/util/RemoveElementsOf.java | 111 |
2 files changed, 165 insertions, 0 deletions
diff --git a/src/core/src/tonkadur/wyrd/v1/compiler/fate/v1/ComputationCompiler.java b/src/core/src/tonkadur/wyrd/v1/compiler/fate/v1/ComputationCompiler.java index 3d48b52..161acba 100644 --- a/src/core/src/tonkadur/wyrd/v1/compiler/fate/v1/ComputationCompiler.java +++ b/src/core/src/tonkadur/wyrd/v1/compiler/fate/v1/ComputationCompiler.java @@ -31,6 +31,7 @@ import tonkadur.wyrd.v1.compiler.util.Fold; import tonkadur.wyrd.v1.compiler.util.FilterLambda; import tonkadur.wyrd.v1.compiler.util.Shuffle; import tonkadur.wyrd.v1.compiler.util.RemoveAt; +import tonkadur.wyrd.v1.compiler.util.RemoveElementsOf; import tonkadur.wyrd.v1.compiler.util.InsertAt; import tonkadur.wyrd.v1.compiler.util.RemoveAllOf; import tonkadur.wyrd.v1.compiler.util.IndexedMapLambda; @@ -2106,6 +2107,59 @@ implements tonkadur.fate.v1.lang.meta.ComputationVisitor } @Override + public void visit_remove_elements_of + ( + final tonkadur.fate.v1.lang.computation.RemoveElementsOfComputation n + ) + throws Throwable + { + final ComputationCompiler collection_in_cc, collection_cc; + final Register result; + + result = reserve(TypeCompiler.compile(compiler, n.get_type())); + + result_as_address = result.get_address(); + result_as_computation = result.get_value(); + + collection_cc = new ComputationCompiler(compiler); + + n.get_target_collection().get_visited_by(collection_cc); + + if (collection_cc.has_init()) + { + init_instructions.add(collection_cc.get_init()); + } + + init_instructions.add + ( + new SetValue(result_as_address, collection_cc.get_computation()) + ); + + collection_cc.release_registers(init_instructions); + + collection_in_cc = new ComputationCompiler(compiler); + + n.get_source_collection().get_visited_by(collection_in_cc); + + assimilate(collection_in_cc); + + init_instructions.add + ( + RemoveElementsOf.generate + ( + compiler.registers(), + compiler.assembler(), + collection_in_cc.get_address(), + result_as_address, + ( + (tonkadur.fate.v1.lang.type.CollectionType) + n.get_target_collection().get_type() + ).is_set() + ) + ); + } + + @Override public void visit_add_elements_of ( final tonkadur.fate.v1.lang.computation.AddElementsOfComputation n diff --git a/src/core/src/tonkadur/wyrd/v1/compiler/util/RemoveElementsOf.java b/src/core/src/tonkadur/wyrd/v1/compiler/util/RemoveElementsOf.java new file mode 100644 index 0000000..93a8829 --- /dev/null +++ b/src/core/src/tonkadur/wyrd/v1/compiler/util/RemoveElementsOf.java @@ -0,0 +1,111 @@ +package tonkadur.wyrd.v1.compiler.util; + +import java.util.List; +import java.util.ArrayList; + +import tonkadur.wyrd.v1.lang.Register; + +import tonkadur.wyrd.v1.lang.type.Type; +import tonkadur.wyrd.v1.lang.type.MapType; + +import tonkadur.wyrd.v1.lang.meta.Instruction; +import tonkadur.wyrd.v1.lang.meta.Computation; + +import tonkadur.wyrd.v1.lang.computation.Cast; +import tonkadur.wyrd.v1.lang.computation.Constant; +import tonkadur.wyrd.v1.lang.computation.Operation; +import tonkadur.wyrd.v1.lang.computation.Address; +import tonkadur.wyrd.v1.lang.computation.RelativeAddress; +import tonkadur.wyrd.v1.lang.computation.ValueOf; +import tonkadur.wyrd.v1.lang.computation.Size; + +import tonkadur.wyrd.v1.lang.instruction.SetValue; + +import tonkadur.wyrd.v1.compiler.util.registers.RegisterManager; + +public class RemoveElementsOf +{ + /* Utility Class */ + private RemoveElementsOf () {} + + /* Uses Durstenfeld's shuffling algorithm */ + public static Instruction generate + ( + final RegisterManager registers, + final InstructionManager assembler, + final Address collection_in, + final Address collection, + final boolean is_set + ) + { + final List<Instruction> result, while_body; + final Register iterator, collection_in_size; + + result = new ArrayList<Instruction>(); + while_body = new ArrayList<Instruction>(); + + iterator = registers.reserve(Type.INT, result); + collection_in_size = registers.reserve(Type.INT, result); + + result.add(new SetValue(iterator.get_address(), Constant.ZERO)); + result.add + ( + new SetValue + ( + collection_in_size.get_address(), + new Size(collection_in) + ) + ); + + while_body.add + ( + RemoveOneOf.generate + ( + registers, + assembler, + new ValueOf + ( + new RelativeAddress + ( + collection_in, + new Cast(iterator.get_value(), Type.STRING), + ( + (MapType) collection_in.get_target_type() + ).get_member_type() + ) + ), + collection, + is_set + ) + ); + + while_body.add + ( + new SetValue + ( + iterator.get_address(), + Operation.plus(iterator.get_value(), Constant.ONE) + ) + ); + + result.add + ( + While.generate + ( + registers, + assembler, + Operation.less_than + ( + iterator.get_value(), + collection_in_size.get_value() + ), + assembler.merge(while_body) + ) + ); + + registers.release(iterator, result); + registers.release(collection_in_size, result); + + return assembler.merge(result); + } +} |


