context: 
  /*
   *  MetaphysicsIndustries.Solus
   *  Copyright (C) 2006-2021 Metaphysics Industries, Inc., Richard Sartor
   *
   *  This library is free software; you can redistribute it and/or
   *  modify it under the terms of the GNU Lesser General Public
   *  License as published by the Free Software Foundation; either
   *  version 3 of the License, or (at your option) any later version.
   *
   *  This library is distributed in the hope that it will be useful,
   *  but WITHOUT ANY WARRANTY; without even the implied warranty of
   *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   *  Lesser General Public License for more details.
   *
   *  You should have received a copy of the GNU Lesser General Public
   *  License along with this library; if not, write to the Free Software
   *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301
   *  USA
   *
   */
  
  using MetaphysicsIndustries.Solus.Evaluators;
  using MetaphysicsIndustries.Solus.Expressions;
  using MetaphysicsIndustries.Solus.Functions;
  using MetaphysicsIndustries.Solus.Values;
  using NUnit.Framework;
  
  namespace MetaphysicsIndustries.Solus.Test.EvaluatorsT.BasicEvaluatorT
  {
      [TestFixture]
      public class EvalIntervalTest
      {
          [Test]
          public void SingleIntervalEval()
          {
              // given
              var eval = new BasicEvaluator();
              var expr = new FunctionCall(MultiplicationOperation.Value,
                  new VariableAccess("x"),
                  new VariableAccess("x"));
              var env = new SolusEnvironment();
              var interval = new VarInterval("x",
                  new Interval(2, false, 6, false, false));
              var numSteps = 5;
              var store = new StoreOp1<Number>();
              // when
              eval.EvalInterval(expr, env, interval, numSteps, store);
              // then
              Assert.IsNotNull(store.Values);
              Assert.AreEqual(5, store.Values.Length);
              Assert.AreEqual(4, store.Values[0].Value);
              Assert.AreEqual(9, store.Values[1].Value);
              Assert.AreEqual(16, store.Values[2].Value);
              Assert.AreEqual(25, store.Values[3].Value);
              Assert.AreEqual(36, store.Values[4].Value);
          }
  
          [Test]
          public void StoreToVector()
          {
              // given
              var eval = new BasicEvaluator();
              var expr = new FunctionCall(MultiplicationOperation.Value,
                  new VariableAccess("x"),
                  new VariableAccess("x"));
              var env = new SolusEnvironment();
              var interval = new VarInterval("x",
                  new Interval(2, false, 6, false, false));
              var numSteps = 5;
              var store = new VectorStoreOp();
              // when
              eval.EvalInterval(expr, env, interval, numSteps, store);
              // then
              var result = store.GetResult();
              Assert.AreEqual(5, result.Length);
              Assert.AreEqual(4, result[0].ToNumber().Value);
              Assert.AreEqual(9, result[1].ToNumber().Value);
              Assert.AreEqual(16, result[2].ToNumber().Value);
              Assert.AreEqual(25, result[3].ToNumber().Value);
              Assert.AreEqual(36, result[4].ToNumber().Value);
          }
  
          [Test]
          public void TwoIntervalEval()
          {
              // given
              var eval = new BasicEvaluator();
              var expr = new FunctionCall(MultiplicationOperation.Value,
                  new VariableAccess("x"),
                  new VariableAccess("y"));
              var env = new SolusEnvironment();
              var interval1 = new VarInterval("x",
                  new Interval(2, false, 6, false, false));
              var numSteps1 = 5;
              var interval2 = new VarInterval("y",
                  new Interval(7, false, 12, false, false));
              var numSteps2 = 6;
              var store = new StoreOp2<Number>();
              // when
              eval.EvalInterval(expr, env,
                  interval1, numSteps1,
                  interval2, numSteps2,
                  store);
              // then
              Assert.IsNotNull(store.Values);
              Assert.AreEqual(5, store.Values.GetLength(0));
              Assert.AreEqual(6, store.Values.GetLength(1));
  
              Assert.AreEqual(14, store.Values[0, 0].Value);
              Assert.AreEqual(16, store.Values[0, 1].Value);
              Assert.AreEqual(18, store.Values[0, 2].Value);
              Assert.AreEqual(20, store.Values[0, 3].Value);
              Assert.AreEqual(22, store.Values[0, 4].Value);
              Assert.AreEqual(24, store.Values[0, 5].Value);
  
              Assert.AreEqual(21, store.Values[1, 0].Value);
              Assert.AreEqual(24, store.Values[1, 1].Value);
              Assert.AreEqual(27, store.Values[1, 2].Value);
              Assert.AreEqual(30, store.Values[1, 3].Value);
              Assert.AreEqual(33, store.Values[1, 4].Value);
              Assert.AreEqual(36, store.Values[1, 5].Value);
  
              Assert.AreEqual(28, store.Values[2, 0].Value);
              Assert.AreEqual(32, store.Values[2, 1].Value);
              Assert.AreEqual(36, store.Values[2, 2].Value);
              Assert.AreEqual(40, store.Values[2, 3].Value);
              Assert.AreEqual(44, store.Values[2, 4].Value);
              Assert.AreEqual(48, store.Values[2, 5].Value);
  
              Assert.AreEqual(35, store.Values[3, 0].Value);
              Assert.AreEqual(40, store.Values[3, 1].Value);
              Assert.AreEqual(45, store.Values[3, 2].Value);
              Assert.AreEqual(50, store.Values[3, 3].Value);
              Assert.AreEqual(55, store.Values[3, 4].Value);
              Assert.AreEqual(60, store.Values[3, 5].Value);
  
              Assert.AreEqual(42, store.Values[4, 0].Value);
              Assert.AreEqual(48, store.Values[4, 1].Value);
              Assert.AreEqual(54, store.Values[4, 2].Value);
              Assert.AreEqual(60, store.Values[4, 3].Value);
              Assert.AreEqual(66, store.Values[4, 4].Value);
              Assert.AreEqual(72, store.Values[4, 5].Value);
          }
  
          [Test]
          public void StoreToMatrix()
          {
              // given
              var eval = new BasicEvaluator();
              var expr = new FunctionCall(MultiplicationOperation.Value,
                  new VariableAccess("x"),
                  new VariableAccess("y"));
              var env = new SolusEnvironment();
              var interval1 = new VarInterval("x",
                  new Interval(2, false, 6, false, false));
              var numSteps1 = 5;
              var interval2 = new VarInterval("y",
                  new Interval(7, false, 12, false, false));
              var numSteps2 = 6;
              var store = new MatrixStoreOp();
              // when
              eval.EvalInterval(expr, env,
                  interval1, numSteps1,
                  interval2, numSteps2,
                  store);
              // then
              var result = store.GetResult();
              Assert.AreEqual(5, result.RowCount);
              Assert.AreEqual(6, result.ColumnCount);
  
              Assert.AreEqual(14, result[0, 0].ToNumber().Value);
              Assert.AreEqual(16, result[0, 1].ToNumber().Value);
              Assert.AreEqual(18, result[0, 2].ToNumber().Value);
              Assert.AreEqual(20, result[0, 3].ToNumber().Value);
              Assert.AreEqual(22, result[0, 4].ToNumber().Value);
              Assert.AreEqual(24, result[0, 5].ToNumber().Value);
  
              Assert.AreEqual(21, result[1, 0].ToNumber().Value);
              Assert.AreEqual(24, result[1, 1].ToNumber().Value);
              Assert.AreEqual(27, result[1, 2].ToNumber().Value);
              Assert.AreEqual(30, result[1, 3].ToNumber().Value);
              Assert.AreEqual(33, result[1, 4].ToNumber().Value);
              Assert.AreEqual(36, result[1, 5].ToNumber().Value);
  
              Assert.AreEqual(28, result[2, 0].ToNumber().Value);
              Assert.AreEqual(32, result[2, 1].ToNumber().Value);
              Assert.AreEqual(36, result[2, 2].ToNumber().Value);
              Assert.AreEqual(40, result[2, 3].ToNumber().Value);
              Assert.AreEqual(44, result[2, 4].ToNumber().Value);
              Assert.AreEqual(48, result[2, 5].ToNumber().Value);
  
              Assert.AreEqual(35, result[3, 0].ToNumber().Value);
              Assert.AreEqual(40, result[3, 1].ToNumber().Value);
              Assert.AreEqual(45, result[3, 2].ToNumber().Value);
              Assert.AreEqual(50, result[3, 3].ToNumber().Value);
              Assert.AreEqual(55, result[3, 4].ToNumber().Value);
              Assert.AreEqual(60, result[3, 5].ToNumber().Value);
  
              Assert.AreEqual(42, result[4, 0].ToNumber().Value);
              Assert.AreEqual(48, result[4, 1].ToNumber().Value);
              Assert.AreEqual(54, result[4, 2].ToNumber().Value);
              Assert.AreEqual(60, result[4, 3].ToNumber().Value);
              Assert.AreEqual(66, result[4, 4].ToNumber().Value);
              Assert.AreEqual(72, result[4, 5].ToNumber().Value);
          }
  
          [Test]
          public void ThreeIntervalEval()
          {
              // given
              var eval = new BasicEvaluator();
              var expr = new FunctionCall(MultiplicationOperation.Value,
                  new VariableAccess("x"),
                  new VariableAccess("y"),
                  new VariableAccess("z"));
              var env = new SolusEnvironment();
              var interval1 = new VarInterval("x",
  
gt:                 new Interval(2, false, 3, false, false));