首页 > 其他分享 >板子

板子

时间:2022-12-24 09:01:14浏览次数:33  
标签:node const int hs len 板子 Hash

自用

namespace HASH {
    const int p = (int)1e9 + 9, base = 233;
	ll inv(ll a, int p) {
		ll x = 1;
		for (int b = p - 2; b; b = b >> 1, a = a * a % p) {
			if (b & 1) x = x * a % p;
		}
		return x;
	}
    ll B[N], invb, invB[N];
    void pre() {
        invb = inv(base, p);
        B[0] = invB[0] = 1;
        for (int i = 1; i < ::N; ++i) {
            B[i] = B[i - 1] * base % p;
            invB[i] = invB[i - 1] * invb % p;
        }
    }
    struct Hash{
        ll hs;
        int len;
        Hash() { clear(); }
        Hash(const ll &hs, const int &len) : hs(hs), len(len) {}
        Hash(const Hash &t) : hs(t.hs), len(t.len) {}
        void clear() { hs = 0; len = 0; }
        void push_front(char c) {
            hs = ((ll)c * B[len] + hs) % p;
            ++len;
        }
        void push_back(char c) {
            ++len;
            hs = (hs * base + c) % p;
        }
    };
    Hash operator+(const Hash &x, const Hash &y) {
        return Hash((x.hs * B[y.len] + y.hs) % p, x.len + y.len);
    }
    bool operator==(const Hash &x, const Hash &y) { return x.hs == y.hs && x.len == y.len; }
    Hash red_front(const Hash &x, const Hash &y) {
        assert(x.len >= y.len);
        return Hash((x.hs - y.hs * B[x.len - y.len] % p + p) % p, x.len - y.len);
    }
    Hash red_back(const Hash &x, const Hash &y) {
        assert(x.len >= y.len);
        return Hash((x.hs - y.hs + p) * invB[y.len] % p, x.len - y.len);
    }
}

namespace HASH{
    const int p[2] = {(int)1e9 + 7, (int)1e9 + 9}, base[2] = {233, dist(rnd)};
    ll B[2][::N], invb[2], invB[2][::N];
    void pre() {
        invb[0] = inv(base[0], p[0]);
        invb[1] = inv(base[1], p[1]);
        B[0][0] = B[1][0] = 1;
        invB[0][0] = invB[1][0] = 1;
        for (int i = 1; i < ::N; ++i) {
            B[0][i] = B[0][i - 1] * base[0] % p[0];
            B[1][i] = B[1][i - 1] * base[1] % p[1];
            invB[0][i] = invB[0][i - 1] * invb[0] % p[0];
            invB[1][i] = invB[1][i - 1] * invb[1] % p[1];
        }
    }
    struct Hash{
        ll hs[2];
        int len;
        Hash() { clear(); }
        Hash(const ll &hs0, const ll &hs1, const int &len) : len(len) { hs[0] = hs0; hs[1] = hs1; }
        Hash(const Hash &t) : len(t.len) { hs[0] = t.hs[0], hs[1] = t.hs[1]; }
        void clear() { hs[0] = hs[1] = 0; len = 0; }
        void push_front(char c) {
            for (int i = 0; i < 2; ++i) hs[i] = ((ll)c * B[i][len] + hs[i]) % p[i];
            ++len;
        }
        void push_back(char c) {
            ++len;
            for (int i = 0; i < 2; ++i) hs[i] = (hs[i] * base[i] + c) % p[i];
        }
    };
    Hash operator+(const Hash &x, const Hash &y) {
        return Hash((x.hs[0] * B[0][y.len] + y.hs[0]) % p[0], (x.hs[1] * B[1][y.len] + y.hs[1]) % p[1], x.len + y.len);
    }
    bool operator==(const Hash &x, const Hash &y) { return x.hs[0] == y.hs[0] && x.hs[1] == y.hs[1] && x.len == y.len; }
    Hash red_front(const Hash &x, const Hash &y) {
        assert(x.len >= y.len);
        return Hash((x.hs[0] - y.hs[0] * B[0][x.len - y.len] % p[0] + p[0]) % p[0], (x.hs[1] - y.hs[1] * B[1][x.len - y.len] % p[1] + p[1]) % p[1], x.len - y.len);
    }
    Hash red_back(const Hash &x, const Hash &y) {
        assert(x.len >= y.len);
        return Hash((x.hs[0] - y.hs[0] + p[0]) * invB[0][y.len] % p[0], (x.hs[1] - y.hs[1] + p[1]) * invB[1][y.len] % p[1] % p[1], x.len - y.len);
    }
}

