算法模板

Abstract

记录一些自己写的算法模板,防止重复造轮子。

图论

邻接表

Code

namespace graph
{
    int n;
    const int maxn = 10000000;
    int head[maxn];
    int cnt;
    struct Edge
    {
        int next, to, value;
    } edge[maxn];
    void add(int u, int v, int c)
    {
        edge[++cnt].next = head[u];
        edge[cnt].to = v;
        edge[cnt].value = c;
        head[u] = cnt;
        return;
    }
    void init()
    {
        cnt = 0;
        for (int i = 0; i <= n; i++)
        {
            head[i] = 0;
        }
        return;
    }
};

线性数据结构

线段树(区间最值,区间和)

Code

namespace seg
{
    const int N = 1e6 + 1000;
    struct Node
    {
        int sum, l, r, tag, min;
    } nodes[N << 2];
#define l(x) (x << 1)
#define r(x) (x << 1 | 1)
    void up(int rt)
    {
        nodes[rt].sum = nodes[l(rt)].sum + nodes[r(rt)].sum;
        nodes[rt].min = min(nodes[l(rt)].min, nodes[r(rt)].min);
        return;
    }
    void down(int rt)
    {
        int mid = nodes[rt].l + nodes[rt].r >> 1;
        if (nodes[rt].tag)
        {
            nodes[l(rt)].tag += nodes[rt].tag, nodes[r(rt)].tag += nodes[rt].tag;
            nodes[l(rt)].sum += nodes[rt].tag * (mid - nodes[l(rt)].l + 1);
            nodes[r(rt)].sum += nodes[rt].tag * (nodes[r(rt)].r - mid);
            nodes[l(rt)].min += nodes[rt].tag;
            nodes[r(rt)].min += nodes[rt].tag;
            nodes[rt].tag = 0;
        }
        return;
    }
    void build(int rt, int l, int r)
    {
        nodes[rt].l = l, nodes[rt].r = r;
        nodes[rt].tag = 0;
        if (l == r)
        {
            std::cin >> nodes[rt].sum;
            nodes[rt].min = nodes[rt].sum;
            return;
        }
        int mid = l + r >> 1;
        build(l(rt), l, mid);
        build(r(rt), mid + 1, r);
        up(rt);
        return;
    }
    void plus(int rt, int ql, int qr, int k)
    {
        int l = nodes[rt].l, r = nodes[rt].r;
        if (ql <= l && r <= qr)
        {
            nodes[rt].tag += k;
            nodes[rt].sum += k * (r - l + 1);
            nodes[rt].min += k;
            return;
        }
        int mid = l + r >> 1;
        down(rt);
        if (ql <= mid)
        {
            plus(l(rt), ql, qr, k);
        }
        if (mid + 1 <= qr)
        {
            plus(r(rt), ql, qr, k);
        }
        up(rt);
        return;
    }
    int query(int rt, int ql, int qr)
    {
        int l = nodes[rt].l, r = nodes[rt].r;
        if (ql <= l && r <= qr)
        {
            return nodes[rt].sum;
        }
        int mid = l + r >> 1;
        int res = 0;
        down(rt);
        if (ql <= mid)
        {
            res += query(l(rt), ql, qr);
        }
        if (qr >= mid + 1)
        {
            res += query(r(rt), ql, qr);
        }
        return res;
    }
};

数学

线性代数

矩阵的基本运算

Code

template <typename T>
struct Mat
{
    int n, m;
    T **a;
    Mat(int _n = 0, int _m = 0) : n(_n), m(_m)
    {
        a = new T *[n];
        for (int i = 0; i < n; i++)
            a[i] = new T[m], memset(a[i], 0, sizeof(T) * m);
    }
    Mat(const Mat &B)
    {
        n = B.n, m = B.m;
        a = new T *[n];
        for (int i = 0; i < n; i++)
            a[i] = new T[m], memcpy(a[i], B.a[i], sizeof(T) * m);
    }
    ~Mat() { delete[] a; }
    Mat &operator=(const Mat &B)
    {
        delete[] a;
        n = B.n, m = B.m;
        a = new T *[n];
        for (int i = 0; i < n; i++)
            a[i] = new T[m], memcpy(a[i], B.a[i], sizeof(T) * m);
        return *this;
    }
    Mat operator+(const Mat &B) const
    { // 矩阵加法。
        assert(n == B.n && m == B.m);
        Mat ret(n, m);
        for (int i = 0; i < n; i++)
            for (int j = 0; j < m; j++)
                ret.a[i][j] = (a[i][j] + B.a[i][j]) % mod;
        return ret;
    }
    Mat &operator+=(const Mat &B) { return *this = *this + B; }
    Mat operator*(const Mat &B) const
    {
        Mat ret(n, B.m);
        for (int i = 0; i < n; ++i)
            for (int j = 0; j < B.m; ret.a[i][j++] %= mod)
                for (int k = 0; k < m; ++k)
                    ret.a[i][j] += a[i][k] * B.a[k][j] % mod;
        return ret;
    }
    Mat &operator*=(const Mat &B) { return *this = *this * B; }
};
Mat<int> qpow(Mat<int> A, int b)
{
    Mat<int> ret(A);
    for (--b; b; b >>= 1, A *= A)
        if (b & 1)
            ret *= A;
    return ret;
}

基础算法

高精度

Code

struct Num
{
    std::vector<int> v;

    void print()
    {
        for (int i = v[0]; i > 0; i--)
        {
            std::cout << v[i];
        }
        return;
    }

    void scan()
    {
        std::string t;
        std::cin >> t;
        int len = t.length();
        v.resize(len + 1, 0);
        for (int i = 0; i < len; i++)
        {
            v[len - i] = t[i] - '0';
        }
        v[0] = len;
        return;
    }

    Num operator+(const Num &rhs) const
    {
        Num result;
        result.v.resize(std::max(v[0], rhs.v[0]) + 2, 0);
        result.v[0] = std::max(v[0], rhs.v[0]) + 1;
        for (int i = 1; i <= result.v[0]; i++)
        {
            if (i <= v[0])
            {
                result.v[i] += v[i];
            }
            if (i <= rhs.v[0])
            {
                result.v[i] += rhs.v[i];
            }
            result.v[i + 1] += result.v[i] / 10;
            result.v[i] %= 10;
        }
        while (result.v[result.v[0]])
        {
            result.v.push_back(result.v[result.v[0]] / 10);
            result.v[result.v[0]] %= 10;
            result.v[0]++;
        }
        while (result.v[result.v[0]] == 0 && result.v[0] > 1)
        {
            result.v[0]--;
        }
        return result;
    }

    Num operator*(const Num &rhs) const
    {
        Num result;
        result.v.resize(v[0] + rhs.v[0] + 1, 0);
        result.v[0] = v[0] + rhs.v[0];
        for (int i = 1; i <= v[0]; i++)
        {
            for (int j = 1; j <= rhs.v[0]; j++)
            {
                result.v[i + j - 1] += rhs.v[j] * v[i];
                result.v[i + j] += result.v[i + j - 1] / 10;
                result.v[i + j - 1] %= 10;
            }
        }
        while (result.v[result.v[0]])
        {
            result.v.push_back(result.v[result.v[0]] / 10);
            result.v[result.v[0]] %= 10;
            result.v[0]++;
        }
        while (result.v[result.v[0]] == 0 && result.v[0] > 1)
        {
            result.v[0]--;
        }
        return result;
    }
};
posted @   carboxylBase  阅读(7)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示