网易游戏面试--两次股票买入卖出的最大收益

第一问:

对于只有一次买入卖出的最大收益可以参照http://blog.csdn.net/calmreason/article/details/7904062,已经将的非常详细了

第二问:

当时做完这种情况后,考官又提出如果可以买入卖出两次,如何在O(N)的时间复杂度下解决问题,当时没有想出来,结果就挂了,今天想把这个问题解决掉

思路大体是这样的,如果要买卖两次的话(这里允许在同一时间卖出再买入,但是不允许同一时间买入再卖出),必定是在某一个时间点的两边进行买入和卖出的,这样就可以把问题简化为在某一个时间点左右进行一次股票买入和卖出的最大收益了。

其中在某一个时间节点左侧的最大收益是可以通过O(N)的时间复杂度得到的,只要在第一问的基础上设置一个数组ret1List[] 来存放当前节点的最大收益就可以了。问题是如何接下来计算右边的最大收益,最后发现如果将数组从后到前来遍历,再设置一个数组ret2List[] 来存放当数组从后到前来遍历时当前的最小收益,那么-1 * ret2List[]的值就对应了右边的最大收益。最后再遍历一遍,找到ret1List[i] - ret2List[i]的最大值,就是所要求的结果

代码如下:

#include <iostream>
using namespace std;
#define LEN 100

int _tmain(int argc, _TCHAR* argv[])
{
	int n;
	cin >> n;
	if(n < 3)
	{
		cout << "error input" << endl;
		return -1;
	}
	int list[LEN];
	int ret1List[LEN]; //存放从左向右遍历时每个节点的最大收益
	int ret2List[LEN];	//存放从右到左遍历时每个节点的最小收益
	for(int i = 0; i < n; i ++)
	{
		cin >> list[i];
	}
	int minNum = list[0];
	int maxDifferent = list[1] - list[0];
	for(int i = 1; i < n - 1; i ++)
	{
		if(list[i] < minNum)
		{
			minNum = list[i];
		}
		else if(list[i] - minNum > maxDifferent)
		{
			maxDifferent = list[i] - minNum;
		}
		ret1List[i] = maxDifferent;
	}
	int maxNum = list[n - 1];
	int minDifferent = list[n - 2] - list[n - 1]; 
	for(int i = n - 2; i > 0; i --)
	{
		if(list[i] > maxNum)
		{
			maxNum = list[i];
		}
		else if(list[i] - maxNum < minDifferent)
		{
			minDifferent = list[i] - maxNum;
		}
		ret2List[i] = minDifferent;
	}
	int max = ret1List[1] - ret2List[1];
	for(int i = 1; i < n - 1; i ++)
	{
		if(max < ret1List[i] - ret2List[i])
		{
			max = ret1List[i] - ret2List[i];
		}
	}
	cout << max << endl;
	return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值