namespace DLX {
    const int R = ::R, C = ::C, N = ::maxn;
    struct node {
        node *lf, *rg, *up, *dw;
        int r, c;
        node() { clear(); }
        void clear() { lf = rg = up = dw = 0; r = c = 0; }
    };
    node pool[N + C], *_now = pool;
    node *head, *row[R], *col[C];
    vector<int> ans;
    int m, ect[C];
    void clear() {
        for (int i = 0; i < R; ++i) row[i] = nullptr;
        for (int i = 0; i < C; ++i) col[i] = nullptr;
        head = nullptr;
        for (node *it = pool; it != _now; ++it) {
            it -> clear();
        }
        _now = pool;
    }
    node* new_node() { return _now++; }
    void linkLR(node *x, node *y) {
        x -> rg = y;
        y -> lf = x;
    }
    void removeLR(node *x) {
        x -> lf -> rg = x -> rg;
        x -> rg -> lf = x -> lf;
    }
    void resumeLR(node *x) {
        x -> lf -> rg = x;
        x -> rg -> lf = x;
    }
    void linkUD(node *x, node *y) {
        x -> dw = y;
        y -> up = x;
    }
    void removeUD(node *x) {
        x -> up -> dw = x -> dw;
        x -> dw -> up = x -> up;
    }
    void resumeUD(node *x) {
        x -> up -> dw = x;
        x -> dw -> up = x;
    }
    void init(int _m) {
        m = _m;
        for (int i = 0; i <= m; ++i) {
            col[i] = new_node();
            col[i] -> c = i;
        }
        for (int i = 0; i <= m; ++i) {
            linkLR(col[i], col[(i + 1) % (m + 1)]);
            linkUD(col[i], col[i]);
            ect[i] = 0;
        }
        head = col[0];
    }
    void insert(int _r, int _c) {
        node *t = new_node();
        t -> r = _r; t -> c = _c;
        linkUD(col[_c] -> up, t);
        linkUD(t, col[_c]);
        if (row[_r] == nullptr) {
            row[_r] = t;
            linkLR(t, t);
        } else {
            linkLR(row[_r] -> lf, t);
            linkLR(t, row[_r]);
        }
        ++ect[_c];
    }
    void remove(node *c) {
        removeLR(c);
        for (node *x = c -> dw; x != c; x = x -> dw) {
            for (node *y = x -> rg; y != x; y = y -> rg) {
                removeUD(y);
                --ect[y -> c];
            }
        }
    }
    void resume(node *c) {
        for (node *x = c -> up; x != c; x = x -> up) {
            for (node *y = x -> lf; y != x; y = y -> lf) {
                resumeUD(y);
                ++ect[y -> c];
            }
        }
        resumeLR(c);
    }
    bool dance() {
        if (head -> rg == head) return true;
        node *t = head -> rg;
        for (node *x = t -> rg; x != head; x = x -> rg) {
            if (ect[x -> c] < ect[t -> c]) t = x;
        }
        remove(t);
        for (node *x = t -> dw; x != t; x = x -> dw) {
            ans.emplace_back(x -> r);
            for (node *y = x -> rg; y != x; y = y -> rg) {
                remove(col[y -> c]);
            }
            if (dance()) return true;
            for (node *y = x -> lf; y != x; y = y -> lf) {
                resume(col[y -> c]);
            }
            ans.pop_back();
        }
        resume(t);
        return false;
    }
    pair<vector<int>, bool> calc() {
        ans.clear();
        bool flag = dance();
        return make_pair(ans, flag);
    }
}

注意:removeresume 的顺序必须正好相反,否则会挂掉,但是神奇的板子题并没有卡。。。。


