Advertisement
Guest User

enumeration of antimatroid, bforce + symmetries elimination

a guest
Apr 13th, 2013
84
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 5.54 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <algorithm>
  4.  
  5. using namespace std;
  6.  
  7. typedef unsigned long long ull;
  8. typedef unsigned int us;
  9.  
  10.  
  11. const int n = 6;
  12. const int N = 1<<n;
  13.  
  14. const int factorial[] = {1,1,2,6,24,120,720,5040};
  15.  
  16.  
  17. class u128
  18. {
  19.     public:
  20.         ull low;
  21.         ull high;
  22.         u128(ull _low=0, ull _high = 0)
  23.         {
  24.             low = _low;
  25.             high = _high;
  26.         }
  27.  
  28.         bool operator<(const u128& b) const
  29.         {
  30.             return (high==b.high) ? (low<b.low) : (high<b.high);
  31.         }
  32.  
  33.         bool operator==(const u128& b) const
  34.         {
  35.             return (high==b.high) && (low==b.low);
  36.         }
  37.  
  38.         u128 operator~() const
  39.         {
  40.             return u128(~low,~high);
  41.         }
  42.  
  43.         u128 operator&(const u128& b) const
  44.         {
  45.             return u128(low&b.low, high&b.high);
  46.         }
  47.  
  48.         u128 operator|=(const u128& b)
  49.         {
  50.             low |= b.low;
  51.             high |= b.high;
  52.             return *this;
  53.         }
  54.         u128 operator&=(const u128& b)
  55.         {
  56.             low &= b.low;
  57.             high &= b.high;
  58.             return *this;
  59.         }
  60.  
  61.         void setbit(unsigned i)
  62.         {
  63.             if(i<64)
  64.                 low |= (1ull << i);
  65.             else
  66.                 high |= (1ull << (i-64));
  67.         }
  68.  
  69.         void erasebit(unsigned i)
  70.         {
  71.             if(i<64)
  72.                 low &= ~(1ull << i);
  73.             else
  74.                 high &= ~(1ull << (i-64));
  75.         }
  76.  
  77.         bool getbit(unsigned i) const
  78.         {
  79.             return (i<64) ? (low & (1ull << i)) : (high & (1ull << (i-64)));
  80.         }
  81. };
  82.  
  83. const int magic = 2000003;
  84. int hash_(const u128& X)
  85. {
  86.     int ret = (X.low%magic)+(X.high%magic);
  87.     return ret<magic?ret:ret-magic;
  88. }
  89. class hashtable
  90. {
  91.     public:
  92.         vector<vector<u128> > table;
  93.         int size;
  94.         hashtable()
  95.         {
  96.             table.resize(magic);
  97.             size = 0;
  98.         }
  99.         void insert(const u128& X)
  100.         {
  101.             int h = hash_(X);
  102.             bool ok = true;
  103.             for(auto& i : table[h])
  104.                 if(i==X)
  105.                 {
  106.                     ok = false;
  107.                     break;
  108.                 }
  109.             if(ok)
  110.             {
  111.                 table[h].push_back(X);
  112.                 size++;
  113.             }
  114.         }
  115. };
  116.  
  117.  
  118. vector<vector<int> > perms;
  119. int psize;
  120. vector<vector<int> > ap;
  121. //vector<int> order;
  122. vector<u128> pred;
  123. vector<u128> succ;
  124.  
  125. int apply(vector<int> p, int x)
  126. {
  127.     int y = 0;
  128.     for(int i=0;i<n;i++)
  129.         if(x & (1<<i))
  130.             y |= 1<<p[i];
  131.     return y;
  132. }
  133.  
  134. pair<u128,vector<int> > _reduce(const u128& X)
  135. {
  136.     u128 R;
  137.     vector<int> C(psize);
  138.     for(int i=0;i<psize;i++)
  139.         C[i]=i;
  140.     vector<int> nC;
  141.     int i=1;
  142.     for(int i=0;i<(1<<n);i++)
  143.     {
  144.         nC.clear();
  145.         bool v = false;
  146.         for(auto& t : C)
  147.         {
  148.             bool nv = X.getbit(ap[i][t]);
  149.             if(nv > v)
  150.             {
  151.                 nC.clear();
  152.                 v = nv;
  153.                 R.setbit(i);
  154.             }
  155.             if(nv == v)
  156.             {
  157.                 nC.push_back(t);
  158.             }
  159.         }
  160.         swap(nC,C);
  161.     }
  162.     return make_pair(R,C);
  163. }
  164. u128 reduce(const u128& X)
  165. {
  166.     return _reduce(X).first;
  167. }
  168. vector<int> aut(const u128& X)
  169. {
  170.     return _reduce(X).second;
  171. }
  172.  
  173.  
  174. long long ans = 0;
  175. long long ans2 = 0;
  176.  
  177. vector<u128> onestep(const vector<u128> P)            
  178. {
  179.     hashtable nL;
  180.     for(auto& S : P)
  181.     {
  182.         vector<int> automorph = aut(S);
  183.         ans += psize/automorph.size();
  184.         ans2 += 1;
  185.         u128 mask(0,0);
  186.         for(int I=1;I<N-1;I++)
  187.             if(S.getbit(I))
  188.                 for(int J=1;J<I;J++)
  189.                     if(S.getbit(J))
  190.                     {
  191.                         int IJ = I|J;
  192.                         if(IJ != I && IJ != J)
  193.                             mask.setbit(IJ);
  194.                     }
  195.  
  196.  
  197.         mask = S & ~mask;
  198.         u128 f1,f2;
  199.         for(int I=0;I<N;I++)
  200.             if(S.getbit(I))
  201.             {
  202.                 f2 |= succ[I] & f1;
  203.                 f1 |= succ[I];
  204.             }
  205.         f1 &= ~f2 & S;
  206.         for(int I=0;I<N;I++)
  207.             if(f1.getbit(I))
  208.                 mask = mask & ~pred[I];
  209.  
  210.         for(int I=1;I<N-1;I++)
  211.             if(mask.getbit(I))
  212.             {
  213.                 for(int a=0;a<automorph.size();a++)
  214.                     mask.erasebit(ap[I][automorph[a]]);
  215.                 u128 nS = S;
  216.                 nS.erasebit(I);
  217.                 nL.insert(reduce(nS));
  218.             }
  219.     }
  220.     vector<u128> ret;
  221.     for(auto& v : nL.table)
  222.         for(auto& x : v)
  223.             ret.push_back(x);
  224.     return ret;
  225. }
  226.  
  227.  
  228. int main()
  229. {
  230.     pred.resize(N);
  231.     succ.resize(N);
  232.     for(int I=0;I<N;I++)
  233.         for(int i=0;i<n;i++)
  234.             if(I & (1<<i))
  235.                 pred[I].setbit(I & ~(1<<i));
  236.             else
  237.                 succ[I].setbit(I | (1<<i));
  238.    
  239.     vector<int> start;
  240.     for(int i=0;i<n;i++)
  241.         start.push_back(i);
  242.     do
  243.     {
  244.         perms.push_back(start);
  245.     }
  246.     while(next_permutation(start.begin(),start.end()));
  247.     psize = perms.size();
  248.    
  249.     ap.resize(N, vector<int>(psize));
  250.     for(int p=0;p<psize;p++)
  251.         for(int i=0;i<N;i++)
  252.             ap[i][p] = apply(perms[p], i);
  253.  
  254.     u128 seed;
  255.     for(int i=0;i<N;i++)
  256.         seed.setbit(i);
  257.  
  258.     vector<u128> L(1,seed);
  259.  
  260.     while(!L.empty())
  261.         L = onestep(L);
  262.     cout << ans << ' ' << ans2 << endl;
  263. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement