Пример #1
0
        public async Task RunYolol([Remainder] string input)
        {
            var code = input.ExtractYololCodeBlock();

            if (code == null)
            {
                await ReplyAsync(@"Failed to parse a yolol program from message - ensure you have enclosed your solution in triple backticks \`\`\`like this\`\`\`");

                return;
            }

            var result = Yolol.Grammar.Parser.ParseProgram(code);

            if (!result.IsOk)
            {
                await ReplyAsync(result.Err.ToString());

                return;
            }

            var network = new DefaultValueDeviceNetwork();
            var state   = new MachineState(network);
            var done    = state.GetVariable(":done");

            // Run lines until completion indicator is set or execution time limit is exceeded
            var limit = 0;
            var pc    = 0;

            while (!done.Value.ToBool() && limit++ < 2000)
            {
                try
                {
                    // If line if blank, just move to the next line
                    if (pc >= result.Ok.Lines.Count)
                    {
                        pc++;
                    }
                    else
                    {
                        pc = result.Ok.Lines[pc].Evaluate(pc, state);
                    }
                }
                catch (ExecutionException)
                {
                    pc++;
                }

                // loop around if program counter goes over max
                if (pc >= 20)
                {
                    pc = 0;
                }
            }

            // Print out the final machine state
            var embed = state.ToEmbed(network, limit, pc + 1).Build();

            await ReplyAsync(embed : embed);
        }
Пример #2
0
        public override ExecutionResult Evaluate(MachineState state)
        {
            var var = state.GetVariable(Left.Name);

            var.Value = Right.Evaluate(state);

            return(new ExecutionResult());
        }
Пример #3
0
        public void ExternalVariable()
        {
            var n = new ConstantNetwork();

            n.Get("name").Value = new Value(13);
            var s = new MachineState(n, new DefaultIntrinsics());

            Assert.AreEqual(13, s.GetVariable(":name").Value.Number);
        }
Пример #4
0
        public void ExternalVariable()
        {
            var n = new ConstantNetwork();

            n.Get("name").Value = new Value((Number)13);
            var s = new MachineState(n);

            Assert.AreEqual((Number)13, s.GetVariable(":name").Value.Number);
        }
Пример #5
0
        public void Enumerate()
        {
            var s = new MachineState(new ConstantNetwork(), new DefaultIntrinsics());

            s.GetVariable("name");

            var arr = s.ToArray();

            Assert.AreEqual(1, arr.Length);
        }
Пример #6
0
        public override Value Evaluate(MachineState state)
        {
            var variable = state.GetVariable(Name);

            var original = variable.Value;
            var modified = Evaluate(original, state.MaxStringLength);

            variable.Value = modified;

            return(PreOp ? modified : original);
        }
Пример #7
0
        public override Value Evaluate(MachineState state)
        {
            var variable = state.GetVariable(Name);

            var original = variable.Value;
            var modified = Modify(original);

            variable.Value = modified;

            return(Return(original, modified));
        }
Пример #8
0
        public void ZijkhalBoolDivision()
        {
            const string code = "a=-9223372036854775.808 c=a/1";
            var          ast  = TestHelpers.Parse(code);

            var st = new MachineState(new NullDeviceNetwork(), 20);

            ast.Lines[0].Evaluate(1, st);

            var ms = TestHelpers.Test(code);

            Assert.AreEqual(st.GetVariable("c").Value, ms.GetVariable("c"));
        }