namespace number_theory {
    template<typename T> inline T gcd(T a, T b) {
        return b == 0 ? a : gcd(b, a % b);
    }
    template<typename T> inline T exgcd(T a, T b, T &x, T &y) {
        if (b == 0) {
            x = 1, y = 0;
            return a;
        }
        T d = exgcd(b, a % b, y, x);
        y -= (a / b) * x;
        return d;
    }
    int fpw(ll a, ll b, int mo) {
        ll x = 1; a = (a % mo + mo) % mo;
        for (; b; b >>= 1, a = a * a % mo) {
            if (b & 1) x = x * a % mo;
        }
        return x;
    }
    int inv(ll a, int mo) { return fpw(a, mo - 2, mo); }
    ll mul(const ll &x, const ll &y, const ll &mo) { return (__int128)x * y % mo; }
    pair<pair<ll, ll>, bool> exCRT(vector<ll> a, vector<ll> b, int n) {//means x mod b[i] = a[i] mod a[i]
        assert(n > 0);
        ll A = a[0], M = b[0];
        for (int i = 1; i < n; ++i) {
            ll k1, k2, t = a[i] - A;
            ll d = exgcd(M, b[i], k1, k2);
            if (t % d != 0) return make_pair(make_pair(-1ll, 0ll), false);
            ll tM = M / gcd(M, b[i]) * b[i];
            A = (mul((mul(t / d, k1, tM) + tM) % tM, M, tM) + A) % tM;
            M = tM;
        }
        return make_pair(make_pair(A, M), true);
    }
    int Phi(int x) {
        int phi = x;
        for (int i = 2; i * i <= x; ++i) if (x % i == 0) {
            phi = phi - phi / i;
            for (; x % i == 0; x /= i);
        }
        if (x > 1) phi = phi - phi / x;
        return phi;
    }
    vector<pair<int, int>> prime_factorization(int x) {
        vector<pair<int, int>> res;
        for (int i = 2; i * i <= x; ++i) if (x % i == 0) {
            int c = 0;
            for (; x % i == 0; x /= i, ++c);
            res.emplace_back(i, c);
        }
        if (x > 1) res.emplace_back(x, 1);
        return res;
    }
    int min_primitive_root(int m) {
        int phi = Phi(m);
        auto v = prime_factorization(phi);
        for (int i = 2; i <= m; ++i) {
            bool flag = 1;
            for (auto x : v) {
                if (fpw(i, phi / x.first, m) == 1) {flag = 0; break; }
            }
            if (flag) return i;
        }
        return -1;
    }
    vector<int> primitive_root(int m) {
        vector<int> res;
        int phi = Phi(m), mn = -1;
        auto v = prime_factorization(phi);
        for (int i = 1; i <= m; ++i) if (gcd(i, m) == 1) {
            bool flag = 1;
            for (auto x : v) {
                if (fpw(i, phi / x.first, m) == 1) {flag = 0; break; }
            }
            if (flag) {
                mn = i;
                break;
            }
        }
        if (mn == -1) return res;
        for (int i = 1; i <= phi; ++i) if (gcd(i, phi) == 1) {
            res.push_back(fpw(mn, i, m));
        }
        sort(res.begin(), res.end());
        return res;
    }
}

标签:node,const,int,hs,len,板子,Hash
From: https://www.cnblogs.com/lazytag/p/17001984.html

相关文章

  • 梦幻布丁 启发式合并板子
    //题意:将一段布丁染色,然后有两种操作,操作1将颜色为x的布丁全部染为y,操作2统计当前一共有多少段颜色//思路:将x染色为y可以想到启发式合并,但是注意我们交换大小集合后,有可......
  • windows上运行qemu仿真stm32板子a9板子实例
    由于网上的教程大部分都是基于Linux系统搞的,其实从初学者的易用性来说,这是不方便的,因为我们还得装个虚拟机,还得装个Ubuntu,还得配一些环境,甚至还得命令行编译出来,很繁琐的,中......
  • 尝试把多项式板子分段喂给 ChatGPT 辨认
    #include<bits/stdc++.h>#defineendl'\n'#definerep(i,a,b)for(inti=(a);i<=(b);++i)#defineRep(i,a,b)for(inti=(a);i>=(b);--i)usingnamespacestd;const......
  • IAR生成的HEX、bin文件用DownLoader_MINI打不开,下载不到板子上
    一开始,我是这样配置IAR->option的,让他生成hex\bin文件:第1)步:第2)步:   但这个样子通过编译生成的hex文件打开是乱码,而且用DownLoader打不开:     后来百......
  • 一本通1456(哈希表板子
     用map<int,bool> #include"bits/stdc++.h"usingnamespacestd;constintN=1e4+5;#defineintunsignedlonglongconstintmod=212370440130137957ll;cha......
  • splay板子
    #include<bits/stdc++.h>usingnamespacestd;constintmaxn=100000+5;structSplay{intch[maxn][0],ch[maxn][1],fa[maxn],siz[maxn],key[maxn],tot;......
  • lca 板子
    这题#10130. 「一本通4.4例1」点的距离求树上两点的距离 #include<bits/stdc++.h>usingnamespacestd;constintN=1e6+2,M=N;intnxt[M],hd[N],all,go[M......
  • 割点板子
    一些直白的理解,和标准定义有差别,但也足够了 点双连通:一个图任意去掉一个点后仍然联通;   边双连通同理割点:去掉某个点后,图不连通     割边同理 求割点(l......
  • 高精度板子
     #include<bits/stdc++.h>usingnamespacestd;intcompare(stringstr1,stringstr2){if(str1.length()>str2.length())return1;elseif(str1.length(......
  • 一些板子
    离散化://离散化,可以处理一些跨越区间比较大的时候的位置关系,空间更紧凑intn,m;inta[N],b[N],c[N];intcnt=0;//lower_bound第一个大于等于x的数//upper_bound......