【问题标题】:about sstream, using a variable as array size and calculation overflow关于sstream,使用变量作为数组大小和计算溢出
【发布时间】:2013-10-04 16:56:51
【问题描述】:

需要在不知道数组大小的情况下从文本文件中读取一次,然后计算均值和方差。 现在我无法创建特定的数组。结果,我无法计算均值和方差。 我真的希望你们能提供帮助。

#include <iostream>
#include <fstream>
#include <string>
#include <sstream>
#include <math.h>
#include "fraction.h"

using namespace std;

void ascending(fraction fractionarr[]);
fraction mean(fraction fractionarr[]);
fraction variance(fraction fractionarr[]);
static const int countlinenumber(ifstream& data);


void ascending(fraction fractionarr[])
{
ifstream data("data1.txt");
fraction temp;
fraction test(0, 1);
int n = 0;
int linenumber = countlinenumber(data);

for (int i = 0; i < 100; i++)
{
    if(fractionarr[i] != test)
    {
        n++;
    }
}
for (int i = 0; i < linenumber; i++)
{
    for(int j = 0; j < linenumber-1; j++)
    {
        if(fractionarr[i+1] != test)
        {
            if(fractionarr[j] > fractionarr[j+1])
            {
                temp = fractionarr[j];
                fractionarr[j] = fractionarr[j+1];
                fractionarr[j+1] = temp;
            }
        }
    }
}
}

fraction mean(fraction fractionarr[])
{
ifstream data("data1.txt");
fraction sum = fractionarr[0];
fraction average;
fraction n(1,1);
fraction test(0,1);
int linenumber = countlinenumber(data);

for (int i = 1; i < linenumber; i++)
{
    if(fractionarr[i] != test)
    {
        sum = sum + fractionarr[i];
        n = n + fraction(1,1);
    }
}

average = sum / n;
return average;
}  

fraction variance(fraction fractionarr[])
{
ifstream data("data1.txt");
fraction average = mean(fractionarr);
fraction* semi = new fraction[100];
fraction total;
fraction t(1, 1);
fraction variance;
fraction test(0,1);
int linenumber = countlinenumber(data);

for (int i = 0; i < linenumber; i++)
{
    if(fractionarr[i] != test)
    {
        semi[i] = (fractionarr[i]-average) * (fractionarr[i]-average);
        t = t + fraction(1, 1); 
    }
}
total = semi[0];
for (int i = 1; i < 100; i++)
{
    if(semi[i] != test)
    {
        total = total + semi[i];
    }
}
variance = total / t;
return variance;
}

static const int countlinenumber(ifstream& data)
{
string temp;
int linenumber = 0;

while(getline(data, temp) && !data.eof())
{
    linenumber++;
}
return linenumber;
}

int main()
{
ifstream data("data1.txt");
ofstream data_out("data1_out.txt");
stringstream ss;

string temp;
char op;
fraction testing(0,1);
fraction average;
static const int linenumber = countlinenumber(data);

int* numerator = new int[linenumber];
int* denominator = new int[linenumber];
fraction* fractionarr = new fraction[linenumber];

for(int i = 0; i < linenumber; i++)
{
    numerator[i] = 0;
    denominator[i] = 0;
}

for(int i = 0; i < linenumber; i++)
{
    if(!data.eof())
    {
        getline(data, temp, '\n');
        ss << temp;
        ss >> numerator[i] >> op >> denominator[i];
        ss.clear();
    }
}
delete [] numerator;
delete [] denominator;

ascending(fractionarr);
for (int i = 0; i < linenumber; i++)
{
    if(fractionarr[i] != testing)
        data_out << fractionarr[i] << endl;
}
data_out.close();

cout << mean(fractionarr) << endl;
average = mean(fractionarr);
cout << variance(fractionarr) << endl;

system("pause");
return 0;


}

【问题讨论】:

  • “我无法创建特定数组”是什么意思?在我看来,您确实创建了数组。您的代码的主要问题似乎是文件处理,到处都是。
  • std::vector 救援。
  • 您也多次阅读该文件,但您被要求阅读一次文本文件。我猜这个问题的真正含义是,当我事先不知道数组的大小并且不允许重新读取数据时,如何将数据读入数组?一个答案是像 Jerry 所说的那样使用 std::vector ,但我想你必须使用数组。如果是这种情况,那么当你知道你需要一个更大的数组时,你必须 resize 数组。所以数组开始时很小,但随着读取的数据越来越多,它的大小会增加。
  • @john 我想我会...但是当我编译整个东西时,分子数组和分母数组都不存在...
  • @JerryCoffin 我之前没有学过 std::vector ......我已经用谷歌搜索了这个主题几天但仍然无法弄清楚

标签: c++ arrays overflow sstream


【解决方案1】:

恐怕这看起来很像家庭作业,我不得不只提供一个方向的想法,而不是一个完整的解决方案来完成你所要求的一切。我希望这足以让你开始:

#include <sstream>
#include <vector>
#include <iterator>
#include <numeric>

int main(){
    std::istringstream input("1 200 50 9.5 300.1");

    std::vector<double> numbers{std::istream_iterator<double>(input), 
                    std::istream_iterator<double>()};

    double sum = std::accumulate(numbers.begin(), numbers.end(), 0.0);

    std::cout << "Sum: " << sum << "\n";
    std::cout << "Count: " << numbers.size() << "\n";
}

这不会计算均值或方差,但根据这里的情况,我相信添加均值的计算应该是微不足道的,而方差只是稍微困难一点(注意:对于方差,您需要std::accumulate 的版本,它使用 lambda 计算与均值的每个平方差)。

【讨论】:

  • 我必须在向量中使用这些函数吗?
  • @user2847449:有很多不同的方法可以完成这项工作,但这个(IMO)是更简单的方法之一。
  • 请问“std::vector numbers{std::istream_iterator(input), std::istream_iterator()};”是什么意思跨度>
  • @user2847449:它正在从迭代器中初始化向量,迭代器从流中读取数据。
  • 但是当我将该行输入到我的视觉工作室时,出现错误提示“预期为';'”...
猜你喜欢
  • 1970-01-01
  • 2021-08-02
  • 2019-12-28
  • 1970-01-01
  • 2012-07-02
  • 1970-01-01
  • 1970-01-01
  • 2022-01-19
  • 2020-09-01
相关资源
最近更新 更多