Пример #9
0
        public override Failure?CheckCase(IReadOnlyDictionary <string, Value> inputs, IReadOnlyDictionary <string, Value> expectedOutputs, MachineState state)
        {
            // Check that the machine state is exactly correct for every expected output
            foreach (var(key, expected) in expectedOutputs)
            {
                var actual = state.GetVariable($":{key}").Value;

                // Add bonus points averaged across all cases
                AddBonusAveragedPoints((expected.Type, actual.Type) switch {
                    (Type.Number, Type.Number) => AccuracyScore(expected.Number, actual.Number),
                    (Type.String, Type.String) => AccuracyScore(expected.String, actual.String),
                    _ => 0,
                });
Пример #10
0
        public virtual Failure?CheckCase(IReadOnlyDictionary <string, Value> inputs, IReadOnlyDictionary <string, Value> expectedOutputs, MachineState state)
        {
            // Check that the machine state is exactly correct for every expected output
            foreach (var(key, value) in expectedOutputs)
            {
                var v = state.GetVariable($":{key}");
                if ((v.Value != value).ToBool())
                {
                    var ii = string.Join(",", inputs.Select(b => $"`:{b.Key}={b.Value.ToHumanString()}`"));
                    var oo = string.Join(",", expectedOutputs.Select(b => $"`:{b.Key}={b.Value.ToHumanString()}`"));
                    return(new Failure(FailureType.IncorrectResult, $"For inputs {ii} expected outputs {oo}, got `{v.Value.ToHumanString()}` for `:{key}`"));
                }
            }

            // All variables ok, return null to indicate no failure
            return(null);
        }
Пример #11
0
 public override Value Evaluate(MachineState state)
 {
     return(state.GetVariable(_var.Name).Value);
 }
        public async Task <(Success?, Failure?)> Verify(Challenge.Challenge challenge, string yolol)
        {
            await Task.CompletedTask;

            IScore scoreMode = challenge.ScoreMode switch {
                ScoreMode.BasicScoring => new BasicScoring(),
                ScoreMode.Approximate => new ApproximateScoring(),
                ScoreMode.Unknown => throw new InvalidOperationException("Cannot use `Unknown` score mode (challenge is broken - contact Martin#2468)"),
                      _ => throw new NotImplementedException($"Score mode `{challenge.ScoreMode}` is not implemented")
            };

            // Retrieve the test cases for the challenge
            var(inputs, outputs) = GetTests(challenge);

            // Check input program fits within 20x70
            var lines = yolol.Split("\n");

            if (lines.Length > 20 || lines.Any(l => l.Length > 70))
            {
                return(null, new Failure(FailureType.ProgramTooLarge, null));
            }

            // parse the program
            var result = Parser.ParseProgram(yolol);

            if (!result.IsOk)
            {
                return(null, new Failure(FailureType.ParseFailed, result.Err.ToString()));
            }
            var entry = result.Ok;

            // Get the variable which the program uses to indicate it is ready to move to the next round
            var state = new MachineState(new DefaultValueDeviceNetwork());
            var done  = state.GetVariable($":{challenge.CheckIndicator}");

            // Begin counting how long it takes to verify (for profiling purposes)
            var timer = new Stopwatch();

            timer.Start();

            // Run through test cases one by one
            var overflowIters = _config.MaxItersOverflow;
            var totalRuntime  = 0u;
            var pc            = 0;

            for (var i = 0; i < Math.Min(inputs.Count, outputs.Count); i++)
            {
                // Set inputs
                var input = inputs[i];
                foreach (var(key, value) in input)
                {
                    state.GetVariable($":{key}").Value = value;
                }

                // Clear completion indicator
                done.Value = 0;

                // Run lines until completion indicator is set or execution time limit is exceeded
                var limit = 0;
                while (!done.Value.ToBool())
                {
                    // Check if this test has exceed it's time limit
                    if (limit++ > _config.MaxTestIters)
                    {
                        //If so use iterations from the overflow pool
                        overflowIters--;

                        //Once the overflow pool is empty too, fail
                        if (overflowIters <= 0)
                        {
                            return(null, new Failure(FailureType.RuntimeTooLong, null));
                        }
                    }

                    totalRuntime++;
                    try
                    {
                        // If line if blank, just move to the next line
                        if (pc >= entry.Lines.Count)
                        {
                            pc++;
                        }
                        else
                        {
                            pc = entry.Lines[pc].Evaluate(pc, state);
                        }
                    }
                    catch (ExecutionException)
                    {
                        pc++;
                    }

                    // loop around if program counter goes over max
                    if (pc >= 20)
                    {
                        pc = 0;
                    }
                }

                // Check this test case with the current scoring mode
                var scoreFailure = scoreMode.CheckCase(input, outputs[i], state);
                if (scoreFailure != null)
                {
                    return(null, scoreFailure);
                }
            }

            Console.WriteLine($"Verified {totalRuntime} ticks, {timer.ElapsedMilliseconds}ms runtime");

            // Calculate score
            var codeLength = yolol.Replace("\n", "").Length;
            var score      = scoreMode.FinalizeScore(
                (uint)inputs.Count,
                totalRuntime,
                codeLength
                );

            return(new Success((uint)score, (uint)totalRuntime, (uint)codeLength), null);
        }
Пример #13
0
 public Value GetVariable(string v)
 {
     return(_machineState.GetVariable(v).Value);
 }
Пример #14
0
        public static void Compare(Program ast, int ticks)
        {
            // Compile setup
            var ext       = new ExternalsMap();
            var lines     = Math.Max(20, ast.Lines.Count);
            var compiled  = ast.Compile(ext, lines);
            var internals = new Value[compiled.InternalsMap.Count];

            Array.Fill(internals, new Value((Number)0));
            var externals = new Value[ext.Count];

            Array.Fill(externals, new Value((Number)0));

            // Interpret setup
            var maxLines = Math.Max(20, ast.Lines.Count);

            int CheckPc(int pc)
            {
                if (pc >= maxLines)
                {
                    return(0);
                }
                if (pc < 0)
                {
                    return(0);
                }
                return(pc);
            }

            var pc = 0;
            var nt = new DeviceNetwork();
            var st = new MachineState(nt, (ushort)maxLines);

            for (var i = 0; i < ticks; i++)
            {
                if (pc >= ast.Lines.Count)
                {
                    pc++;
                }
                else
                {
                    try
                    {
                        pc = ast.Lines[pc].Evaluate(pc, st);
                    }
                    catch (ExecutionException)
                    {
                        pc++;
                    }
                }
                pc = CheckPc(pc);

                compiled.Tick(internals, externals);

                foreach (var item in compiled.InternalsMap)
                {
                    var interpretedVal = st.GetVariable(item.Key.Name).Value;
                    var compiledVal    = internals[item.Value];
                    Assert.AreEqual(interpretedVal, compiledVal, $"varname:{item.Key} ticks:{i}");
                }

                foreach (var item in ext)
                {
                    var interpretedVal = st.GetVariable(item.Key.Name).Value;
                    var compiledVal    = externals[item.Value];
                    Assert.AreEqual(interpretedVal, compiledVal, $"varname:{item.Key} ticks:{i}");
                }
            }
        }
Пример #15
0
        public async Task <(Success?, Failure?)> Verify(Challenge.Challenge challenge, string yolol)
        {
            await Task.CompletedTask;

            if (challenge.ScoreMode != Challenge.ScoreMode.BasicScoring)
            {
                throw new NotImplementedException($"Score mode `{challenge.ScoreMode}` is not implemented");
            }

            // Retrieve the test cases for the challenge
            var(inputs, outputs) = GetTests(challenge);

            // Check input program is 20x70
            var lines = yolol.Split("\n");

            if (lines.Length > 20 || lines.Any(l => l.Length > 70))
            {
                return(null, new Failure(FailureType.ProgramTooLarge, null));
            }

            // parse the entry program
            var result = Parser.ParseProgram(yolol);

            if (!result.IsOk)
            {
                return(null, new Failure(FailureType.ParseFailed, result.Err.ToString()));
            }

            var entry = result.Ok;

            // Get the variable which the program uses to indicate it is ready to move to the next round
            var state = new MachineState(new DefaultValueDeviceNetwork());
            var done  = state.GetVariable($":{challenge.CheckIndicator}");

            // Begin counting how long it takes to verify
            var timer = new Stopwatch();

            timer.Start();

            // Run through test cases one by one
            var overflowIters = _config.MaxItersOverflow;
            var totalRuntime  = 0u;
            var pc            = 0;

            for (var i = 0; i < Math.Min(inputs.Count, outputs.Count); i++)
            {
                // Set inputs
                var input = inputs[i];
                foreach (var(key, value) in input)
                {
                    state.GetVariable($":{key}").Value = value;
                }

                // Clear completion indicator
                done.Value = 0;

                // Run lines until completion indicator is set or execution time limit is exceeded
                var limit = 0;
                while (!done.Value.ToBool())
                {
                    // Check if this test has exceed it's time limit
                    if (limit++ > _config.MaxTestIters)
                    {
                        //If so use iterations from the overflow pool
                        overflowIters--;

                        //Once the overflow pool is empty too, fail
                        if (overflowIters <= 0)
                        {
                            return(null, new Failure(FailureType.RuntimeTooLong, null));
                        }
                    }

                    totalRuntime++;
                    try
                    {
                        // If line if blank, just move to the next line
                        if (pc >= entry.Lines.Count)
                        {
                            pc++;
                        }
                        else
                        {
                            pc = entry.Lines[pc].Evaluate(pc, state);
                        }
                    }
                    catch (ExecutionException)
                    {
                        pc++;
                    }

                    // loop around if program counter goes over max
                    if (pc >= 20)
                    {
                        pc = 0;
                    }
                }

                // Check outputs
                foreach (var(key, value) in outputs[i])
                {
                    var v = state.GetVariable($":{key}");
                    if ((v.Value != value).ToBool())
                    {
                        var ii = string.Join(",", input.Select(b => $"`:{b.Key}={b.Value.ToHumanString()}`"));
                        var oo = string.Join(",", outputs[i].Select(b => $"`:{b.Key}={b.Value.ToHumanString()}`"));

                        return(null, new Failure(FailureType.IncorrectResult, $"For inputs {ii} expected outputs {oo}, got `{v.Value.ToHumanString()}` for `:{key}`"));
                    }
                }
            }

            Console.WriteLine($"Verified {totalRuntime} ticks, {timer.ElapsedMilliseconds}ms runtime");

            // Calculate score
            var codeLength = yolol.Replace("\n", "").Length;
            var score      = _score.Score(
                (uint)inputs.Count,
                totalRuntime,
                codeLength
                );

            return(new Success((uint)score, (uint)totalRuntime, (uint)codeLength), null);
        }