public class Euler904 {

    static class Fraction {
        long p;
        long q;

        Fraction(long p, long q) {
            this.p = p;
            this.q = q;
        }
    }

    static class Candidate {
        boolean valid = false;
        double diff = 0.0;
        long sum = 0;
        java.math.BigInteger area = java.math.BigInteger.ZERO;
    }

    static double tanThetaFromU(double u) {
        double u2 = u * u;
        return 3.0 * u * (u2 - 1.0) / ((u2 + 1.0) * (u2 + 1.0));
    }

    static Fraction fareyPrev(Fraction lo, Fraction hi, long N) {
        long k = (N + hi.q) / lo.q;
        return new Fraction(k * lo.p - hi.p, k * lo.q - hi.q);
    }

    static Fraction fareyNext(Fraction lo, Fraction hi, long N) {
        long k = (N + lo.q) / hi.q;
        return new Fraction(k * hi.p - lo.p, k * hi.q - lo.q);
    }

    static Fraction[] fareyBounds(double x, long N) {
        java.util.List<Long> a = new java.util.ArrayList<>();
        double y = x;
        for (int i = 0; i < 64; ++i) {
            long ai = (long) Math.floor(y);
            a.add(ai);
            double frac = y - ai;
            if (Math.abs(frac) < 1e-15) {
                break;
            }
            y = 1.0 / frac;
        }

        java.util.List<Long> ps = new java.util.ArrayList<>();
        java.util.List<Long> qs = new java.util.ArrayList<>();
        long pMinus2 = 0;
        long pMinus1 = 1;
        long qMinus2 = 1;
        long qMinus1 = 0;

        for (long ai : a) {
            long p = ai * pMinus1 + pMinus2;
            long q = ai * qMinus1 + qMinus2;
            ps.add(p);
            qs.add(q);
            if (q > N) {
                break;
            }
            pMinus2 = pMinus1;
            pMinus1 = p;
            qMinus2 = qMinus1;
            qMinus1 = q;
        }

        int idx = 0;
        while (idx < qs.size() && qs.get(idx) <= N) {
            ++idx;
        }

        if (idx == 0) {
            return new Fraction[] { new Fraction(0, 1), new Fraction(1, 0) };
        }

        if (idx == qs.size()) {
            return new Fraction[] { new Fraction(ps.get(idx - 1), qs.get(idx - 1)),
                    new Fraction(ps.get(idx - 1), qs.get(idx - 1)) };
        }

        long pPrev = ps.get(idx - 1);
        long qPrev = qs.get(idx - 1);
        long pPrevPrev = (idx >= 2) ? ps.get(idx - 2) : 1;
        long qPrevPrev = (idx >= 2) ? qs.get(idx - 2) : 0;

        long t = (N - qPrevPrev) / qPrev;
        long pCand = pPrevPrev + t * pPrev;
        long qCand = qPrevPrev + t * qPrev;

        if ((double) pPrev / qPrev < x) {
            return new Fraction[] { new Fraction(pPrev, qPrev), new Fraction(pCand, qCand) };
        } else {
            return new Fraction[] { new Fraction(pCand, qCand), new Fraction(pPrev, qPrev) };
        }
    }

    static long gcd(long a, long b) {
        return b == 0 ? a : gcd(b, a % b);
    }

    static boolean isValidFraction(Fraction f, long L) {
        if (f.q <= 0 || f.p <= 0)
            return false;
        if (f.p <= f.q)
            return false;
        if (((f.p + f.q) & 1L) == 0)
            return false;
        if (gcd(f.p, f.q) != 1)
            return false;
        long m = f.p;
        long n = f.q;
        if (m > Math.sqrt(L))
            return false;
        return m * m + n * n <= L;
    }

    static Fraction findValidLower(Fraction lo, Fraction hi, long N, long L) {
        if (lo.p <= lo.q)
            return new Fraction(0, 0);
        for (int steps = 0; steps < 100000; ++steps) {
            if (isValidFraction(lo, L))
                return lo;
            Fraction prev = fareyPrev(lo, hi, N);
            hi = lo;
            lo = prev;
            if (lo.q == 0)
                break;
        }
        return new Fraction(0, 0);
    }

    static Fraction findValidUpper(Fraction lo, Fraction hi, long N, long L) {
        for (int steps = 0; steps < 100000; ++steps) {
            if (isValidFraction(hi, L))
                return hi;
            Fraction next = fareyNext(lo, hi, N);
            lo = hi;
            hi = next;
            if (hi.q == 0)
                break;
        }
        return new Fraction(0, 0);
    }

