牛客網-華為-2020屆校園招聘上機考試-2


題目描述
小王手里有點閑錢,想着做點賣水果的小買賣,給出兩個數組m、n,用m[i]表示第i個水果的成本價,n[i]表示第i個水果能賣出的價錢,假如現在有本錢k元,試問最后最多能賺多少錢?

說明:
1.每種水果只能買一次,只能賣一次;
2.數組m,n大小不超過50;
3.數組元素為正整數,不超過1000。

輸入描述
1.數組m, n;
2.本錢k
備注:
1.首行輸入逗號分隔的數組m的元素值
2.第二行輸入逗號分隔數字n的元素值
3.第三行輸入本錢

輸出描述
最多能賺多少錢。

示例1
輸入
4,2,6,4
5,3,8,7
15
輸出
22

說明
樣例計算過程:
先買前3種水果,全部賣出,再買第4種水果,再賣出,最后本金變為22。
(感覺這個說明解釋不正確……不是正確的解題思路……)


1.思考

  • 先計算每種水果的平均利潤,即收益/本金,並按照從大到小排序,這里使用pair<int, double>來將利潤和水果index進行聯系;
  • 再按照利潤從大到小來買水果,若本金足夠則買入,否則買下一個便宜的,並將已經買過的水果用visit標記;
  • 直到所有水果都買過,或者本金不足以支撐買最便宜的水果為止。


2.知識點

  • 買入和賣出的價格不一定是個位數,這個string和int的轉換過程中要注意;
  • 在排序過程中將價格和最初的pair進行綁定,可以使用pair,及定義一個vector<pair<int, double>>類型;
  • 判斷結束的方式是:再購買並賣出一輪之后的價格和上一輪一樣,說明沒有可以買入的水果。


3.實現

#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
#include <numeric>
using namespace std;

int Str2Num(string s){
	int len = s.size();
	int n = 0;
	for (int i = 0; i < len; i++){
		n = n * 10 + s[i] - '0';
	}
	return n;
}

void Apart(string str, vector<int>& num){
	int pos, n, len;
	string s;
	while (!str.empty()){
		len = str.size();
		pos = str.find(',');
		if (pos > 0){
			s = str.substr(0, pos);
			n = Str2Num(s);
			num.push_back(n);
			str = str.substr(pos + 1, len-pos-1);
		}
		else{
			n = Str2Num(str);
			num.push_back(n);
			break;
		}
	}
}

bool comp(pair<int, double>& a, pair<int, double>& b){
	return a.second > b.second;
}

int main(){
	string inputm, inputn;

	while (getline(cin, inputm)){
		//Input
		vector<int> m, n;
		int lenin = inputm.size();
		getline(cin, inputn);
		int k;
		cin >> k;

		Apart(inputm, m);
		Apart(inputn, n);

		//Calculate average profit and sort it
		int len = m.size();
		vector<pair<int, double>> avr;
		for (int i = 0; i < len; i++){
			avr.push_back(make_pair(i, (n[i] - m[i]) / (1.0*m[i])));
		}
		sort(avr.begin(), avr.end(), comp);

		//Buy and sell
		vector<int> visit(len, 0), win;
		int i, idx, klast=-1;
		bool brk = false;
		while (!avr.empty()){			
			i = 0;
			while (i < len){
				idx = avr[i].first;
				if (visit[i]==0 && m[i] < k){
					k -= m[i];
					win.push_back(n[i]);
					visit[i] = 1;
				}
				i++;
			}
			k += accumulate(win.begin(), win.end(), 0);
			win.clear();

			if (k == klast)
				break;

			klast = k;			
		}

		cout << k << endl;
	}

	return 0;
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM