股票交易类算法

问题1:简单买卖:只允许买卖一次Best Time to Buy and Sell Stock

本题意思就是你得到一系列在接下来几天的股票价格,现在你被允许只用一次交易(就是买进再卖出)来获取最大利益。 

 求一组数中最大差问题(只能是后面的数减前面的数)

转化一下思路,求出两两相邻数的差,求一系列差值的最大连续子序列和,问题就转化为 

Maximum Subarray问题

注意两点:

收益不能为负,所以如果求出来的值小于0,输出0

如果给出的数组只有一个数,也输出0

public int maxProfit(int[] prices) {
        int length = prices.length;
        if(length < 2)return 0;
    	int sum = 0,max = Integer.MIN_VALUE;
    	for(int i =1;i<length;i++){
    	    int diff = prices[i]-prices[i-1];
    	    sum += diff;
    	    if(max < sum)max=sum;
    	    if(sum < 0)sum = 0;
    	}
    	if(max < 0)return 0;
    	return max;
    }

问题2:简单买卖:可以买卖无穷多次

意思是买卖股票时可以不计买卖次数,但是必须在买之前先把以前的股票卖掉。然后求能获利最大的额度。 这样的话也很简单,只要遇见下一天的价格比这一天价格高的话,就卖出。

求所有上升期差价的总和。

public int maxProfit(int[] prices) {
        int length = prices.length;
        int ret = 0;
        for(int i = 0;i<length-1;i++){
            if(prices[i]<prices[i+1]){
               ret +=  (prices[i+1]-prices[i]);
            }
        }
        return ret;
    }

问题3:挑选股票

挑选规则:给定一个股票集合vector<int> stocks,股票编号为1,2,3...,N。挑选规则:

1. 从左往右,第一个开始,每隔一个就删除一个;比如第一次删除的是1,3,5...

2. 从右往左,最后一个开始,每隔一个就删除一个。

重复1,2步骤,直至列表中只剩一只股票。

输入:股票个数N。

输出:最后剩下的那只股票编号。

示例:输入20,输出6。

import java.util.Scanner;
import java.util.List;
import java.util.ArrayList;


public class pickStock {
    public static void main(String[] args) {
        Scanner scan = new Scanner(System.in);       
        int n = scan.nextInt();
        List<Boolean> stocks = new ArrayList<>();
        for (int i = 0; i<n; ++i) {
            stocks.add(true);
        }

        while (true) {
            pickLeft(stocks);
            int last = check(stocks);
            if (last != -1) {
                System.out.println(last+1);
                return;
            }
            pickRight(stocks);
            last = check(stocks);
            if (last != -1) {
                System.out.println(last+1);
                return;
            }
        }
    }
    /**
     * 从左往右遍历,奇数未的股票删除(设置为false)
     */
    private static void pickLeft(List<Boolean> stocks) {
        int count = 0;
        for (int i = 0; i<stocks.size(); ++i) {
            if (stocks.get(i)) {
                count++;
            }
            if (count%2 != 0) {
                stocks.set(i, false);
            }
        }
    }

    private static void pickRight(List<Boolean> stocks) {
        int count = 0;
        for (int i = stocks.size()-1; i>=0; --i) {
            if (stocks.get(i)) {
                count++;
            }
            if (count%2 != 0) {
                stocks.set(i, false);
            }
        }
    }

    /**
     * 判断是否是最后一个,如果是,返回下标,否则返回-1
     */
    private static int check(List<Boolean> stocks) {
        int count = 0, last_index = -1;
        for (int i = 0; i<stocks.size(); ++i) {
            if(stocks.get(i)) {
                count++;
                last_index = i;
            }
            if (count > 1) {
                return -1;
            }
        }
        return last_index;
    }
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值