public TrinomialTree(StochasticProcess1D process,
                             TimeGrid timeGrid,
                             bool isPositive /*= false*/)
            : base(timeGrid.size())
        {
            branchings_ = new List <Branching>();
            dx_         = new InitializedList <double>(1);
            timeGrid_   = timeGrid;
            x0_         = process.x0();

            int nTimeSteps = timeGrid.size() - 1;
            int jMin       = 0;
            int jMax       = 0;

            for (int i = 0; i < nTimeSteps; i++)
            {
                double t  = timeGrid[i];
                double dt = timeGrid.dt(i);

                //Variance must be independent of x
                double v2 = process.variance(t, 0.0, dt);
                double v  = Math.Sqrt(v2);
                dx_.Add(v * Math.Sqrt(3.0));

                Branching branching = new Branching();
                for (int j = jMin; j <= jMax; j++)
                {
                    double x    = x0_ + j * dx_[i];
                    double m    = process.expectation(t, x, dt);
                    int    temp = (int)(Math.Floor((m - x0_) / dx_[i + 1] + 0.5));

                    if (isPositive)
                    {
                        while (x0_ + (temp - 1) * dx_[i + 1] <= 0)
                        {
                            temp++;
                        }
                    }

                    double e  = m - (x0_ + temp * dx_[i + 1]);
                    double e2 = e * e;
                    double e3 = e * Math.Sqrt(3.0);

                    double p1 = (1.0 + e2 / v2 - e3 / v) / 6.0;
                    double p2 = (2.0 - e2 / v2) / 3.0;
                    double p3 = (1.0 + e2 / v2 + e3 / v) / 6.0;

                    branching.add(temp, p1, p2, p3);
                }
                branchings_.Add(branching);

                jMin = branching.jMin();
                jMax = branching.jMax();
            }
        }