《算法分析》股民解套

题目要求

某股民投资某证券,购入该证券时间作为起始点0,当天的盈亏也定为0。假定证券价格每个交易日的变化有三档:比前一个交易日上涨1个单位,与前一个交易日持平,比前一个交易日下跌1个单位。

该股民对其持有证券的收益期望值是k个单位。即:只要该证券的价格比其购入的价格高k个单位,他就会卖出

题目分析

由题目可知,每天的交易变化为三种,分别是:-1、0、1。由用户输入交易日和期望获得的交易利益。当交易日为3时,表示三天的交易变化。且当收益提前达到期望收益时,则立刻卖出股票。

由此可知,当交易日为3时,且没有提前达到收益时,最大的循环次数为27次,则3的n次方,即交易日的n次方种可能性中找出能够达到收益的交易变化,并统计出有多少种方案。

该证券获利了结,反之如果没有达到预期的利润,他就会继续持有该证券,持有的天数最多为N个交易日。在第N个交易日,股民已经失去了耐心,无论是否达到收益预期,证券都会被该股民卖出。

解决方式:

当输入3 1 时可能出现的结果如下:

程序从day = 3 开始,当day>1时,一直嵌套直至day = 1,当day = 1时,意味着,进入最末端的判断,此时在最末端进行三次循环,并且加前两次循环的值,判断是否满足期望收入。当末端三次循环判断完成后,返回到上一层,即第二层day = 2 ,改变第二次的值后再次进入末端循环判断是否满足期望收入,当第二层的三次判断都完成后,返回到第一层,即day = 3,改变第一次的值后,再次进入第二层,第二层同样从-1开始赋值,赋值后进入末端,进行循环判断,以此类推。当循环在第二层或第一层就已经满足期望收入时,即不再进行后面的循环判断。  

流程图如下:

 

代码如下:

一、初始化部分

#include <stdio.h>
int k;                  //控制数组下标
int y;                  //控制数组下标
int x;                  //控制数组下标
int a[10] = {5,5,5,5,5,5};         //数组保存满足条件的变化(为了看变化 所以赋值为5)
int count = 0;          //保存有多少个满足条件
int j = 0;              //存储这一次生成的序列和是否满足用户所需要的交易额
void array(int);    //定义了一个自定义函数,穷举出所有的可能性
int day;            //保存用户所需要的交易天数
int company;        //保存用户所期望的获利单位
int arrday;         //固定存放交易天数

(代码只是最基础的写出,并没有进行整理优化)

二、主函数(用于输入输出和调用)

int main() {                                        //主函数用于调用
    printf("请输入最多持有几个交易额:");
    scanf("%d",&day);
    printf("请输入期望获利单位:");
    scanf("%d",&company);
    arrday = day;           //固定存放交易天数
    array(company);         //调用函数
    printf("\n");
    printf("count = %d",count);                     //输出
}

三、自定义函数(功能的实现)




void array(int company){
    int i;              //循环单位,表示第一天生成的三个数分别是-1、0、1
    if (day > 1){
        for (i = -1 ; i <= 1 ; i++ ){
            a[day] = i;                       //改变当前数组的值
            day = day - 1;
            j = j + i;                      //累加趋势
            if (j == company){              //如果本次循环中J等于所需的获利,则增加一次
               count = count + 1;               //计数加一
                    for (x = arrday ; x > day ; x--){
                        printf("%d",a[x]);
                        a[x] = 0;
                    }
               printf("\n");
               day = day + arrday - 1;
               j = 0;               //归零趋势累加
               k = 0;               //归零计数器
               continue;            //提前满足后结束本次循环,进入下一次
            }
            //printf ("-----)%d\n",day);            //测试递归之前的day值为多少
            array(company);             //递归调用
            //printf("%d\n",j);             //测试J返回来的值
            j =  j - i;                     //减去上次判断的值
            //printf("****%d\n",j);          //测试当前J的值
            //printf("****%d\n",day);               //测试当前day的值是否传递回来
            if (k == 9){                     //每就是往上多回归一次(找一个不确定的值)
                day = day + 1;
                k = 0;
            }
        }
    }
    else{                       //最后一天的三种结果生成
        for (i = -1 ; i <=1 ;i++){
            k = k + 1;
            j =j + i;
            if (j == company){  //如果满足条件,则输出
                a[day] = i;                           //本次的结果加入到数组
                    for(y = arrday ; y >= day; y--) {         //输出之前的每天增长趋势  (暂时性改动 y = 3 ; y >= 0 ; y--)
                        printf("%d", a[y]);
                    }
                a[y+1] = 0;
                printf("\n");
                count = count + 1;                      //累加1
                j = j - i;                              //减去本次的值
            }
            else{
                j = j - i;                          //减去上次本次判断的值
            }
        }
        //printf("****%d\n",day);           //测试当前在第几层递归
        day = day + 1;
        //printf("---%d\n",day);            //测试day是否改变
    }
}

其中运用的函数的递归调用以及选择结构。并且包含了一些编码时的测试代码。

运行效果:



本次代码并不完善,只可以完成基础的几个计算,并可以完成所有的功能,后续更新出完美的代码,并且本题有多种解题思路,这种方法思路较难,不好理解。只用作作者自己的学习记录。

----2022/11/25



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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值