美文网首页
业余爱好(24点问题)

业余爱好(24点问题)

作者: 这样你就找不到我了 | 来源:发表于2020-09-27 11:10 被阅读0次

    四个数的运算结果,可以看成三个数的运算结果与一个数的运算结果
    三个数的运算结果,可以看成两个数的运算结果与一个数的运算结果
    两个数的运算结果,可以看成一个数的运算结果与一个数的运算结果

    我们A,B,B,D表示四个数,用X表示某种运算关系,可以得到如下:

    X(ABCD)= X(A X(BCD))
    X(A X(BCD)) = X(A X(X(B X(CD))))
    X(A X(X(B X(CD))))= X(A X(X(B X(X(CXD)))))

    以上可知:任意四个数的运算结果,可以转化为前两个数的运算结果 与 第三个数的运算结果 与 第四个数的运算结果。

    值得注意的是,如果是1 2 3 4 这四个数,其实同时包含了 -1 -2 -3 -4 这四个数。

    举个例子:
    5x(5-1/5)= -1/5的结果 + 5 的结果 x 5的结果 = (-1/5+5)x5

    因此我们可以设计程序,从左至右,每次计算两个枚举数的值,进而得出最终结果。

    这里使用深度遍历的方式枚举所有的可能,ABCD四个数,在1234个位置上都要出现
    dfs(int n,double ans int *a)的n表示当前结算第几个数与ans的运算结果,ans记录上一次运算的结果,数组a中存储着ABCD四个数。
    最开始,我们默认第一个计算的结果ans为数组中的第一个数,即ans = a[0],注意这里的a[0]每次计算之后需要调整,使ABCD四个数都在a[0]中出现过。
    0位置的数用完之后,与之计算的下一个数自然就是1位置的数了,所以n初值为1。
    使用0123这四个数映射+-x/四种运算。
    注意前面提到的,每个数都可以变为负数。

    #include<stdio.h>
    
    
    int flag = 0;
    void dfs(int n,double ans,int *a){
        if(n==4){
            if(ans == 24){
                flag = 1;//flag=1输出Yes 
            }
        }
        if(n<4){
        for(int i=n;i<4;i++)
            for(int w=0;w<4;w++){
                if(w==0){
                    dfs(n+1,ans+a[n],a);
                    dfs(n+1,-(ans+a[n]),a);
                }
                    
                if(w==1){
                    dfs(n+1,ans-a[n],a);
                    dfs(n+1,-(ans-a[n]),a);
                }
                
                if(w==2){
                    dfs(n+1,ans*a[n],a);
                    dfs(n+1,-ans*a[n],a);
                }
                
                if(w==3){
                    dfs(n+1,ans/double(a[n]),a);
                    dfs(n+1,-ans/double(a[n]),a);
                }
            }
        }
    }
    
    int main(){
        int point[2];
        while(true){
            int a[4];
            for(int i=0;i<4;i++){
                scanf("%d",a+i);
            }
            if(a[0]==0&&a[1]==0&&a[2]==0&&a[3]==0)
                break;
            
            for(int i=0;i<4;i++){
                //四个数都有机会充当第一个数进行计算
                int t = a[0];
                a[0] = a[i];
                a[i] = t;
                dfs(1,a[0],a);
                //别忘了还原,下次还要交换 
                t = a[0];
                a[0] = a[i];
                a[i] = t;
            }
                
            
            if(flag)
                printf("YES\n");
            else
                printf("NO\n");
            flag = 0;
            
        }
        return 0;
    } 
    
    
    
    

    相关文章

      网友评论

          本文标题:业余爱好(24点问题)

          本文链接:https://www.haomeiwen.com/subject/gfmkuktx.html