以下程序计算真正大数的所有素数(例如600,851,475,143)。到目前为止一切正常,除非我输入大量的析构函数导致应用程序崩溃。任何人都可以看到我的申请有问题吗? 在重新检查我的解决方案后,答案是错误的,但问题仍然有效。
#include <iostream>
#include <iterator>
#include <algorithm>
#include <vector>
#include <cmath>
#include <stdexcept>
#include <climits>
typedef std::vector<unsigned long long>::const_iterator prime_it;
#define MAX_COL 900000
struct large_vector
{
public:
large_vector(unsigned long long size, unsigned int row) :
m_Row(row)
{
m_RowVector.reserve(size);
}
std::vector<bool> m_RowVector;
unsigned int m_Row;
};
struct prime_factor
{
public:
prime_factor(unsigned long long N);
~prime_factor() {}
void print_primes();
private:
std::vector<bool> m_Primes;
std::vector<large_vector>m_Vect_Primes;
unsigned long long m_N;
};
prime_factor::prime_factor(unsigned long long N) :
m_N(N)
{
// If number is odd then we need the cieling of N/2 / MAX_COL
int number_of_vectors = (m_N % MAX_COL == 0) ? (m_N / MAX_COL) : ((m_N / MAX_COL) + 1);
std::cout << "There will be " << number_of_vectors << " rows";
if (number_of_vectors != 0) {
for (int x = 0; x < number_of_vectors; ++x) {
m_Vect_Primes.push_back(large_vector(MAX_COL, x));
}
m_Vect_Primes[0].m_RowVector[0] = false;
m_Vect_Primes[0].m_RowVector[1] = false;
unsigned long long increment = 2;
unsigned long long index = 0;
while (index < m_N) {
for (index = 2*increment; index < m_N; index += increment) {
unsigned long long row = index/MAX_COL;
unsigned long long col = index%MAX_COL;
m_Vect_Primes[row].m_RowVector[col] = true;
}
while (m_Vect_Primes[increment/MAX_COL].m_RowVector[increment%MAX_COL]) {
increment++;
}
}
}
}
void prime_factor::print_primes()
{
for (int index = 0; index < m_N; ++index) {
if (m_Vect_Primes[index/MAX_COL].m_RowVector[index%MAX_COL] == false) {
std::cout << index << " ";
}
}
}
/*!
* Driver
*/
int main(int argc, char *argv[])
{
static const unsigned long long N = 600851475143;
prime_factor pf(N);
pf.print_primes();
}
更新 我很确定这是一个有效的版本:
#include <iostream>
#include <iterator>
#include <algorithm>
#include <vector>
#include <cmath>
#include <stdexcept>
#include <climits>
typedef std::vector<unsigned long long>::const_iterator prime_it;
#define MAX_COL 900000
struct large_vector
{
public:
large_vector(unsigned long long size, unsigned int row) :
m_Row(row)
{
m_RowVector.resize(size);
}
std::vector<bool> m_RowVector;
unsigned int m_Row;
};
struct prime_factor
{
public:
prime_factor(unsigned long long N);
~prime_factor() {}
void print_primes();
private:
std::vector<bool> m_Primes;
std::vector<large_vector>m_Vect_Primes;
unsigned long long m_N;
};
prime_factor::prime_factor(unsigned long long N) :
m_N(N)
{
// If number is odd then we need the cieling of N/2 / MAX_COL
int number_of_vectors = (m_N % MAX_COL == 0) ? ((m_N/2) / MAX_COL) : (((m_N/2) / MAX_COL) + 1);
std::cout << "There will be " << number_of_vectors << " rows";
if (number_of_vectors != 0) {
for (int x = 0; x < number_of_vectors; ++x) {
m_Vect_Primes.push_back(large_vector(MAX_COL, x));
}
m_Vect_Primes[0].m_RowVector[0] = false;
m_Vect_Primes[0].m_RowVector[1] = false;
unsigned long long increment = 2;
unsigned long long index = 0;
while (index < m_N) {
for (index = 2*increment; index < m_N/2; index += increment) {
unsigned long long row = index/MAX_COL;
unsigned long long col = index%MAX_COL;
m_Vect_Primes[row].m_RowVector[col] = true;
}
increment += 1;
while (m_Vect_Primes[increment/MAX_COL].m_RowVector[increment%MAX_COL]) {
increment++;
}
}
}
}
void prime_factor::print_primes()
{
for (unsigned long long index = 0; index < m_N/2; ++index) {
if (m_Vect_Primes[index/MAX_COL].m_RowVector[index%MAX_COL] == false) {
std::cout << index << " ";
}
}
}
/*!
* Driver
*/
int main(int argc, char *argv[])
{
static const unsigned long long N = 400;
prime_factor pf(N);
pf.print_primes();
}
答案 0 :(得分:3)
您对保留的使用不正确。
m_RowVector.reserve(size);
此处m_RowVector
保留了空间,以便向量可以增长而不会重新分配。 但 m_RowVector
的大小仍为0
,因此仍然未定义访问任何元素。您必须使用resize()
或push_back()
更改数组的大小,才能将元素放入向量中。
我看不出有什么不对,但我确信你还有其他索引超出了矢量问题。我会将operator []的使用更改为方法at(),当您访问向量末尾的元素并为您提供错误实际位置的线索时,这将引发异常。