Пример #1
0
    def implicit(self, N, M):
        S = self.S
        K = self.K
        r = self.r
        q = self.q
        T = self.T
        sigma = self.sigma

        # Step 1:
        t_delta = T / N
        S_max = 2 * K
        S_delta = S_max / M

        # Step 2:
        Fc_hat = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fp_hat = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fc = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fp = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        for j in range(M + 1):
            Fc[j][N] = max(j * S_delta - K, 0)
            Fp[j][N] = max(K - j * S_delta, 0)

        # Step 3:
        for i in range(N - 1, -1, -1):
            # Step 3.1:
            for j in range(1, M):
                Fc_hat[j][i + 1] = Fc[j][i + 1]
                Fp_hat[j][i + 1] = Fp[j][i + 1]
            Fc_hat[0][i + 1] = 0
            Fc_hat[M][i + 1] = S_max - K * math.exp(-r * (N - i) * t_delta)
            Fp_hat[0][i + 1] = K * math.exp(-r * (N - i) * t_delta)
            Fp_hat[M][i + 1] = 0

            # Step 3.2:
            A = [[0 for _ in range(M + 1)] for _ in range(M + 1)]
            A[0][0] = 1
            for j in range(1, M):
                A[j][j -
                     1] = 0.5 * t_delta * ((r - q) * j - sigma * sigma * j * j)
                A[j][j] = 1 + t_delta * (sigma * sigma * j * j + r)
                A[j][j + 1] = -0.5 * t_delta * (sigma * sigma * j * j +
                                                (r - q) * j)
            A[M][M] = 1
            A_inv = matrixOperations.inverse(A)
            Fc_hat_col = [[Fc_hat[j][i + 1]] for j in range(M + 1)]
            Fp_hat_col = [[Fp_hat[j][i + 1]] for j in range(M + 1)]
            Fc_col = matrixOperations.multiply(A_inv, Fc_hat_col)
            Fp_col = matrixOperations.multiply(A_inv, Fp_hat_col)
            for j in range(M + 1):
                Fc[j][i] = Fc_col[j][0]
                Fp[j][i] = Fp_col[j][0]

        # Step 4:
        k = int(math.floor(S / S_delta))

        # Step 5:
        Vc = Fc[k][0] + (Fc[k + 1][0] - Fc[k][0]) / S_delta * (S - k * S_delta)
        Vp = Fp[k][0] + (Fp[k + 1][0] - Fp[k][0]) / S_delta * (S - k * S_delta)

        return {"call": Vc, "put": Vp}
Пример #2
0
def crankNicolson(S, K, r, q, T, sigma, N, M):
    # Step 1:
    t_delta = T / N
    S_max = 2 * K
    S_delta = S_max / M

    # Step 2:
    Fc = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
    Fp = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
    for j in range(M + 1):
        Fc[j][N] = max(j * S_delta - K, 0)
        Fp[j][N] = max(K - j * S_delta, 0)

    # Step 3:
    for i in range(N - 1, -1, -1):
        # Step 3.1, 3.2:
        bc = [[0] for _ in range(M + 1)]
        bp = [[0] for _ in range(M + 1)]
        for j in range(1, M):
            alpha = 0.25 * t_delta * (sigma * sigma * j * j - (r - q) * j)
            beta = -0.5 * t_delta * (sigma * sigma + r)
            gamma = 0.25 * t_delta * (sigma * sigma * j * j + (r - q) * j)
            bc[j][0] = alpha * Fc[j - 1][i + 1] + beta * Fc[j][i + 1] + gamma * Fc[j + 1][i + 1]
            bp[j][0] = alpha * Fp[j - 1][i + 1] + beta * Fp[j][i + 1] + gamma * Fp[j + 1][i + 1]
        bc[0][0] = 0
        bc[M][0] = S_max - K * math.exp(-r * (N - i) * t_delta)
        bp[0][0] = K * math.exp(-r * (N - i) * t_delta)
        bp[M][0] = 0

        # Step 3.3:
        M1 = [[0 for _ in range(M + 1)] for _ in range(M + 1)]
        M1[0][0] = 1
        M1[M][M] = 1

        for j in range(1, M):
            M1[j][j - 1] = 0.25 * t_delta * (sigma * sigma * j * j - (r - q) * j)
            M1[j][j] = -0.5 * t_delta * (sigma * sigma + r)
            M1[j][j + 1] = 0.25 * t_delta * (sigma * sigma * j * j + (r - q) * j)

        M1_inv = matrixOperations.inverse(M1)
        Fc_col = matrixOperations.multiply(M1_inv, bc)
        Fp_col = matrixOperations.multiply(M1_inv, bp)
        for j in range(M + 1):
            Fc[j][i] = Fc_col[j][0]
            Fp[j][i] = Fp_col[j][0]

    # Step 4:
    k = int(math.floor(S / S_delta))

    # Step 5:
    Vc = Fc[k][0] + (Fc[k + 1][0] - Fc[k][0]) / S_delta * (S - k * S_delta)
    Vp = Fp[k][0] + (Fp[k + 1][0] - Fp[k][0]) / S_delta * (S - k * S_delta)

    return {"call": Vc, "put": Vp}
    def ImplicitFDM(self, M, N):
        # 1
        t_delta = self.T / N
        S_max = 2 * self.K
        S_delta = S_max / M
        # 2
        Fc_hat = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fp_hat = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fc = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fp = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        for j in range(M + 1):
            Fc[j][N] = max(j * S_delta - self.K, 0)
            Fp[j][N] = max(self.K - j * S_delta, 0)
        # 3
        A = [[0 for _ in range(M + 1)] for _ in range(M + 1)]
        A[0][0] = 1
        for j in range(1, M):
            A[j][j - 1] = 0.5 * t_delta * (
                (self.r - self.q) * j - self.sigma * self.sigma * j * j)
            A[j][j] = 1 + t_delta * (self.sigma * self.sigma * j * j + self.r)
            A[j][j + 1] = -0.5 * t_delta * (self.sigma * self.sigma * j * j +
                                            (self.r - self.q) * j)
        A[M][M] = 1
        A_inv = matrixOperations.inverse(A)

        for i in range(N - 1, -1, -1):
            # 3.1
            for j in range(1, M):
                Fc_hat[j][i + 1] = Fc[j][i + 1]
                Fp_hat[j][i + 1] = Fp[j][i + 1]
            Fc_hat[0][i + 1] = 0
            Fc_hat[M][i + 1] = S_max - self.K * exp(-self.r *
                                                    (N - i) * t_delta)
            Fp_hat[0][i + 1] = self.K * exp(-self.r * (N - i) * t_delta)
            Fp_hat[M][i + 1] = 0
            # 3.2

            Fc_hat_col = [[Fc_hat[j][i + 1]] for j in range(M + 1)]
            Fp_hat_col = [[Fp_hat[j][i + 1]] for j in range(M + 1)]
            Fc_col = matrixOperations.multiply(A_inv, Fc_hat_col)
            Fp_col = matrixOperations.multiply(A_inv, Fp_hat_col)
            for j in range(M + 1):
                Fc[j][i] = Fc_col[j][0]
                Fp[j][i] = Fp_col[j][0]
        # 4
        k = int(floor(self.S / S_delta))
        # 5
        Vc = (Fc[k][0] + (Fc[k + 1][0] - Fc[k][0]) / S_delta *
              (self.S - k * S_delta))
        Vp = (Fp[k][0] + (Fp[k + 1][0] - Fp[k][0]) / S_delta *
              (self.S - k * S_delta))
        return {"call": Vc, "put": Vp}
Пример #4
0
    def fit(self, x, y):
        x = buildX(x)
        y = buildY(y)

        # xT * x
        result = multiply(transposed(x), x)
        # inverse(xT * x)
        result = inverse(result)
        # inverse(xT * x) * xT
        result = multiply(result, transposed(x))
        # inverse(xT * x) * xT * y
        result = multiply(result, y)

        self.intercept_ = result[0][0]  # w0
        self.coef_[0] = result[1][0]  # w1
        self.coef_[1] = result[2][0]  # w2
def rootMeanSquareError(answers, coefficients, x_bar):
    error_vector = matrixOperations.subtract(
        answers, matrixOperations.multiply(coefficients, x_bar))
    s = 0
    for i in error_vector:
        s = s + i[0]**2

    return (s / len(error_vector))**0.5
def jacobi(D, L, U, solution_vector):
    vector_x_0 = [[0] for i in range(len(solution_vector))]
    tol = 10**-6
    D_inverse = [[0 for i in range(len(D))] for j in range(len(D))]
    for i in range(len(D)):
        D_inverse[i][i] = 1 / D[i][i]
    for i in range(10**6):
        vector_x_1 = matrixOperations.multiply(
            D_inverse,
            matrixOperations.subtract(
                solution_vector,
                matrixOperations.multiply(matrixOperations.add(L, U),
                                          vector_x_0)))
        if (matrixOperations.isEqual(vector_x_1, vector_x_0, tol)):
            vector_x_0 = [i[:] for i in vector_x_1]
            print("Required", i, "steps")
            break
        vector_x_0 = [i[:] for i in vector_x_1]

    matrixOperations.printMatrix(vector_x_0)
    def CrankNicolsonM(self, M, N):
        # 1
        t_delta = self.T / N
        S_max = 2 * self.K
        S_delta = S_max / M
        # 2
        Fc = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        Fp = [[0 for _ in range(N + 1)] for _ in range(M + 1)]
        for j in range(M + 1):
            Fc[j][N] = max(j * S_delta - self.K, 0)
            Fp[j][N] = max(self.K - j * S_delta, 0)

        # 3
        M1 = [[0 for _ in range(M + 1)] for _ in range(M + 1)]
        M1[0][0] = 1
        M1[M][M] = 1

        for j in range(1, M):
            M1[j][j - 1] = -0.25 * t_delta * (self.sigma * self.sigma * j * j -
                                              (self.r - self.q) * j)
            M1[j][j] = 1 + 0.5 * t_delta * (self.sigma * self.sigma * j * j +
                                            self.r)
            M1[j][j + 1] = -0.25 * t_delta * (self.sigma * self.sigma * j * j +
                                              (self.r - self.q) * j)
        M1_inv = matrixOperations.inverse(M1)

        for i in range(N - 1, -1, -1):
            # 3.1 and 3.2:
            bc = [[0] for _ in range(M + 1)]
            bp = [[0] for _ in range(M + 1)]
            for j in range(1, M):
                alpha = 0.25 * t_delta * (self.sigma * self.sigma * j * j -
                                          (self.r - self.q) * j)
                beta = -0.5 * t_delta * (self.sigma * self.sigma * j * j +
                                         self.r)
                gamma = 0.25 * t_delta * (self.sigma * self.sigma * j * j +
                                          (self.r - self.q) * j)
                bc[j][0] = (alpha * Fc[j - 1][i + 1] +
                            (1 + beta) * Fc[j][i + 1] +
                            gamma * Fc[j + 1][i + 1])
                bp[j][0] = (alpha * Fp[j - 1][i + 1] +
                            (1 + beta) * Fp[j][i + 1] +
                            gamma * Fp[j + 1][i + 1])
            bc[0][0] = 0
            bc[M][0] = S_max - self.K * exp(-self.r * (N - i) * t_delta)
            bp[0][0] = self.K * exp(-self.r * (N - i) * t_delta)
            bp[M][0] = 0

            # 3.3
            Fc_col = matrixOperations.multiply(M1_inv, bc)
            Fp_col = matrixOperations.multiply(M1_inv, bp)
            for j in range(M + 1):
                Fc[j][i] = Fc_col[j][0]
                Fp[j][i] = Fp_col[j][0]
        # 4
        k = int(floor(self.S / S_delta))
        # 5
        Vc = (Fc[k][0] + (Fc[k + 1][0] - Fc[k][0]) / S_delta *
              (self.S - k * S_delta))
        Vp = (Fp[k][0] + (Fp[k + 1][0] - Fp[k][0]) / S_delta *
              (self.S - k * S_delta))
        return {"call": Vc, "put": Vp}
Пример #8
0
 def test_multiply(self):
     A = [[1, 1, 1], [1, 1, 1], [1, 1, 1]]
     B = [[1, 1, 1], [1, 1, 1], [1, 1, 1]]
     product = [[3, 3, 3], [3, 3, 3], [3, 3, 3]]
     self.assertEqual(multiply(A, B), product)
def leastSquares(A, b):
    A_transpose = matrixOperations.transpose(A)
    return matrixOperations.multiply(
        matrixOperations.multiply(
            matrixOperations.invert(matrixOperations.multiply(A_transpose, A)),
            A_transpose), b)