    static Candidate evaluateFraction(Fraction f, double tAlpha, long L) {
        Candidate cand = new Candidate();
        if (f.p == 0 || f.q == 0)
            return cand;
        long m = f.p;
        long n = f.q;
        long m2 = m * m;
        long n2 = n * n;
        long a = m2 - n2;
        long b = 2L * m * n;
        long c = m2 + n2;
        long k = L / c;
        if (k == 0)
            return cand;

        double t = 3.0 * a * b / (2.0 * c * c);
        double diff = Math.abs(t - tAlpha) / (1.0 + t * tAlpha);

        cand.valid = true;
        cand.diff = diff;
        cand.sum = k * (a + b + c);
        java.math.BigInteger bK = java.math.BigInteger.valueOf(k);
        java.math.BigInteger bA = java.math.BigInteger.valueOf(a);
        java.math.BigInteger bB = java.math.BigInteger.valueOf(b);
        cand.area = bK.multiply(bK).multiply(bA).multiply(bB);
        return cand;
    }

    static Candidate bestCandidateForU(double uTarget, double tAlpha, long L) {
        Candidate best = new Candidate();
        if (uTarget <= 1.0)
            return best;

        double R = Math.sqrt(L);
        double denom = Math.sqrt(1.0 + uTarget * uTarget);
        long N = (long) Math.floor(R / denom);
        if (N < 1)
            N = 1;

        Fraction[] bounds = fareyBounds(uTarget, N);
        Fraction lo = bounds[0];
        Fraction hi = bounds[1];

        Fraction loValid = findValidLower(lo, hi, N, L);
        Fraction hiValid = findValidUpper(lo, hi, N, L);

        if (loValid.q != 0) {
            best = evaluateFraction(loValid, tAlpha, L);
        }
        if (hiValid.q != 0) {
            Candidate cand = evaluateFraction(hiValid, tAlpha, L);
            if (!best.valid) {
                best = cand;
            } else if (cand.valid) {
                double eps = 1e-15;
                if (cand.diff + eps < best.diff) {
                    best = cand;
                } else if (Math.abs(cand.diff - best.diff) <= eps) {
                    if (cand.area.compareTo(best.area) > 0) {
                        best = cand;
                    }
                }
            }
        }

        return best;
    }

    static long computeF(double alphaDeg, long L) {
        double kPi = Math.acos(-1.0);
        double kUMin = 1.0 + Math.sqrt(2.0);
        double kTMax = 0.75;

        double alphaRad = alphaDeg * kPi / 180.0;
        double tAlpha = Math.tan(alphaRad);

        double uLow = 1.0;
        double uHigh = kUMin;
        if (tAlpha < kTMax) {
            double low = 1.0;
            double high = kUMin;
            for (int iter = 0; iter < 100; ++iter) {
                double mid = 0.5 * (low + high);
                if (tanThetaFromU(mid) < tAlpha) {
                    low = mid;
                } else {
                    high = mid;
                }
            }
            uLow = 0.5 * (low + high);

            low = kUMin;
            high = Math.max(kUMin + 1.0, 3.0 / tAlpha + 2.0);
            while (tanThetaFromU(high) > tAlpha) {
                high *= 2.0;
            }
            for (int iter = 0; iter < 100; ++iter) {
                double mid = 0.5 * (low + high);
                if (tanThetaFromU(mid) > tAlpha) {
                    low = mid;
                } else {
                    high = mid;
                }
            }
            uHigh = 0.5 * (low + high);
        }

        Candidate best = bestCandidateForU(uLow, tAlpha, L);
        Candidate alt = bestCandidateForU(uHigh, tAlpha, L);

        if (!best.valid) {
            best = alt;
        } else if (alt.valid) {
            double eps = 1e-15;
            if (alt.diff + eps < best.diff) {
                best = alt;
            } else if (Math.abs(alt.diff - best.diff) <= eps) {
                if (alt.area.compareTo(best.area) > 0) {
                    best = alt;
                }
            }
        }

        return best.sum;
    }

    public static String solve() {
        int N = 45000;
        long L = 10000000000L;

        int threads = Math.max(1, Runtime.getRuntime().availableProcessors());
        long[] partial = new long[threads];
        Thread[] pool = new Thread[threads];

        for (int t = 0; t < threads; ++t) {
            final int tIdx = t;
            pool[t] = new Thread(() -> {
                long local = 0;
                for (int i = 1 + tIdx; i <= N; i += threads) {
                    double alpha = Math.cbrt(i);
                    local += computeF(alpha, L);
                }
                partial[tIdx] = local;
            });
            pool[t].start();
        }

        long total = 0;
        try {
            for (int t = 0; t < threads; t++) {
                if (pool[t] != null)
                    pool[t].join();
                total += partial[t];
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }

        return Long.toString(total);
    }

    public static void main(String[] args) {
        System.out.println(solve());
    }
}
