Closed. This question is off-topic. It is not currently accepting answers. Learn more。
想改进这个问题吗?Update the question所以堆栈溢出的值小于aa>。
两年前关闭。
我有一个奇怪的问题,我的C++多线程程序没有运行到完成。它应该运行NUM_线程-1次。任何资源,以帮助我在正确的方向将不胜感激!
目前这些是重要的功能
在
来自
此外,当相同的容器(
想改进这个问题吗?Update the question所以堆栈溢出的值小于aa>。
两年前关闭。
我有一个奇怪的问题,我的C++多线程程序没有运行到完成。它应该运行NUM_线程-1次。任何资源,以帮助我在正确的方向将不胜感激!
目前这些是重要的功能
int main(void) {
int ret;
//Threads + current thread tracker
pthread_t threads[NUM_THREADS]; int j = 0;
int num_transacts = 0; bool isBuy = true;
srand(time(NULL));
Stock MSFT("MSFT"); stocks.push_back(MSFT);
Stock AMZN("AMZN"); stocks.push_back(AMZN);
Stock BAC("BAC"); stocks.push_back(BAC);
Stock NKE("NKE"); stocks.push_back(NKE);
//Buys or Sells for NUM_THREADS - 1 times
while (num_transacts < NUM_THREADS) {
if (isBuy) {
//Percent chance to buy
if (((double)rand() / (double)RAND_MAX) < Z) {
cout << "Making buy thread.\n";
pthread_mutex_lock(&mLock);
ret = pthread_create(&threads[j], NULL, buy, NULL);
if (ret != 0) {
cout << "Thread failed at Buy Thread Create.\n";
}
pthread_mutex_unlock(&mLock);
cout << "BuyNumTrans: " << num_transacts << "\n";
++j;
++num_transacts;
isBuy = false;
}
}
else {
if (bought.size() > 0) {
//Percent chance to sell if it has increased or decreased too much in price
int s = rand() % bought.size();
if ((bought.at(s).checkPrice()) > (((1 + X)*bought.at(s).getCost())) || (bought.at(s).checkPrice()) < (((1 + Y)*bought.at(s).getCost()))) {
cout << "Making sell thread.\n";
pthread_mutex_lock(&mLock);
ret = pthread_create(&threads[j], NULL, sell, (void*) &s);
if (ret != 0) {
cout << "Thread failed at Sell Thread Create.\n";
}
pthread_mutex_unlock(&mLock);
cout << "SellNumTrans: " << num_transacts << "\n";
++j;
++num_transacts;
}
//Gets a new price possibility
bought.at(s).getPrice();
}
isBuy = true;
}
}
for (int i = 0; i < NUM_THREADS; ++i) {
pthread_join(threads[i], NULL);
}
return 0;
}
pthread_mutex_t mLock;
pthread_mutex_t bLock;
pthread_mutex_t sLock;
vector<Stock> stocks;
vector<Stock> bought;
int balance = 1000000, yield = 0, profit = 0, Tcost = 0;
//In format BUY MSFT 100 35.2
//In format SELL MSFT 80 45
void* processTransact(void* argument) {
string* arg = (string*)argument;
istringstream iss(*arg);
vector<string> words{ istream_iterator<string>(iss), istream_iterator<string> {} };
if (words.front() == "BUY") {
words.erase(words.begin());
//gets the symbol name
string symbol = words.front();
words.erase(words.begin());
//gets num of stocks to buy
string a = words.front();
int buyNum = atoi(a.c_str());
words.erase(words.begin());
//gets the price per share
a = words.front();
int sharePrice = atoi(a.c_str());
//update num_shares, cost, balance, and Tcost
Stock newBuy(symbol, buyNum, sharePrice);
balance -= (buyNum * sharePrice);
bought.push_back(newBuy);
cout << "Bought stock... " << balance << endl;
pthread_exit(NULL);
}
else {
words.erase(words.begin());
//gets the symbol name
string symbol = words.front();
words.erase(words.begin());
//gets num of stocks to sell
string a = words.front();
int buyNum = atoi(a.c_str());
words.erase(words.begin());
//gets the price per share
a = words.front();
int sharePrice = atoi(a.c_str());
a = words.front();
int s = atoi(a.c_str());
//update num_shares, cost, balance, and Tcost
balance += (buyNum * sharePrice);
bought.erase(bought.begin() + s);
cout << "Sold stock... " << balance << endl;
pthread_exit(NULL);
}
sleep(2);
}
void* buy(void*) {
pthread_mutex_lock(&mLock);
pthread_t thread;
srand(time(NULL));
int ret;
int i = rand() % stocks.size();
//Creates a string that processTransact can parse
string transactString = "BUY " + stocks.at(i).getName() + " 100 " + to_string(stocks.at(i).getPrice());//make transaction string
ret = pthread_create(&thread, NULL, processTransact, (void*)&transactString);
if (ret != 0) {
cout << "Error in buy thread process create.\n";
}
pthread_join(thread, NULL);
pthread_mutex_unlock(&mLock);
pthread_exit(NULL);
}
void* sell(void* argument) {
pthread_mutex_lock(&mLock);
pthread_t thread;
int ret, s = *((int*)argument);;
//Creates a string that processTransact can parse
string transactString = "SELL " + bought.at(s).getName() + " 100 " + to_string(bought.at(s).getPrice()) + to_string(s);//make transaction string
ret = pthread_create(&thread, NULL, processTransact, (void*)&transactString);
if (ret != 0) {
cout << "Error in sell thread process create.\n";
}
pthread_join(thread, NULL);
pthread_mutex_unlock(&mLock);
pthread_exit(NULL);
}
最佳答案
在上面的代码中,我看到了在bought
变量访问期间潜在的未定义行为问题。这可能是你问题的原因。
在while
循环中有行:
if (bought.size() > 0) {
//Percent chance to sell if it has increased or decreased too much in price
int s = rand() % bought.size();
在
void* processTransact(void* argument)
函数中:bought.push_back(newBuy);
// Code skipped ....
bought.erase(bought.begin() + s);
来自
processTransact
的代码在单独的线程中修改bought
的大小。在while
循环中,对bought.size()
的访问与使用mLock
互斥量不同步。这意味着您可能在bought
验证后得到空的bought.size() > 0
向量。它在rand() % 0
处导致未定义的行为。此外,当相同的容器(
bought
)从不同的线程修改和读取时,C++标准并不保证thread safety。09-05 22:51