public void Merge(int rowCount0, int rowCount1, Type[] colTypes0, string[] colNames0, Type[] colTypes1, string[] colNames1)
        {
            //Arrange
            var frame0 = BasicFrameGenerator.CreateTable(rowCount0, colTypes0, colNames0);
            var frame1 = BasicFrameGenerator.CreateTable(rowCount1, colTypes1, colNames1);

            var merger = new BasicFrameMerger();

            //Act
            IFrame frameX = merger.Merge(frame0, frame1, Guid.NewGuid());

            //Assert
            Assert.NotNull(frameX);

            int expectedColCount = frame0.ColumnCount + frame1.ColumnCount;

            Assert.Equal(expectedColCount, frameX.ColumnCount);
            Assert.Equal(frame0.RowCount, frameX.RowCount);
            Assert.Equal(frame1.RowCount, frameX.RowCount);

            // --------------
            BasicFrame baseFrame = frameX as BasicFrame;

            int colIndex = 0;
            int rowIndex = 0;
            for (int i = 0; i < colTypes0.Length; i++)
            {
                for (int j = 0; j < baseFrame.RowCount; j++)
                {
                    rowIndex = j;
                    colIndex = i;

                    bool result = baseFrame.Rows[rowIndex][colIndex].Equals(frame0.Rows[rowIndex][colIndex]);
                    Assert.True(result, "Items should match");

                    if (baseFrame.Columns[colIndex].DataType == typeof(int))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = int.MinValue;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(double))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = double.MinValue;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(string))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = (rowIndex + colIndex).ToString();
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(DateTime))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = DateTime.Now;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(bool))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = !((bool)frame0.Rows[rowIndex][colIndex]);
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(Guid))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = Guid.NewGuid();
                    }

                    result = baseFrame.Rows[rowIndex][colIndex] == frame0.Rows[rowIndex][colIndex];
                    Assert.False(result, "A: Items should NOT match after change");
                }
            }

            int offset = colTypes0.Length;
            int k = 0;
            for (int i = 0; i < colTypes1.Length; i++)
            {
                k = (i + offset);

                for (int j = 0; j < baseFrame.RowCount; j++)
                {
                    rowIndex = j;
                    colIndex = k;

                    bool result = baseFrame.Rows[rowIndex][colIndex].Equals(frame1.Rows[rowIndex][i]);
                    Assert.True(result, "Items should match");

                    if (baseFrame.Columns[colIndex].DataType == typeof(int))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = int.MinValue;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(double))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = double.MinValue;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(string))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = (rowIndex + colIndex).ToString();
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(DateTime))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = DateTime.Now;
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(bool))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = !((bool)frame1.Rows[rowIndex][i]);
                    }
                    else if (baseFrame.Columns[colIndex].DataType == typeof(Guid))
                    {
                        baseFrame.Rows[rowIndex][colIndex] = Guid.NewGuid();
                    }

                    result = baseFrame.Rows[rowIndex][colIndex] == frame1.Rows[rowIndex][i];
                    Assert.False(result, "B: Items should NOT match after change");
                }
            }
        }
        public void Merge_Throws_Ex_If_Row_Counts_Do_Not_Match(int rowCount0, int rowCount1, Type[] colTypes0, Type[] colTypes1)
        {
            //Arrange
            var frame0 = BasicFrameGenerator.CreateTable(rowCount0, colTypes0) as BasicFrame;
            var frame1 = BasicFrameGenerator.CreateTable(rowCount1, colTypes1) as BasicFrame;

            var merger = new BasicFrameMerger();

            //Act, Assert
            var ex = Assert.Throws<ArgumentException>(() => merger.Merge(frame0, frame1, Guid.NewGuid()));
        }
        public void Merge_Throws_Ex_If_Frame_Type_Is_Not_Supported_For_Second_Param()
        {
            //Arrange
            var frame0 = BasicFrameGenerator.CreateTable(0, new Type[] { }) as BasicFrame;
            var frame1 = new DummyFrame();

            var merger = new BasicFrameMerger();

            //Act, Assert
            var ex = Assert.Throws<ArgumentException>(() => merger.Merge(frame0, frame1, Guid.NewGuid()));
        }
        public void Merge_Throws_Ex_If_Both_Inputs_Are_Same_Instance()
        {
            //Arrange
            IFrame frame0 = BasicFrameGenerator.CreateTable(1, new Type[] { typeof(string) });
            IFrame frame1 = frame0;

            BasicFrameMerger merger = new BasicFrameMerger();

            //Act, Assert
            var ex = Assert.Throws<ArgumentException>(() => merger.Merge(frame0, frame1, Guid.NewGuid()));
        }
        public void Merge_Returns_New_Frame_With_Specified_Id()
        {
            //Arrange
            var frame0 = BasicFrameGenerator.CreateTable(2, new Type[] { typeof(int) });
            var frame1 = BasicFrameGenerator.CreateTable(2, new Type[] { typeof(double) });

            Guid id = Guid.NewGuid();
            var merger = new BasicFrameMerger();

            //Act
            IFrame frameX = merger.Merge(frame0, frame1, id);

            //Assert
            Assert.NotNull(frameX);
            Assert.Equal(id, frameX.Id);
        }
        public void Merge_Returned_Frame_Has_All_Unique_Col_Names(int rowCount0, int rowCount1, Type[] colTypes0, string[] colNames0, Type[] colTypes1, string[] colNames1)
        {
            //Arrange
            var frame0 = BasicFrameGenerator.CreateTable(rowCount0, colTypes0, colNames0) as BasicFrame;
            var frame1 = BasicFrameGenerator.CreateTable(rowCount1, colTypes1, colNames1) as BasicFrame;

            var merger = new BasicFrameMerger();

            //Act
            IFrame frameX = merger.Merge(frame0, frame1, Guid.NewGuid());

            //Assert
            Assert.NotNull(frameX);

            int expectedColCount = frame0.ColumnCount + frame1.ColumnCount;

            Assert.Equal(expectedColCount, frameX.ColumnCount);
            Assert.Equal(frame0.RowCount, frameX.RowCount);
            Assert.Equal(frame1.RowCount, frameX.RowCount);

            //-----------------------------------------------------
            // Verify all col names are unique
            for (int i = 0; i < frameX.ColumnNames.Length; i++)
            {
                for (int j = 0; j < frameX.ColumnNames.Length; j++)
                {
                    if (i == j)
                        continue;
                    Assert.NotEqual(frameX.ColumnNames[i], frameX.ColumnNames[j]);
                }
            }
        }