public static ModulusNumber F(int w, int h)
        {
            if (w == 0 || h == 0)
            {
                return(ModulusNumber.One);
            }

            ModulusEvenOdd[] previous = new ModulusEvenOdd[w];
            ModulusEvenOdd[] current  = new ModulusEvenOdd[w];

            for (int i = 0; i < w; i++)
            {
                current[i] = ModulusEvenOdd.OneEven;
            }

            for (int i = 1; i < h; i++)
            {
                if (i % 10 == 0)
                {
                    Console.WriteLine(i);
                }

                ModulusEvenOdd[] temp = previous;
                previous = current;
                current  = temp;

                for (int j = 1; j <= w; j++)
                {
                    ModulusEvenOdd result = Get(current, j - 1) + Get(previous, j).Swap;

                    for (int k = 1; k < j; k++)
                    {
                        ModulusEvenOdd subResult0 = Get(previous, k).Swap;
                        ModulusEvenOdd subResult1 = Get(current, j - k - 1);
                        ModulusEvenOdd total      = subResult0 * subResult1;
                        result += total;
                    }

                    Set(current, j, result);
                }
            }

            return(current[w - 1].Odd - previous[w - 1].Odd);
        }
 static void Set(ModulusEvenOdd[] values, int w, ModulusEvenOdd value)
 {
     values[w - 1] = value;
 }
        private static ModulusNumber Solve(BigInteger w, int h)
        {
            int           size    = h * 2;
            ModulusMatrix matrix  = new ModulusMatrix(size, size);
            ModulusMatrix initial = new ModulusMatrix(size, 1);
            ModulusMatrix temp    = new ModulusMatrix(size, 1);

            // matrix loop
            for (int i = 0; i < size; i++)
            {
                for (int j = 0; j < size; j++)
                {
                    if (j == i)
                    {
                        initial[j, 0] = ModulusNumber.One;
                    }
                    else
                    {
                        initial[j, 0] = ModulusNumber.Zero;
                    }

                    temp[j, 0] = ModulusNumber.Zero;
                }

                // temp loop
                for (int j = 0; j < h; j++)
                {
                    ModulusEvenOdd total = new ModulusEvenOdd();

                    // initial loop
                    for (int k = 0; k < h; k++)
                    {
                        ModulusEvenOdd value = Get(initial, k);

                        if (k >= j)
                        {
                            total += value;
                        }
                        else
                        {
                            if (((j - k) % 2) == 1)
                            {
                                total += value.Swap;
                            }
                            else
                            {
                                total += value;
                            }
                        }
                    }

                    Set(temp, j, total);
                }

                matrix.SetColumn(i, temp.GetColumn(0));
            }

            for (int i = 0; i < h; i++)
            {
                if (i % 2 == 0)
                {
                    Set(initial, i, ModulusEvenOdd.OneEven);
                }
                else
                {
                    Set(initial, i, ModulusEvenOdd.OneOdd);
                }
            }

            ModulusMatrix powerMatrix = ModulusMatrix.Power(matrix, w - 1);
            ModulusMatrix result      = powerMatrix * initial;

            ModulusNumber sum = ModulusNumber.Zero;

            for (int i = 0; i < h; i++)
            {
                sum += result[i * 2 + 1, 0];
            }

            return(sum);
        }
 private static void Set(ModulusMatrix values, int index, ModulusEvenOdd value)
 {
     values[index * 2, 0]     = value.Even;
     values[index * 2 + 1, 0] = value.Odd;
 }
        private static ModulusEvenOdd Get(ModulusMatrix values, int index)
        {
            ModulusEvenOdd result = new ModulusEvenOdd(values[index * 2, 0], values[index * 2 + 1, 0]);

            return(result);
        }
Exemple #6
0
        private static ModulusNumber Solve(int w, int h)
        {
            ModulusEvenOdd[] previous = new ModulusEvenOdd[h];
            ModulusEvenOdd[] current  = new ModulusEvenOdd[h];

            for (int i = 0; i < h; i++)
            {
                if (i % 2 == 0)
                {
                    current[i] = ModulusEvenOdd.OneEven;
                }
                else
                {
                    current[i] = ModulusEvenOdd.OneOdd;
                }
            }

            for (int i = 1; i < w; i++)
            {
                Console.WriteLine(i);

                ModulusEvenOdd[] temp = previous;
                previous = current;
                current  = temp;

                for (int j = 0; j < h; j++)
                {
                    ModulusEvenOdd total = new ModulusEvenOdd();

                    for (int k = 0; k < h; k++)
                    {
                        ModulusEvenOdd value = previous[k];

                        if (k >= j)
                        {
                            total += value;
                        }
                        else
                        {
                            if (((j - k) % 2) == 1)
                            {
                                total += value.Swap;
                            }
                            else
                            {
                                total += value;
                            }
                        }
                    }

                    current[j] = total;
                }
            }

            ModulusNumber sum = ModulusNumber.Zero;

            for (int i = 0; i < h; i++)
            {
                sum += current[i].Odd;
            }

            return(sum);
        }