C ++中的超长数组

时间:2011-10-21 00:52:25

标签: c++ c arrays performance

我有两套A和B.套装A包含独特的元素。集B包含所有元素。 B中的每个元素都是10乘10矩阵,其中所有条目都是1或0.我需要扫描集合B,每次遇到新矩阵时我都会将它添加到集合A.因此集合A是B的子集只包含唯一的矩阵。

5 个答案:

答案 0 :(得分:4)

似乎你真的正在寻找管理大型稀疏数组的方法。平凡的是,您可以使用哈希映射将您的巨型索引作为键,将数据作为值。如果您更多地谈论您的问题,我们可能会为您的问题找到更合适的数据结构。

更新

如果集合B只是一组矩阵而不是所有可能的10x10二进制矩阵的集合,那么你只需要一个稀疏数组。每次找到新矩阵时,都会计算其密钥(可能只是将矩阵转换为100位二进制值,甚至是100个字符的字符串!),查找该索引。如果不存在此键,请为该键插入值1。如果密钥确实存在,则递增并重新存储该密钥的新值。

答案 1 :(得分:3)

以下是一些代码,可能效率不高:

# include <vector>
# include <bitset>
# include <algorithm>

// I assume your 10x10 boolean matrix is implemented as a bitset of 100 bits.

// Comparison of bitsets
template<size_t N>
class bitset_comparator
{
    public :
      bool operator () (const std::bitset<N> & a, const std::bitset<N> & b) const
      {
          for(size_t i = 0 ; i < N ; ++i)
          {
              if( !a[i] && b[i] )       return true ;
              else if( !b[i] && a[i] )  return false ;
          }
          return false ;
      }
} ;

int main(int, char * [])
{
    std::set< std::bitset<100>, bitset_comparator<100> > A ;
    std::vector< std::bitset<100> >                      B ; 


    // Fill B in some manner ...

    // Keeping unique elements in A
    std::copy(B.begin(), B.end(), std::inserter(A, A.begin())) ;
}

您可以使用std::list代替std::vector。 B中元素的相对顺序未保留在A中(A中的元素已排序)。

编辑:我在第一篇文章中颠倒了A和B.现在这是正确的。抱歉给你带来不便。我还纠正了比较函子。

答案 2 :(得分:1)

  

B中的每个元素都是10乘10矩阵,其中所有条目都是1或0。

好,这意味着它可以用100位数字表示。让我们将其舍入到128位(16个字节)。

一种方法是使用链表 - 创建一个像(在C中)的结构:

typedef struct sNode {
    unsigned char bits[16];
    struct sNode *next;
};

并将整个列表B维护为已排序的链接列表。

与使用100位数作为数组索引进行真正巨大的(在给定已知宇宙的大小的情况下不可能的数组)数组相比,性能将稍微低于(a)

当需要将新项目插入B时,请将其插入所需位置(在相等或更大的位置之前)。如果它是一个全新的(如果你之前插入的那个是不同的,你会知道这个),也可以将它添加到A


(a)虽然可能不是那么难以管理 - 但你可以选择提高速度。

一种可能性是使用跳过列表,以便在搜索期间更快地遍历。这是另一个指针,它不引用下一个元素,而是引用一个10(或100或1000)个元素。这样,您可以合理地快速接近所需元素,并在该点之后进行一步搜索。

或者,由于您正在讨论位,因此可以将B划分为(例如)1024个子B列表。使用100位值的前10位来确定需要使用哪个子B并仅存储接下来的90位。仅此一项就可以将搜索速度平均提高1000(如果需要改进,可以使用更多的前导位和更多的子B)。

您还可以在100位值上使用散列来生成一个较小的键,您可以将其用作数组/列表的索引,但我认为这不会给您带来任何真正的优势。上一段。

答案 3 :(得分:0)

将每个矩阵转换为100个二进制数字的字符串。现在通过Linux实用程序运行它:

sort | uniq

如果您确实需要在C ++中执行此操作,则可以实现自己的合并排序,然后uniq部分变得微不足道。

答案 4 :(得分:0)

您不需要N个桶,其中N是所有可能输入的数量。 binary tree只会做得很好。这是用C ++中的set类实现的。

vector<vector<vector<int> > > A; // vector of 10x10 matrices
// fill the matrices in A here

set<vector<vector<int> > > B(A.begin(), A.end()); // voila!
// now B contains all elements in A, but only once for duplicates