使用线程时的内存分配问题
Problem with Memory Allocation while Using Threads
我正在尝试使用一个使用数据分配的结构。尽管在每个函数中获得了正确的输出,但当这些函数通过线程 运行 时,我收到了溢出错误。我目前的代码是:
#include <iostream> // cout, endl
#include <thread> // thread
using namespace std;
// a structure to hold parameters to pass to a thread
struct StatData
{
// the number of numbers
int n;
// the array of numbers
double *numbers;
};
void average(StatData *data, double *avg) {
int id;
int size = data->n;
double sum = 0.0;
for(int i = 0; i < size; i++){
sum += data->numbers[i];
}
*avg = sum / size;
}
void minimum(StatData *data, double *min) {
int id;
int size = data->n;
*min = data->numbers[0];
for(int i = 0; i < size; i++){
if (*min > data->numbers[i]){
*min = data->numbers[i];
}
}
}
void maximum(StatData *data, double *max) {
int id;
int size = data->n;
*max = data->numbers[0];
for(int i = 0; i < size; i++){
if (*max < data->numbers[i]){
*max = data->numbers[i];
}
}
}
int main(int argc, char** argv) {
// checking if arguments were passed
if (argc <= 1) {
cout << "No numbers were passed." << endl;
cout << "At least one number needs to be entered." << endl;
return 1;
}
// declaring worker threads
thread avg_t, min_t, max_t;
// variables for values
double avg_v;
double min_v;
double max_v;
// initalizing data structure to hold numbers
StatData data;
data.n = argc - 1; // the amount of numbers passed
data.numbers = new double[data.n]; // allocating space for nums
// Filling in the array with numbers using atof
for (int i = 0; i < data.n; i++) {
data.numbers[i] = atof(argv[i+1]); // converting string to double
}
// creating average thread
avg_t = thread(average, &data, &avg_v);
// creating minimum thread
min_t = thread(minimum, &data, &min_v);
// creating maximum thread
max_t = thread(maximum, &data, &max_v);
// wating for threads to finish
avg_t.join();
min_t.join();
max_t.join();
printf ("The average value is %d\n", &avg_v);
printf ("The minimum value is %d\n", &min_v);
printf ("The maximum value is %d\n", &max_v);
// freeing up dynamically allocated space
delete[] data.numbers;
}
当我 运行 一个 ./test 值为 47、58 和 6 时,我得到一个打印语句:
平均值为-502425280
最小值为 -502425288
最大值为-502425296
我不确定导致代码执行此操作的错误所在。
您正在打印值的地址(&avg_v
是指向 avg_v
的指针,当打印为 %d
时,将打印指针本身的一部分值).
要打印 double
值本身,只需执行
printf ("The average value is %lf\n", avg_v);
printf ("The minimum value is %lf\n", min_v);
printf ("The maximum value is %lf\n", max_v);
注意 %d
用于打印 整数 ,对于浮点值使用 %f
或 %lf
(两者等价)。
&
仅在 scanf
中需要,因为 scanf
获取变量的地址。 printf
采用实际值,因此无需将地址传递给它(当然除非你想打印地址)。
解决了这个问题后,可以通过使用更多 C++ 标准库功能使程序变得更简单。仅举几例:std::vector
、std::accumulate
、std::min_element
、std::max_element
、std::async
(这会为您创建一个线程和 returns 一个未来)和 lambda:
#include <iostream>
#include <thread>
#include <vector>
#include <numeric>
#include <algorithm>
#include <future>
int main(int argc, char** argv) {
if (argc <= 1) {
std::cout << "No numbers were passed.\n"
"At least one number needs to be entered.\n";
return 1;
}
std::vector<double> data;
for (int i = 1; i < argc; i++) {
data.push_back(atof(argv[i]));
}
auto avg_f = std::async([&] {
return accumulate(data.begin(), data.end(), 0.0) / data.size();
});
auto min_f = std::async([&] {
return *min_element(data.begin(), data.end());
});
auto max_f = std::async([&] {
return *max_element(data.begin(), data.end());
});
// the 3 values are now being computed in parallel ...
double avg_v = avg_f.get(); // get the values from futures (waits as necessary)
double min_v = min_f.get();
double max_v = max_f.get();
std::cout << "The average value is " << avg_v << "\n";
std::cout << "The minimum value is " << min_v << "\n";
std::cout << "The maximum value is " << max_v << "\n";
}
我正在尝试使用一个使用数据分配的结构。尽管在每个函数中获得了正确的输出,但当这些函数通过线程 运行 时,我收到了溢出错误。我目前的代码是:
#include <iostream> // cout, endl
#include <thread> // thread
using namespace std;
// a structure to hold parameters to pass to a thread
struct StatData
{
// the number of numbers
int n;
// the array of numbers
double *numbers;
};
void average(StatData *data, double *avg) {
int id;
int size = data->n;
double sum = 0.0;
for(int i = 0; i < size; i++){
sum += data->numbers[i];
}
*avg = sum / size;
}
void minimum(StatData *data, double *min) {
int id;
int size = data->n;
*min = data->numbers[0];
for(int i = 0; i < size; i++){
if (*min > data->numbers[i]){
*min = data->numbers[i];
}
}
}
void maximum(StatData *data, double *max) {
int id;
int size = data->n;
*max = data->numbers[0];
for(int i = 0; i < size; i++){
if (*max < data->numbers[i]){
*max = data->numbers[i];
}
}
}
int main(int argc, char** argv) {
// checking if arguments were passed
if (argc <= 1) {
cout << "No numbers were passed." << endl;
cout << "At least one number needs to be entered." << endl;
return 1;
}
// declaring worker threads
thread avg_t, min_t, max_t;
// variables for values
double avg_v;
double min_v;
double max_v;
// initalizing data structure to hold numbers
StatData data;
data.n = argc - 1; // the amount of numbers passed
data.numbers = new double[data.n]; // allocating space for nums
// Filling in the array with numbers using atof
for (int i = 0; i < data.n; i++) {
data.numbers[i] = atof(argv[i+1]); // converting string to double
}
// creating average thread
avg_t = thread(average, &data, &avg_v);
// creating minimum thread
min_t = thread(minimum, &data, &min_v);
// creating maximum thread
max_t = thread(maximum, &data, &max_v);
// wating for threads to finish
avg_t.join();
min_t.join();
max_t.join();
printf ("The average value is %d\n", &avg_v);
printf ("The minimum value is %d\n", &min_v);
printf ("The maximum value is %d\n", &max_v);
// freeing up dynamically allocated space
delete[] data.numbers;
}
当我 运行 一个 ./test 值为 47、58 和 6 时,我得到一个打印语句: 平均值为-502425280 最小值为 -502425288 最大值为-502425296
我不确定导致代码执行此操作的错误所在。
您正在打印值的地址(&avg_v
是指向 avg_v
的指针,当打印为 %d
时,将打印指针本身的一部分值).
要打印 double
值本身,只需执行
printf ("The average value is %lf\n", avg_v);
printf ("The minimum value is %lf\n", min_v);
printf ("The maximum value is %lf\n", max_v);
注意 %d
用于打印 整数 ,对于浮点值使用 %f
或 %lf
(两者等价)。
&
仅在 scanf
中需要,因为 scanf
获取变量的地址。 printf
采用实际值,因此无需将地址传递给它(当然除非你想打印地址)。
解决了这个问题后,可以通过使用更多 C++ 标准库功能使程序变得更简单。仅举几例:std::vector
、std::accumulate
、std::min_element
、std::max_element
、std::async
(这会为您创建一个线程和 returns 一个未来)和 lambda:
#include <iostream>
#include <thread>
#include <vector>
#include <numeric>
#include <algorithm>
#include <future>
int main(int argc, char** argv) {
if (argc <= 1) {
std::cout << "No numbers were passed.\n"
"At least one number needs to be entered.\n";
return 1;
}
std::vector<double> data;
for (int i = 1; i < argc; i++) {
data.push_back(atof(argv[i]));
}
auto avg_f = std::async([&] {
return accumulate(data.begin(), data.end(), 0.0) / data.size();
});
auto min_f = std::async([&] {
return *min_element(data.begin(), data.end());
});
auto max_f = std::async([&] {
return *max_element(data.begin(), data.end());
});
// the 3 values are now being computed in parallel ...
double avg_v = avg_f.get(); // get the values from futures (waits as necessary)
double min_v = min_f.get();
double max_v = max_f.get();
std::cout << "The average value is " << avg_v << "\n";
std::cout << "The minimum value is " << min_v << "\n";
std::cout << "The maximum value is " << max_v << "\n";
}