蓝桥杯历年真题,来,看看

.标题: 世纪末的星期


    曾有邪教称1999年12月31日是世界末日。当然该谣言已经不攻自破。

    还有人称今后的某个世纪末的12月31日,如果是星期一则会....

    有趣的是,任何一个世纪末的年份的12月31日都不可能是星期一!! 

    于是,“谣言制造商”又修改为星期日......

    1999年的12月31日是星期五,请问:未来哪一个离我们最近的一个世纪末年(即xx99年)的12月31日正好是星期天(即星期日)?

    请回答该年份(只写这个4位整数,不要写12月31等多余信息)

2299,Calender类可用于1970年以后的日期操作

Java中Calendar类的常用方法https://blog.csdn.net/yx0628/article/details/79317440

public class _01_世纪末的星期 {
  public static void main(String[] args) {
    Calendar calendar = Calendar.getInstance();//可用于1970年后操作日期用
    for (int year = 1999; year < 10000; year+=100) {
      calendar.set(Calendar.YEAR,year);
      calendar.set(Calendar.MONTH,11);//12月  只有月份是0开始的,0对应1月
      calendar.set(Calendar.DAY_OF_MONTH,31);
      System.out.println(year+" "+calendar.get(Calendar.DAY_OF_WEEK));
      if(calendar.get(Calendar.DAY_OF_WEEK)==1){//1:星期天 2:星期一 外国人的第一天是星期天
        break;
      }
    }
  }
}
 下面这个特别暴力的代码不只适合1970以后的日子,考点闰年判断

import java.util.Scanner;
 
public class _01_世纪末的星期1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int year = 1999;
        int week = 4;//为了方便求模,0代表星期一,1999年12月31是星期五,初始化4
//        int[] data1 = new int[] {-1,31,28,31,30,31,30,31,31,30,31,30,31};
//        int[] data2 = new int[] {-1,31,29,31,30,31,30,31,31,30,31,30,31};//闰年天数
        
        for(year=2000;year<=9999;year++) {
                if((year%100!=0 && year%4==0) || year%400==0)
                    week = (week+366)%7;
                else
                    week = (week+365)%7;
                if(year%100==99)
                    System.out.println(year+" "+week);
        }
        
    }
 
}

2.标题: 马虎的算式


    小明是个急性子,上小学的时候经常把老师写在黑板上的题目抄错了。

    有一次,老师出的题目是:36 x 495 = ?

    他却给抄成了:396 x 45 = ?

    但结果却很戏剧性,他的答案竟然是对的!!

    因为 36 * 495 = 396 * 45 = 17820

    类似这样的巧合情况可能还有很多,比如:27 * 594 = 297 * 54

    假设 a b c d e 代表1~9不同的5个数字(注意是各不相同的数字,且不含0)

    能满足形如: ab * cde = adb * ce 这样的算式一共有多少种呢?


请你利用计算机的优势寻找所有的可能,并回答不同算式的种类数。

满足乘法交换律的算式计为不同的种类,所以答案肯定是个偶数。


答案直接通过浏览器提交。
注意:只提交一个表示最终统计种类数的数字,不要提交解答过程或其它多余的内容。
 

142,暴力到没朋友,填空题暴力枚举就好,别想什么回溯

import java.util.Scanner;
 
public class _02_马虎的算式1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int ans=0;
        for(int a=1;a<=9;a++)
            for(int b=1;b<=9;b++) {
                if(b==a)
                    continue;
                for(int c=1;c<=9;c++) {
                    if(c==a || c==b)
                        continue;
                    for(int d=1;d<=9;d++) {
                        if(d==a || d==b || d==c)
                            continue;
                        for(int e=1;e<=9;e++) {
                            if(e==a || e==b || e==c || e==d)
                                continue;
                            if((10*a+b)*(100*c+10*d+e)==(100*a+10*d+b)*(10*c+e))//ab * cde = adb * ce
                                ans++;
                        }            
                    }
                }
            }
        
        System.out.println(ans);    
    }
}
 


3.标题: 振兴中华

    小明参加了学校的趣味运动会,其中的一个项目是:跳格子。

    地上画着一些格子,每个格子里写一个字,如下所示:(也可参见p1.jpg)

从我做起振
我做起振兴
做起振兴中
起振兴中华


    比赛时,先站在左上角的写着“从”字的格子里,可以横向或纵向跳到相邻的格子里,但不能跳到对角的格子或其它位置。一直要跳到“华”字结束。


    要求跳过的路线刚好构成“从我做起振兴中华”这句话。

    请你帮助小明算一算他一共有多少种可能的跳跃路线呢?

答案是一个整数,请通过浏览器直接提交该数字。
注意:不要提交解答过程,或其它辅助说明类的内容。


35,dp,递归都可以,leetcode 62. 不同路径(Unique Paths) 

import java.util.Scanner;
 
public class _03_振兴中华 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int[][] dp = new int[15][15];
        
        for(int i=1;i<=5;i++) //预处理
            dp[i][1] = dp[1][i] = 1;
            
        for(int i=2;i<=5;i++)
            for(int j=2;j<=5;j++)
                dp[i][j] = dp[i][j-1] + dp[i-1][j];
        System.out.println(dp[4][5]);
        System.out.println(f(4,5));
    }
    
    static int f(int x,int y){
        if(x==1 && y==1)
            return 1;
        if(x==1)
            return f(x,y-1);
        if(y==1)
            return f(x-1,y);
        
        return f(x-1,y) + f(x,y-1);
    }
 
}
 


4.标题: 黄金连分数


    黄金分割数0.61803... 是个无理数,这个常数十分重要,在许多工程问题中会出现。有时需要把这个数字求得很精确。

    对于某些精密工程,常数的精度很重要。也许你听说过哈勃太空望远镜,它首次升空后就发现了一处人工加工错误,对那样一个庞然大物,其实只是镜面加工时有比头发丝还细许多倍的一处错误而已,却使它成了“近视眼”!!


    言归正传,我们如何求得黄金分割数的尽可能精确的值呢?有许多方法。

    比较简单的一种是用连分数:

                  1
    黄金数 = ---------------------
                        1
             1 + -----------------
                          1
                 1 + -------------
                            1
                     1 + ---------
                          1 + ...

                           

    这个连分数计算的“层数”越多,它的值越接近黄金分割数。

    请你利用这一特性,求出黄金分割数的足够精确值,要求四舍五入到小数点后100位。

    小数点后3位的值为:0.618
    小数点后4位的值为:0.6180
    小数点后5位的值为:0.61803
    小数点后7位的值为:0.6180340
   (注意尾部的0,不能忽略)

你的任务是:写出精确到小数点后100位精度的黄金分割值。

注意:尾数的四舍五入! 尾数是0也要保留!

显然答案是一个小数,其小数点后有100位数字,请通过浏览器直接提交该数字。
注意:不要提交解答过程,或其它辅助说明类的内容。

精确到100位,一看就知道是要考大数类,感觉每年都会考一题大数类

//1.化为求斐波那契相邻两项的比值,到多少项?越多越精确,n/n+1项,n再往上增加,这个比值的小数点后101位是稳定的,也就是不变的
//  2.double无法表示100位小数,BigInteger和BigDecimal
public class _04黄金连分数 {
  public static void main(String[] args) {
    BigInteger a=BigInteger.ONE;
    BigInteger b=BigInteger.ONE;
    //斐波那契数列的迭代形式
    for (int i = 3; i < 500; i++) {
      BigInteger t=b;
      b=a.add(b);//大整数的加法
      a=t;
    }
    //大浮点数的除法
    BigDecimal divide = new BigDecimal(a,110).divide(new BigDecimal(b,110), BigDecimal.ROUND_HALF_DOWN);
    //截取字符串
    System.out.println(divide.toPlainString().substring(0,103));
 
  }
}
//0.6180339887498948482045868343656381177203091798057628621354486227052604628189024497072072041893911375
 

5.标题:有理数类

    有理数就是可以表示为两个整数的比值的数字。一般情况下,我们用近似的小数表示。但有些时候,不允许出现误差,必须用两个整数来表示一个有理数。

    这时,我们可以建立一个“有理数类”,下面的代码初步实现了这个目标。为了简明,它只提供了加法和乘法运算。

class Rational
{
    private long ra;
    private long rb;
    
    private long gcd(long a, long b){
        if(b==0) return a;
        return gcd(b,a%b);
    }
    public Rational(long a, long b){
        ra = a;
        rb = b;    
        long k = gcd(ra,rb);
        if(k>1){ //需要约分
            ra /= k;  
            rb /= k;
        }
    }
    // 加法
    public Rational add(Rational x){
        return ________________________________________;  //填空位置
    }
    // 乘法
    public Rational mul(Rational x){
        return new Rational(ra*x.ra, rb*x.rb);
    }
    public String toString(){
        if(rb==1) return "" + ra;
        return ra + "/" + rb;
    }
}
 
使用该类的示例:
    Rational a = new Rational(1,3);
    Rational b = new Rational(1,6);
    Rational c = a.add(b);
    System.out.println(a + "+" + b + "=" + c);

请分析代码逻辑,并推测划线处的代码,通过网页提交
注意:仅把缺少的代码作为答案,千万不要填写多余的代码、符号或说明文字!!

数学通分:a/b + c/d = (a*d+b*c)/(b*d)

new Rational(ra*x.rb+rb*x.ra, rb*x.rb)
new Rational(this.ra * x.rb + x.ra * this.rb, this.rb * x.rb)
上面的答案都行,不要this是观察到乘法函数也没写


6.标题:三部排序

    一般的排序有许多经典算法,如快速排序、希尔排序等。

    但实际应用时,经常会或多或少有一些特殊的要求。我们没必要套用那些经典算法,可以根据实际情况建立更好的解法。

    比如,对一个整型数组中的数字进行分类排序:

    使得负数都靠左端,正数都靠右端,0在中部。注意问题的特点是:负数区域和正数区域内并不要求有序。可以利用这个特点通过1次线性扫描就结束战斗!!

    以下的程序实现了该目标。

    static void sort(int[] x)
    {
        int p = 0;
        int left = 0;
        int right = x.length-1;
        
        while(p<=right){
            if(x[p]<0){
                int t = x[left];
                x[left] = x[p];
                x[p] = t;
                left++;
                p++;
            }
            else if(x[p]>0){
                int t = x[right];
                x[right] = x[p];
                x[p] = t;
                right--;            
            }
            else{
                _________________________;  //代码填空位置
            }
        }
    }
   如果给定数组:
   25,18,-2,0,16,-5,33,21,0,19,-16,25,-3,0
   则排序后为:
   -3,-2,-16,-5,0,0,0,21,19,33,25,16,18,25
    


请分析代码逻辑,并推测划线处的代码,通过网页提交
注意:仅把缺少的代码作为答案,千万不要填写多余的代码、符号或说明文字!!

答案:p++,快排思想,可以了解下三路快排,检验答案的时候吧代码复制运行一下就好,样例可以自己弄,也可以用给的


7.标题:错误票据

    某涉密单位下发了某种票据,并要在年终全部收回。

    每张票据有唯一的ID号。全年所有票据的ID号是连续的,但ID的开始数码是随机选定的。

    因为工作人员疏忽,在录入ID号的时候发生了一处错误,造成了某个ID断号,另外一个ID重号。

    你的任务是通过编程,找出断号的ID和重号的ID。

    假设断号不可能发生在最大和最小号。

要求程序首先输入一个整数N(N<100)表示后面数据行数。
接着读入N行数据。
每行数据长度不等,是用空格分开的若干个(不大于100个)正整数(不大于100000)
每个整数代表一个ID号。

要求程序输出1行,含两个整数m n,用空格分隔。
其中,m表示断号ID,n表示重号ID

例如:
用户输入:
2
5 6 8 11 9 
10 12 9

则程序输出:
7 9


再例如:
用户输入:
6
164 178 108 109 180 155 141 159 104 182 179 118 137 184 115 124 125 129 168 196
172 189 127 107 112 192 103 131 133 169 158 
128 102 110 148 139 157 140 195 197
185 152 135 106 123 173 122 136 174 191 145 116 151 143 175 120 161 134 162 190
149 138 142 146 199 126 165 156 153 193 144 166 170 121 171 132 101 194 187 188
113 130 176 154 177 120 117 150 114 183 186 181 100 163 160 167 147 198 111 119

则程序输出:
105 120
   

资源约定:
峰值内存消耗(含虚拟机) < 64M
CPU消耗  < 2000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.6及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

  这题有点坑,排序后贪心,先删了重复的数,再从头开始比较缺失了哪个,顺序反过来处理很可能掉坑,1,2,2,4,输出可能就是 2 2 了,另外list.get(i)==list.get(i+1)不能这样判断,用equals(),属于类的数值判断了

import java.util.ArrayList;
import java.util.Collections;
import java.util.Scanner;
 
public class _07_错误票据1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        ArrayList list = new ArrayList<>();
        in.next();//n没什么用
        while(in.hasNext()) {
            int x = in.nextInt();
            if(x==-1)//仅仅方便自己检查,没用
                break;
            list.add(x);
        }
        int x=0,y=0;
        Collections.sort(list);
        for(int i=0;i             if(list.get(i).equals(list.get(i+1))) {
                y = list.get(i);
                list.remove(i);
                break;
            }
        }
        int start = list.get(0);
        for(int i:list) {
            if(start!=i) {
                System.out.println(start+" "+y);
                break;
            }else
                start++;
        }
        
    }
}
import java.util.ArrayList;
import java.util.Collections;
import java.util.Scanner;
 
public class _07_错误票据 {
  public static void main(String[] args) {
    Scanner sc = new Scanner(System.in);
    ArrayList list = new ArrayList();
    int N = sc.nextInt();
    sc.nextLine();//吃掉整数后面的换行符
    for (int i = 0; i < N; i++) {
 
      String line = sc.nextLine();
      String[] split = line.split(" ");
      for (int j = 0; j < split.length; j++) {
        list.add(Integer.parseInt(split[j]));
      }
    }
 
    // System.out.println(list.size());
    Collections.sort(list);
    int a = 0, b = 0;
    for (int i = 1; i < list.size(); i++) {
      if (list.get(i) - list.get(i - 1) == 2)
        a = list.get(i) - 1;
 
      if (list.get(i) - list.get(i - 1) == 0)//注意此处有坑,不能用==
        b = list.get(i);
    }
    System.out.println(a + " " + b);
  }
}

8.标题:幸运数

    幸运数是波兰数学家乌拉姆命名的。它采用与生成素数类似的“筛法”生成。

    首先从1开始写出自然数1,2,3,4,5,6,....
    
    1 就是第一个幸运数。
    我们从2这个数开始。把所有序号能被2整除的项删除,变为:

    1 _ 3 _ 5 _ 7 _ 9 ....

    把它们缩紧,重新记序,为:
    
    1 3 5 7 9 .... 。这时,3为第2个幸运数,然后把所有能被3整除的序号位置的数删去。注意,是序号位置,不是那个数本身能否被3整除!! 删除的应该是5,11, 17, ...

    此时7为第3个幸运数,然后再删去序号位置能被7整除的(19,39,...) 

    最后剩下的序列类似:

    1, 3, 7, 9, 13, 15, 21, 25, 31, 33, 37, 43, 49, 51, 63, 67, 69, 73, 75, 79, ...

本题要求:

输入两个正整数m n, 用空格分开 (m < n < 1000*1000)
程序输出 位于m和n之间的幸运数的个数(不包含m和n)。

例如:
用户输入:
1 20
程序输出:
5

例如:
用户输入:
30 69
程序输出:
8

资源约定:
峰值内存消耗(含虚拟机) < 64M
CPU消耗  < 2000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.6及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

蓝桥杯的数据很神奇,自己说的100W,可我自测的时候10W也有点勉强了,很暴力的模拟AC代码,个人认为它给的数据规模会比它说的会小,看了源样例最多到1W5,呵呵了,另外3个样例最多是300,也就是超级无敌的暴力都能拿75%的分

import java.util.Arrays;
import java.util.Scanner;
 
public class _08幸运数1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int m = in.nextInt();
        int n = in.nextInt();
        
        int[] a = new int[n+1];
        
        for(int i=1;i<=n;i++)
            a[i] = i;
        for(int i=1;i<=n;i++)
            if(i%2==0)
                a[i] = Integer.MAX_VALUE;
        Arrays.sort(a);
        int t = n;
        for(int i=2;i<=t;i++) {
            int k = a[i];
            if(k==Integer.MAX_VALUE)
                break;
            for(int j=k;j<=t;j+=k)
                a[j] = Integer.MAX_VALUE;
            Arrays.sort(a,1,t);
            for(int j=1;j<=t;j++)
                if(a[j]==Integer.MAX_VALUE) {
                    t = j;
                    break;
                }
        }
 
        int ans = 0;
        for(int i=1;i<=n;i++) {
            if(a[i]>m && a[i]                 ans++;
        }
        System.out.println(ans);
    }
 
}
 

9.标题:带分数

    100 可以表示为带分数的形式:100 = 3 + 69258 / 714

    还可以表示为:100 = 82 + 3546 / 197

    注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0)。

    类似这样的带分数,100 有 11 种表示法。

题目要求:
从标准输入读入一个正整数N (N<1000*1000)
程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数。
注意:不要求输出每个表示,只统计有多少表示法!


例如:
用户输入:
100
程序输出:
11

再例如:
用户输入:
105
程序输出:
6


资源约定:
峰值内存消耗(含虚拟机) < 64M
CPU消耗  < 3000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.6及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

  回溯,把分数变成乘法,避免浮点误差,注意边界,没事别搞什么小的优化,蓝桥的数据不大,不会卡你的

import java.util.Scanner;
 
public class _09带分数1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        x = in.nextInt();
        dfs(0);
        System.out.println(ans);
    }
    static int ans = 0,n = 9,x;
    static int A[] = new int[] {1,2,3,4,5,6,7,8,9};
    static void dfs(int m) {
        if(m>=9) {
            for(int i=1;i                 int a=0;
                for(int k=0;k                     a = 10*a + A[k];
                if(a>x)
                    break;
                for(int j=i+1;j                     int b=0,c=0;
                    for(int k=i;k                         b = 10*b + A[k];
                    for(int k=j;k                         c = 10*c + A[k];    
                    if((x-a)*c==b)
                        ans++;
                }
            }
            return;
        }
        
        for(int i=m;i             swap(i,m);
            dfs(m+1);
            swap(i,m);
        }
        
        
    }
    private static void swap(int i, int j) {
        int t = A[i];
        A[i] = A[j];
        A[j] = t;
    }
 
}
 


10.标题:连号区间数

    小明这些天一直在思考这样一个奇怪而有趣的问题:

    在1~N的某个全排列中有多少个连号区间呢?这里所说的连号区间的定义是:

    如果区间[L, R] 里的所有元素(即此排列的第L个到第R个元素)递增排序后能得到一个长度为R-L+1的“连续”数列,则称这个区间连号区间。

    当N很小的时候,小明可以很快地算出答案,但是当N变大的时候,问题就不是那么简单了,现在小明需要你的帮助。

输入格式:
第一行是一个正整数N (1 <= N <= 50000), 表示全排列的规模。
第二行是N个不同的数字Pi(1 <= Pi <= N), 表示这N个数字的某一全排列。

输出格式:
输出一个整数,表示不同连号区间的数目。

示例:
用户输入:
4
3 2 4 1

程序应输出:
7

用户输入:
5
3 4 2 5 1

程序应输出:
9

解释:
第一个用例中,有7个连号区间分别是:[1,1], [1,2], [1,3], [1,4], [2,2], [3,3], [4,4]
第二个用例中,有9个连号区间分别是:[1,1], [1,2], [1,3], [1,4], [1,5], [2,2], [3,3], [4,4], [5,5]


资源约定:
峰值内存消耗(含虚拟机) < 64M
CPU消耗  < 5000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.6及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

别开二维数组记录,5w数据会爆内存,不过实际在官网还是AC了,所以数据弱,最大给到3984而已,4000的数据规模,O(n^3)也能拿80%趴

import java.util.Scanner;
 
public class _10连号区间数1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int n = in.nextInt();
        int[] a = new int[n+1];
//        int[][] max = new int[n+1][n+1];
//        int[][] min = new int[n+1][n+1];
        for(int i=1;i<=n;i++)
            a[i] = in.nextInt();
        int ans=0;
        for(int i=1;i<=n;i++) {
            int max=-1,min=999999999;
            for(int j=i;j<=n;j++) {
                max = Math.max(max, a[j]);
                min = Math.min(min, a[j]);
                if(max-min<=j-i)
                    ans++;
            }
        }
 
        System.out.println(ans);
    }
 
}
小结:

01 世纪末的星期 枚举每个世纪末,判断是否星期天  Calendar
02 马虎的算式 枚举每个位上的数字,组合判断
03 振兴中华 找重复中的变化,找边界
**04 黄金连分数 1.识别问题等价于斐波那契的n项和n+1项的比值,2.n要多少才够,3.怎么处理很大的数和精度要求很高的浮点数
 
05 有理数类 面向对象+分数加法(通分与约分)
06 三部排序 快速排序(三指针区间法)变体;极限思维(考虑全部是0)
 
07 错误票据 输入比较特殊,排序,迭代(获取断号和重号),输出
08 幸运数 模拟筛选过程,枚举计数
09 带分数 1-9用递归做全排列,对每一个排列,都枚举+和/的位置,然后进行检查
10 连号区间数 枚举所有区间,检查这个区间里面的数排序后是否连号
  

文章知识点与官方知识档案匹配,可进一步学习相关知识
算法技能树蓝桥杯-简单第几天5290 人正在系统学习中

一叶之修
关注

49


9

107


专栏目录
蓝桥杯历年真题及答案整理
04-06
官网上的答案,C版答案,C++版答案,JAVA版答案都有,数据亲测有效。 之前有人说太贵了,实属冤枉,那个积分不是我自己设置的= =
蓝桥杯历年省赛JAVA-B组真题汇总及题目详解
hyx153183740的博客
 1万+
蓝桥杯历年省赛JAVA-B组真题汇总及题目详解 2013年第四届蓝桥杯省赛真题详解 第四届蓝桥杯JavaB组题目解析 2014年第五届蓝桥杯省赛真题详解 第五届蓝桥杯JavaB组题目解析 2015年第五届蓝桥杯省赛真题详解 第六届蓝桥杯JavaB组题目解析 2016年第五届蓝桥杯省赛真题详解 第七届蓝桥杯JavaB组题目解析 2017年第五届蓝桥杯省赛真题详解 第八届蓝桥杯JavaB组题目解析 2...
评论9


 


AntonioIXE
2022.02.25

第七题有个小问题:在读取每行数字然后用空格进行分割时,可能有多个空格连续的情况。需要改为:
String[] split = line.split("\\s+");
才能通过

_小花
2021.04.13

package 蓝桥杯第四届省赛JavaB组;
 
import java.util.Scanner;
 
public class t_09_带分数 {
    static int ans=0;
    static int vis[]=new int[10];
    static int a[] =new int[9];
    static int n;
 
    static void dfs(int num) {
        if(num==9) {
            if(check(a)) {
                    ans++;
                }
            return;
        }
        for (int i = 1; i <=9; i++) {
            if(vis[i]==0) {
                vis[i]=1;
                a[num]=i;
                dfs(num+1);
                a[num]=0;
                vis[i]=0;
            }
        }
    }
 
    
    private static boolean check(int[] arr) {
        for (int i =1; i <=7; i++) { //i表示元素的个数
            //获得第一个数字
            int num1=toInt(arr,0,i);
            if(num1>n) break;
            //获取第二个数的元素
            for (int j =1; j <=9-i-1; j++) { //j表示元素的个数
                int num2=toInt(arr,i,j);
                int num3=toInt(arr,i+j,9-i-j);
                if ((num1 + num2 / num3)==n&&num2%num3==0) {
                    return true;
                }
            }
        }
        return false;
    }
 
 
    /**
     * 
     * @param arr 数组
     * @param pos 起始地址
     * @param len 组合的位数
     * @return
     */
    static int toInt(int[] arr ,int pos,int len) {
        int ans=0;
        for (int i =pos; i             ans=ans*10+arr

_小花
2021.04.13

package 蓝桥杯第四届省赛JavaB组;
 
import java.util.ArrayList;
import java.util.Scanner;
 
public class t_08_幸运数 {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int m=sc.nextInt();
        int n=sc.nextInt();
        int lucky=2,index=0,lucky_count=0;//lucky取2,为了忽略1
        ArrayList list=new ArrayList();
        ArrayList list_r=new ArrayList();
        for(int i=1;i<=n;i++) {
            list.add(i);
        }
        
        while(lucky             for (int i =1; i                 if(i%lucky==0) {
                    list_r.add(list.get(i-1));
                }
            }
            index++;
            list.removeAll(list_r);
            if(index>=list.size()) {
                break;
            }
            lucky=list.get(index);
        }
        for(int i=1;i             if(list.get(i)m) {
                lucky_count++;
            }
        }
        System.out.println(lucky_count);
    }
}

1.标题:武功秘籍

    小明到X山洞探险,捡到一本有破损的武功秘籍(2000多页!当然是伪造的)。他注意到:书的第10页和第11页在同一张纸上,但第11页和第12页不在同一张纸上。

    小明只想练习该书的第81页到第92页的武功,又不想带着整本书。请问他至少要撕下多少张纸带走?

这是个整数,请通过浏览器提交该数字,不要填写任何多余的内容。

7,(80,81),(82,83),(84,85),(86,87),(88,89),(90,91),(91,92)

题目告诉你2000多页,10-11连在一起,说明没过对称轴,就好数了,如果告诉你10和2000一页呢?


2.标题:切面条

    一根高筋拉面,中间切一刀,可以得到2根面条。

    如果先对折1次,中间切一刀,可以得到3根面条。

    如果连续对折2次,中间切一刀,可以得到5根面条。

    那么,连续对折10次,中间切一刀,会得到多少面条呢?

答案是个整数,请通过浏览器提交答案。不要填写任何多余的内容。

1025,脑补了一下,二分有关,猜下公式2^n+1,再推下n=3的情况,就差不多了

3.标题:猜字母

    把abcd...s共19个字母组成的序列重复拼接106次,得到长度为2014的串。

    接下来删除第1个字母(即开头的字母a),以及第3个,第5个等所有奇数位置的字母。

    得到的新串再进行删除奇数位置字母的动作。如此下去,最后只剩下一个字母,请写出该字母。

答案是一个小写字母,请通过浏览器提交答案。不要填写任何多余的内容。

按照它说的做就好,不过我26个字母不会排,好在有ASCII码,答案:q

String会内存溢出,用StringBuilder,StringBuilder的好处就是修改多次有优势,百度下

public class 猜字母 {
 
    public static void main(String[] args) {
//abcdefghijklmnopqrs
        StringBuilder s = new StringBuilder("abcdefghijklmnopqrs");
        for(int i=1;i<=105;i++)
            s.append("abcdefghijklmnopqrs");
        
        while(s.length()>1) {
            System.out.println(s.length());
            StringBuilder s1 = new StringBuilder();
            for(int i=1;i                 s1.append(s.charAt(i));
            s = s1;
        }
        
        System.out.println(s);
        
    }
 
}
 replace()函数

/*
题目:猜字母
      把abcd...s共19个字母组成的序列重复拼接106次,得到长度为2014的串。
      接下来删除第1个字母(即开头的字母a),以及第3个,第5个等所有奇数位置的字母。
      得到的新串再进行删除奇数位置字母的动作。如此下去,最后只剩下一个字母,请写出该字母。
答案:q 
*/
    
#include
using namespace std;
 
int main(){
    string s="abcdefghijklmnopqrs";
    string ss;
    for(int i=0;i<106;i++){
        ss+=s;        //拼接106次 
    }
    while(ss.size()>1){        //判断循环结束 
        for(int i=0;i             ss.replace(i,1,"");        //replace()函数 的使用 
        }
    }
 
    cout<     return 0;
}
 
/*
知识点 
    replace()函数: 
    
    用str中的num个字符替换本字符串中的字符,从index开始 
    用str中的num2个字符(从index2开始)替换本字符串中的字符,从index1开始,最多num1个字符 
    用str中的num个字符(从index开始)替换本字符串中的字符 
    用str中的num2个字符(从index2开始)替换本字符串中的字符,从index1开始,num1个字符 
    用num2个ch字符替换本字符串中的字符,从index开始 
    用str中的字符替换本字符串中的字符,迭代器start和end指示范围 
    用str中的num个字符替换本字符串中的内容,迭代器start和end指示范围, 
    用num个ch字符替换本字符串中的内容,迭代器start和end指示范围. 
    
    例如,以下代码显示字符串"They say he carved it himself...find your soul-mate, Homer." 
        string s = "They say he carved it himself...from a BIGGER spoon";
        string s2 = "find your soul-mate, Homer.";
    
        s.replace( 32, s2.length(), s2 );
    
        cout << s << endl;
    
*/

4.标题:大衍数列

    中国古代文献中,曾记载过“大衍数列”, 主要用于解释中国传统文化中的太极衍生原理。

    它的前几项是:0、2、4、8、12、18、24、32、40、50 ...

    其规律是:对偶数项,是序号平方再除2,奇数项,是序号平方减1再除2。

    以下的代码打印出了大衍数列的前 100 项。

for(int i=1; i<100; i++)
{
    if(________________)  //填空
        System.out.println(i*i/2);
    else
        System.out.println((i*i-1)/2);
}
    请填写划线部分缺失的代码。通过浏览器提交答案。

注意:不要填写题面已有的内容,也不要填写任何说明、解释文字。

i%2==0


5.标题:圆周率

    数学发展历史上,圆周率的计算曾有许多有趣甚至是传奇的故事。其中许多方法都涉及无穷级数。

    图1.png中所示,就是一种用连分数的形式表示的圆周率求法。

    下面的程序实现了该求解方法。实际上数列的收敛对x的初始值 并不敏感。    

    结果打印出圆周率近似值(保留小数点后4位,并不一定与圆周率真值吻合)。

    double x = 111; 
    for(int n = 10000; n>=0; n--){
        int i = 2 * n + 1;
        x = 2 + (i*i / x);
    }
    
    System.out.println(String.format("%.4f", ______________));


    

4.0/(x-1)


6.标题:奇怪的分式

    上小学的时候,小明经常自己发明新算法。一次,老师出的题目是:

    1/4 乘以 8/5 

    小明居然把分子拼接在一起,分母拼接在一起,答案是:18/45 (参见图1.png)

    老师刚想批评他,转念一想,这个答案凑巧也对啊,真是见鬼!

    对于分子、分母都是 1~9 中的一位数的情况,还有哪些算式可以这样计算呢?

    请写出所有不同算式的个数(包括题中举例的)。

    显然,交换分子分母后,例如:4/1 乘以 5/8 是满足要求的,这算做不同的算式。

    但对于分子分母相同的情况,2/2 乘以 3/3 这样的类型太多了,不在计数之列!

注意:答案是个整数(考虑对称性,肯定是偶数)。请通过浏览器提交。不要书写多余的内容。

14,暴力4个for 打印验证 

public class _06奇怪的分式 {
 
    public static void main(String[] args) {
        // A/B x C/D = E/F   A*C*F = E*B*D
        int ans=0;
        for(int a=1;a<10;a++)
            for(int b=1;b<10;b++)
                for(int c=1;c<10;c++)
                    for(int d=1;d<10;d++) {
                        int e = 10*a+c;
                        int f = 10*b+d;
                        if(a==b || c==d)
                            continue;
 
                        if(a*c*f==e*b*d) {
                            ans++;
                            System.out.println(a+"/"+b+" x "+c+"/"+d+" = "+e+"/"+f+"  "+ans);
                        }
                        
                    }
        
    }
 
}
 


7.标题:扑克序列

    A A 2 2 3 3 4 4, 一共4对扑克牌。请你把它们排成一行。
    要求:两个A中间有1张牌,两个2之间有2张牌,两个3之间有3张牌,两个4之间有4张牌。

    请填写出所有符合要求的排列中,字典序最小的那个。

例如:22AA3344 比 A2A23344 字典序小。当然,它们都不是满足要求的答案。


请通过浏览器提交答案。“A”一定不要用小写字母a,也不要用“1”代替。字符间一定不要留空格。

2342A3A4,又是一道全排,因为A是比2大的那么把A看成5就好

public class _07扑克序列1 {
 
    public static void main(String[] args) {
        dfs(0);
    }
    
    static int[] a = new int[] {5,5,2,2,3,3,4,4};
    
    static void dfs(int m) {
        
        if(m>=8) {
            int A1=-1,A2=-1,B1=-1,B2=-1,C1=-1,C2=-1,D1=-1,D2=-1;
            for(int i=0;i<8;i++)
                if(a[i]==5) {
                    if(A1==-1) 
                        A1 = i;
                    else
                        A2 = i;
                }else if(a[i]==2) {
                    if(B1==-1) 
                        B1 = i;
                    else
                        B2 = i;                    
                }else if(a[i]==3) {
                    if(C1==-1) 
                        C1 = i;
                    else
                        C2 = i;                    
                }else if(a[i]==4) {
                    if(D1==-1) 
                        D1 = i;
                    else
                        D2 = i;                    
                }
            if(A2-A1!=2 || B2-A1!=3 || C2-C1!=4 || D2-D1!=5)
                return;
            for(int i=0;i<8;i++)
                if(a[i]==5)
                    System.out.print("A");
                else
                    System.out.print(a[i]);
            System.out.println();
            return;
        }
        
        for(int i=m;i<8;i++) {
            swap(i,m);
            dfs(m+1);
            swap(i,m);
        }    
        
    }
    
    static void swap(int i,int j) {
        int t = a[i];
        a[i] = a[j];
        a[j] = t;
    }
    
}
8.标题:分糖果

    有n个小朋友围坐成一圈。老师给每个小朋友随机发偶数个糖果,然后进行下面的游戏:

    每个小朋友都把自己的糖果分一半给左手边的孩子。

    一轮分糖后,拥有奇数颗糖的孩子由老师补给1个糖果,从而变成偶数。

    反复进行这个游戏,直到所有小朋友的糖果数都相同为止。

    你的任务是预测在已知的初始糖果情形下,老师一共需要补发多少个糖果。

【格式要求】

    程序首先读入一个整数N(2     接着是一行用空格分开的N个偶数(每个偶数不大于1000,不小于2)
    要求程序输出一个整数,表示老师需要补发的糖果数。

例如:输入
3
2 2 4
程序应该输出:
4

资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 1000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。


模拟,模拟每一轮操作

import java.util.Scanner;
 
public class _08分糖果 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int n = in.nextInt();
        int[] a = new int[n];
        int[] b = new int[n];
        int ans=0;
        for(int i=0;i             a[i] = in.nextInt();
        
        while(true) {
            boolean flag = true;
            
            for(int i=0;i                 b[i] = a[i]/2;
            
            for(int i=0;i                 a[i] = a[i]/2 + b[(i+1)%n];
                if(a[i]%2==1) {
                    ans++;
                    a[i]++;
                }
            }
            for(int i=1;i                 if(a[i]!=a[0]) {
                    flag = false;
                    break;
                }
            
            if(flag)
                break;
        }
        
        System.out.println(ans);
        
    }
 
}
 


9.标题:地宫取宝

    X 国王有一个地宫宝库。是 n x m 个格子的矩阵。每个格子放一件宝贝。每个宝贝贴着价值标签。

    地宫的入口在左上角,出口在右下角。

    小明被带到地宫的入口,国王要求他只能向右或向下行走。

    走过某个格子时,如果那个格子中的宝贝价值比小明手中任意宝贝价值都大,小明就可以拿起它(当然,也可以不拿)。

    当小明走到出口时,如果他手中的宝贝恰好是k件,则这些宝贝就可以送给小明。

    请你帮小明算一算,在给定的局面下,他有多少种不同的行动方案能获得这k件宝贝。

【数据格式】

    输入一行3个整数,用空格分开:n m k (1<=n,m<=50, 1<=k<=12)

    接下来有 n 行数据,每行有 m 个整数 Ci (0<=Ci<=12)代表这个格子上的宝物的价值

    要求输出一个整数,表示正好取k个宝贝的行动方案数。该数字可能很大,输出它对 1000000007 取模的结果。

例如,输入:
2 2 2
1 2
2 1
程序应该输出:
2

再例如,输入:
2 3 2
1 2 3
2 1 5
程序应该输出:
14

资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 2000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。
 

问题 1436: [蓝桥杯][2014年第五届真题]地宫取宝 

之前写过,不过隔的久,风格有点差别,记忆化搜索,这里是从出口到入口的递归,那个博客是入口开始的,初始化为-1的话,判断完后记得设为0,不然你的答案莫名的-1-1-1,用四维数组记忆

import java.util.Scanner;
 
public class _09地宫取宝1 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        n = in.nextInt();
        m = in.nextInt();
        k = in.nextInt();
        a = new int[n+5][m+5];
        int max=0;
        for(int i=0;i             for(int j=0;j                 a[i][j] = in.nextInt();
                max = Math.max(max, a[i][j]);
            }
        memo = new int[n+5][m+5][k+5][max+5];
        for(int i=0;i<=n;i++)
            for(int j=0;j<=m;j++)
                for(int x=0;x<=k;x++)
                    for(int y=0;y<=max+1;y++)
                        memo[i][j][x][y] = -1;
 
        System.out.println(f(n-1,m-1,k,max+1));
 
    }
    
    static int n,m,k;
    static int[][][][] memo;
    static int[][] a;
    
    static int f(int x,int y,int now,int max) {
        if(memo[x][y][now][max]!=-1)
            return memo[x][y][now][max];
        
        if(x==0 && y==0) {
            if(now==0)
                return 1;
            if(now==1 && max>a[x][y])
                return 1;
            return 0;
        }
 
        memo[x][y][now][max] = 0;
        
        if(now>0) {
            if(x>0) {
                memo[x][y][now][max] = (memo[x][y][now][max]+f(x-1,y,now,max))%1000000007;
                if(max>a[x][y])
                    memo[x][y][now][max] = (memo[x][y][now][max]+f(x-1,y,now-1,a[x][y]))%1000000007;
            }
            if(y>0) {
                memo[x][y][now][max] = (memo[x][y][now][max]+f(x,y-1,now,max))%1000000007;
                if(max>a[x][y])
                    memo[x][y][now][max] = (memo[x][y][now][max]+f(x,y-1,now-1,a[x][y]))%1000000007;
            }
        } else {
            if(x>0) 
                memo[x][y][now][max] = (memo[x][y][now][max]+f(x-1,y,now,max))%1000000007;
            if(y>0) 
                memo[x][y][now][max] = (memo[x][y][now][max]+f(x,y-1,now,max))%1000000007;
        }
        return memo[x][y][now][max]%1000000007;
    }
 
}
 


10.标题:矩阵翻硬币

    小明先把硬币摆成了一个 n 行 m 列的矩阵。

    随后,小明对每一个硬币分别进行一次 Q 操作。

    对第x行第y列的硬币进行 Q 操作的定义:将所有第 i*x 行,第 j*y 列的硬币进行翻转。

    其中i和j为任意使操作可行的正整数,行号和列号都是从1开始。

    当小明对所有硬币都进行了一次 Q 操作后,他发现了一个奇迹——所有硬币均为正面朝上。

    小明想知道最开始有多少枚硬币是反面朝上的。于是,他向他的好朋友小M寻求帮助。

    聪明的小M告诉小明,只需要对所有硬币再进行一次Q操作,即可恢复到最开始的状态。然而小明很懒,不愿意照做。于是小明希望你给出他更好的方法。帮他计算出答案。

【数据格式】
    输入数据包含一行,两个正整数 n m,含义见题目描述。
    输出一个正整数,表示最开始有多少枚硬币是反面朝上的。

【样例输入】
2 3

【样例输出】
1

【数据规模】
对于10%的数据,n、m <= 10^3;
对于20%的数据,n、m <= 10^7;
对于40%的数据,n、m <= 10^15;
对于10%的数据,n、m <= 10^1000(10的1000次方)。

资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 2000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

数学题,考点太多了

第x行第y列被翻动的总次数?
考虑第1行,第y列,y有多少真因子,就会被翻动多少次,而所有的y中,只有平方数的真因子个数为奇数(约数总是成对出现的)
考虑第1列,第x行,x有多少真因子,就会被翻动多少次,而所有的x中,只有平方数的真因子个数为奇数
x,y硬币被翻动的次数=x真因子个数*y真因子个数,只有奇数*奇数=奇数,所以,若要x,y为反面,必须x,y都是平方数
因此,反面硬币总数=m中的平方数的个数*n中平方数的个数
那么在m中有多少个平方数呢?答案是sqrt(m)向下取整个,如9内有三个平方数1,4,9;16里面有4个平方数1,4,9,16;25内有5个平方数
因此此题等价于求sqrt(m)*sqrt(n),那么怎么对一个很大的数开平方呢?
假设一个数的长度为length,其平方根的长度为length/2(偶数)或者length/2+1(奇数)
我们可以从高位不停地试探,每一个取平方后恰好不超过目标平方数的值
/*
标题:矩阵翻硬币
    小明先把硬币摆成了一个 n 行 m 列的矩阵。
    随后,小明对每一个硬币分别进行一次 Q 操作。
    对第x行第y列的硬币进行 Q 操作的定义:将所有第 i*x 行,第 j*y 列的硬币进行翻转。
    其中i和j为任意使操作可行的正整数,行号和列号都是从1开始。
    当小明对所有硬币都进行了一次 Q 操作后,他发现了一个奇迹——所有硬币均为正面朝上。
    小明想知道最开始有多少枚硬币是反面朝上的。于是,他向他的好朋友小M寻求帮助。
    聪明的小M告诉小明,只需要对所有硬币再进行一次Q操作,即可恢复到最开始的状态。然而小明很懒,不愿意照做。于是小明希望你给出他更好的方法。帮他计算出答案。
【数据格式】
    输入数据包含一行,两个正整数 n m,含义见题目描述。
    输出一个正整数,表示最开始有多少枚硬币是反面朝上的。
【样例输入】
2 3
【样例输出】
1
【数据规模】
对于10%的数据,n、m <= 10^3;
对于20%的数据,n、m <= 10^7;
对于40%的数据,n、m <= 10^15;
对于100%的数据,n、m <= 10^1000(10的1000次方)。
资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 2000ms
请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。
所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。
*/
 
import java.math.BigInteger;
import java.util.Arrays;
import java.util.Scanner;
 
//第x行第y列被翻动的总次数?
//考虑第1行,第y列,y有多少真因子,就会被翻动多少次,而所有的y中,只有平方数的真因子个数为奇数(约数总是成对出现的)
//考虑第1列,第x行,x有多少真因子,就会被翻动多少次,而所有的x中,只有平方数的真因子个数为奇数
//x,y硬币被翻动的次数=x真因子个数*y真因子个数,只有奇数*奇数=奇数,所以,若要x,y为反面,必须x,y都是平方数
//因此,反面硬币总数=m中的平方数的个数*n中平方数的个数
//那么在m中有多少个平方数呢?答案是sqrt(m)向下取整个,如9内有三个平方数1,4,9;16里面有4个平方数1,4,9,16;25内有5个平方数
//因此此题等价于求sqrt(m)*sqrt(n),那么怎么对一个很大的数开平方呢?
//假设一个数的长度为length,其平方根的长度为length/2(偶数)或者length/2+1(奇数)
//我们可以从高位不停地试探,每一个取平方后恰好不超过目标平方数的值
public class _10矩阵翻硬币 {
  public static void main(String[] args) {
    Scanner sc = new Scanner(System.in);
    String s1 = sc.next();
    String s2 = sc.next();
    System.out.println(sqrt(s1).multiply(sqrt(s2)));
  }
 
  private static BigInteger sqrt(String s) {
    int length = s.length();
    int len = 0;
    if (length % 2 == 0)
      len = length / 2;
    else
      len = length / 2 + 1;
    char[] sArr = new char[len];
    Arrays.fill(sArr, '0');
    BigInteger target = new BigInteger(s);
    for (int pos = 0; pos < len; pos++) {
      for (char c = '1'; c <= '9'; c++) {
        sArr[pos] = c;//在pos这个位置上试着填入1-9
        BigInteger pow = new BigInteger(String.valueOf(sArr)).pow(2);//平方
        if (pow.compareTo(target) == 1)//试探数的平方更大
        {
          sArr[pos] -= 1;
          break;
        }
      }
    }
    return new BigInteger(String.valueOf(sArr));
  }
}
 

小结:

01 武功秘籍 书的构造方式,思维题
02 切面条 发现规律,思维题
03 猜字母 数组中元素的挪动和挤压
04 大衍数列 考察奇偶数判断
05 圆周率 细心,极限思维
06 奇怪的分式 枚举abcd,分数运算,最大公约数
07 扑克排序 带重复元素的全排列
08 分糖果 模拟
**09 地宫取宝 搜索->记忆型递归,因为子问题重复求解
****10 矩阵翻硬币 数学;字符,字符串,BigInteger的互相转化

1.三角形面积

如图1所示。图中的所有小方格面积都是1。
那么,图中的三角形面积应该是多少呢?

请填写三角形的面积。不要填写任何多余内容或说明性文字。

思路:矩形减去3个三角形面积 8*8 - 0.5*8*4 - 0.5*4*6 - 0.5*8*2 答案:28


2.立方变自身

观察下面的现象,某个数字的立方,按位累加仍然等于自身。
1^3 = 1 
8^3  = 512    5+1+2=8
17^3 = 4913   4+9+1+3=17
...

请你计算包括1,8,17在内,符合这个性质的正整数一共有多少个?

请填写该数字,不要填写任何多余的内容或说明性的文字。
 

答案:6,暴力枚举1到10000,打印观察,发现最大的数只是到27,没必要再扩大枚举的范围了,6已是答案

public class _02立方变自身1 {
 
    public static void main(String[] args) {
        int ans = 0;
        for(int i=1;i<=10000;i++) {
            if(i==f(i*i*i)) {
                System.out.println(":"+i);
                ans++;
            }
        }
        
        System.out.println(ans);
    }
    
    static int f(int x) {
        int ans=0;
        while(x>0) {
            ans+=x%10;
            x/=10;
        }
        return ans;
    }
 
}
3.三羊献瑞

观察下面的加法算式:

      祥 瑞 生 辉
  +   三 羊 献 瑞
-------------------
   三 羊 生 瑞 气

(如果有对齐问题,可以参看【图1.jpg】)

其中,相同的汉字代表相同的数字,不同的汉字代表不同的数字。

请你填写“三羊献瑞”所代表的4位数字(答案唯一),不要填写任何多余内容。

这种0-9不同数字的枚举,直接暴力就好,不过感觉暴力也要写挺久的,也可以试下全排,答案:1085

public class _03三羊献瑞_ {
 
    public static void main(String[] args) {
        for(int x1=0;x1<10;x1++)
            for(int x2=0;x2<10;x2++) {
                if(x1==x2)
                    continue;
                for(int x3=0;x3<10;x3++) {
                    if(x3==x1 || x3==x2)
                        continue;
                    for(int x4=0;x4<10;x4++) {
                        if(x4==x1 || x4==x2 || x4==x3)
                            continue;
                        for(int x5=0;x5<10;x5++) {
                            if(x5==x1 || x5==x2 || x5==x3 || x5==x4)
                                continue;
                            for(int x6=0;x6<10;x6++) {
                                if(x6==x1 || x6==x2 || x6==x3 || x6==x4 || x6==x5)
                                    continue;
                                for(int x7=0;x7<10;x7++) {
                                    if(x7==x1 || x7==x2 || x7==x3 || x7==x4 || x7==x5 || x7==x6)
                                        continue;
                                    for(int x8=0;x8<10;x8++) {
                                        if(x8==x1 || x8==x2 || x8==x3 || x8==x4 || x8==x5 || x8==x6 || x8==x7)
                                            continue;
                                        if(x1==0 || x5==0)
                                            continue;
                                        int x = 1000*x1 + 100*x2 + 10*x3 + x4;
                                        int y = 1000*x5 + 100*x6 + 10*x7 + x2;
                                        int z = 10000*x5 + 1000*x6 + 100*x3 + 10*x2 + x8;
 
                                        if(x+y==z) {
                                            System.out.println(x+"+"+y+"=="+z);
                                            System.out.println(x1+" "+x2+" "+x3+" "+x4+" "+x5+" "+x6+" "+x7+" "+x8+" ");
                                        }
 
                                    }
                                }
                            }
                        }
                    }
                }
            }
 
    }
 
}
 全排的话直接截取前8个数就好,写起来比上面8个for要舒爽,不过直觉上感觉8个for稳一点org

public class _03三羊献瑞_全排 {
 
    public static void main(String[] args) {
        dfs(0);
    }
    
    static int[] a = new int [] {0,1,2,3,4,5,6,7,8,9};
    
    static void dfs(int m) {
        if(m>=10) {
            int x = 1000*a[0] + 100*a[1] + 10*a[2] + a[3];
            int y = 1000*a[4] + 100*a[5] + 10*a[6] + a[1];
            int z = 10000*a[4] + 1000*a[5] + 100*a[2] + 10*a[1] + a[7];
            if(a[0]==0 || a[4]==0)
                return;
            if(x+y==z)
                System.out.println(x+"+"+y+"=="+z);
            
            return;
        }
        
        for(int i=m;i<10;i++) {
            swap(i,m);
            dfs(m+1);
            swap(i,m);
        }
        
        
        
    }
 
    static void swap(int i,int j) {
        int t = a[i];
        a[i] = a[j];
        a[j] = t;
    }
    
}

4.循环节长度

两个整数做除法,有时会产生循环小数,其循环部分称为:循环节。
比如,11/13=6=>0.846153846153.....  其循环节为[846153] 共有6位。
下面的方法,可以求出循环节的长度。

请仔细阅读代码,并填写划线部分缺少的代码。

    public static int f(int n, int m)
    {
        n = n % m;    
        Vector v = new Vector();
        
        for(;;)
        {
            v.add(n);
            n *= 10;
            n = n % m;
            if(n==0) return 0;
            if(v.indexOf(n)>=0)  _________________________________ ;  //填空
        }
    }
注意,只能填写缺少的部分,不要重复抄写已有代码。不要填写任何多余的文字。

return v.size() - v.indexOf(n);差点没看到v.add(),这里直接填v.size()是不对的比如7/18 0.3888888  但他会输出2,而应该是1,所以要减去第一个重复字母的下标


5.九数组分数

1,2,3...9 这九个数字组成一个分数,其值恰好为1/3,如何组法?

下面的程序实现了该功能,请填写划线部分缺失的代码。

public class A
{
    public static void test(int[] x)
    {
        int a = x[0]*1000 + x[1]*100 + x[2]*10 + x[3];
        int b = x[4]*10000 + x[5]*1000 + x[6]*100 + x[7]*10 + x[8];        
        if(a*3==b) System.out.println(a + " " + b);
    }
    
    public static void f(int[] x, int k)
    {
        if(k>=x.length){
            test(x);
            return;
        }
        
        for(int i=k; i             {int t=x[k]; x[k]=x[i]; x[i]=t;}
            f(x,k+1);
            _______________________________________       // 填空
        }
    }
    
    public static void main(String[] args)
    {
        int[] x = {1,2,3,4,5,6,7,8,9};        
        f(x,0);
    }
}
注意,只能填写缺少的部分,不要重复抄写已有代码。不要填写任何多余的文字。

答案:{int t=x[k]; x[k]=x[i]; x[i]=t;},全排,回溯


6.加法变乘法

我们都知道:1+2+3+ ... + 49 = 1225
现在要求你把其中两个不相邻的加号变成乘号,使得结果为2015

比如:
1+2+3+...+10*11+12+...+27*28+29+...+49 = 2015
就是符合要求的答案。

请你寻找另外一个可能的答案,并把位置靠前的那个乘号左边的数字提交(对于示例,就是提交10)。

注意:需要你提交的是一个整数,不要填写任何多余的内容。

答案:16,看错题目了,还想用下前缀和,这里模拟,先减去这4个改变的数,再加入2个乘积的结果

public class _06__加法变乘法 {
 
    public static void main(String[] args) {
        int[] sum = new int[50];
        for(int i=1;i<=49;i++)
            sum[i]=sum[i-1]+i;
        
        for(int i=1;i<49;i++)
            for(int j=i+1;j<49;j++) {//i+2是最符合题意的,不相邻嘛,不过没关系打印观察
                int ans = 1225;
                ans = ans -(i+i+1);
                ans = ans -(j+j+1);
                ans = ans + i*(i+1)+j*(j+1);
                if(ans==2015)
                    System.out.println(i+" "+j);
            }
 
        
    }
 
}

7.牌型种数

小明被劫持到X赌城,被迫与其他3人玩牌。
一副扑克牌(去掉大小王牌,共52张),均匀发给4个人,每个人13张。
这时,小明脑子里突然冒出一个问题:
如果不考虑花色,只考虑点数,也不考虑自己得到的牌的先后顺序,自己手里能拿到的初始牌型组合一共有多少种呢?

请填写该整数,不要填写任何多余的内容或说明文字。
答案:3598180
考点递归,其实前面一直下来都没考到dp和递归,从这角度想,应该会用到了把,不过我是暴力模拟到开头就发现可以递归了org,这里呢,每种纸牌有5种取法,有13种纸牌,可以选择取1个,取2个,取3个,取4个,取0个,注意不取的情况一定不能漏qaq,第一次漏了,粗心鸭= =,所以考试记得回头检查

    static int f(int n,int m) {
        if(n==0)
            return m==0?1:0;
        if(m==0)//这个属于剪枝把,填空题没有也没事
            return 1;
        if(m<0)//边界判断
            return 0;
        
        return f(n-1,m) + f(n-1,m-1) + f(n-1,m-2) +f(n-1,m-3)+f(n-1,m-4);
    }
网上的暴力枚举代码也是挺可爱的,可以学习下,重点是稳hhha,我们不差时间哈~ 

#include
using namespace std;
int main()
{
    int sum=0;
    for(int a=0; a<=4; a++)
        for(int b=0; b<=4; b++)
            for(int c=0; c<=4; c++)
                for(int d=0; d<=4; d++)
                    for(int e=0; e<=4; e++)
                        for(int f=0; f<=4; f++)
                            for(int g=0; g<=4; g++)
                                for(int h=0; h<=4; h++)
                                    for(int i=0; i<=4; i++)
                                        for(int j=0; j<=4; j++)
                                            for(int k=0; k<=4; k++)
                                                for(int l=0; l<=4; l++)
                                                    for(int m=0; m<=4; m++)
                                                    {
                                                        if(a+b+c+d+e+f+g+h+i+j+k+l+m==13)
                                                            sum++;
                                                    }
                                                    cout<     return 0;
}

8.饮料换购

乐羊羊饮料厂正在举办一次促销优惠活动。乐羊羊C型饮料,凭3个瓶盖可以再换一瓶C型饮料,并且可以一直循环下去,但不允许赊账。

请你计算一下,如果小明不浪费瓶盖,尽量地参加活动,那么,对于他初始买入的n瓶饮料,最后他一共能得到多少瓶饮料。

输入:一个整数n,表示开始购买的饮料数量(0 输出:一个整数,表示实际得到的饮料数

例如:
用户输入:
100
程序应该输出:
149

用户输入:
101
程序应该输出:
151


资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 1000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。
 

问题 1072: 汽水瓶之前做到过一题,比这题难一点的,区别是这题可以先借给你一瓶汽水,意思是最后2个瓶盖也可以换一瓶,

这2题的做法都是递归+直接模拟= =

import java.util.Scanner;
 
public class _08饮料换购_ {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int n = in.nextInt();
        System.out.println(n+f(n));
    }
    
    static int f(int n) {
        if(n<3)
            return 0;
        
        return n/3+f(n%3+n/3);
    }
    
    
 
}
注意下面代码是相似题的,并不是饮料换购,原题链接:问题 1072: 汽水瓶

/**
 * http://www.dotcpp.com/oj/problem1072.html
 * @author 叶
 *
 */
//有这样一道智力题:“某商店规定:三个空汽水瓶可以换一瓶汽水。小张手上有十个空汽水瓶,
//她最多可以换多少瓶汽水喝?”答案是5瓶,方法如下:先用9个空瓶子换3瓶汽水,喝掉3瓶满的,
//喝完以后4个空瓶子,用3个再换一瓶,喝掉这瓶满的,这时候剩2个空瓶子。然后你让老板先借给你一瓶汽水
//,喝掉这瓶满的,喝完以后用3个空瓶子换一瓶满的还给老板。
//如果小张手上有n个空汽水瓶,最多可以换多少瓶汽水喝?
 
import java.util.Scanner;
public class 汽水瓶 {
 
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        for(int i=0;i<10;i++)
        {
            int x = in.nextInt();
            if(x!=0)
                System.out.println(f(x));
            else
                break;
        }
    }
    
    static int f(int x)
    {
        if(x<2)
            return 0;
        return 1+f(x-2);
    }
 
}
 

9.垒骰子

赌圣atm晚年迷恋上了垒骰子,就是把骰子一个垒在另一个上边,不能歪歪扭扭,要垒成方柱体。
经过长期观察,atm 发现了稳定骰子的奥秘:有些数字的面贴着会互相排斥!
我们先来规范一下骰子:1 的对面是 4,2 的对面是 5,3 的对面是 6。
假设有 m 组互斥现象,每组中的那两个数字的面紧贴在一起,骰子就不能稳定的垒起来。 atm想计算一下有多少种不同的可能的垒骰子方式。
两种垒骰子方式相同,当且仅当这两种方式中对应高度的骰子的对应数字的朝向都相同。
由于方案数可能过多,请输出模 10^9 + 7 的结果。

不要小看了 atm 的骰子数量哦~

「输入格式」
第一行两个整数 n m
n表示骰子数目
接下来 m 行,每行两个整数 a b ,表示 a 和 b 不能紧贴在一起。

「输出格式」
一行一个数,表示答案模 10^9 + 7 的结果。

「样例输入」
2 1
1 2

「样例输出」
544

「数据范围」
对于 30% 的数据:n <= 5
对于 60% 的数据:n <= 100
对于 100% 的数据:0 < n <= 10^9, m <= 36


资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 2000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

前面的题目都比较水,到了第九题,突然难度上去了,不过这题60%的数据还是很小的,可以试试拼一波暴力,30%的数据就更离谱了,n<=5,读懂题应该就能拿下了,考点:dp+快速幂+矩阵快速幂

import java.util.Scanner;
 
/*
垒骰子
赌圣atm晚年迷恋上了垒骰子,就是把骰子一个垒在另一个上边,不能歪歪扭扭,要垒成方柱体。
经过长期观察,atm 发现了稳定骰子的奥秘:有些数字的面贴着会互相排斥!
我们先来规范一下骰子:1 的对面是 4,2 的对面是 5,3 的对面是 6。
假设有 m 组互斥现象,每组中的那两个数字的面紧贴在一起,骰子就不能稳定的垒起来。 atm想计算一下有多少种不同的可能的垒骰子方式。
两种垒骰子方式相同,当且仅当这两种方式中对应高度的骰子的对应数字的朝向都相同。
由于方案数可能过多,请输出模 10^9 + 7 的结果。
不要小看了 atm 的骰子数量哦~
「输入格式」
第一行两个整数 n m
n表示骰子数目
接下来 m 行,每行两个整数 a b ,表示 a 和 b 不能紧贴在一起。
「输出格式」
一行一个数,表示答案模 10^9 + 7 的结果。
「样例输入」
2 1
1 2
「样例输出」
544
「数据范围」
对于 30% 的数据:n <= 5
对于 60% 的数据:n <= 100
对于 100% 的数据:0 < n <= 10^9, m <= 36
资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 2000ms
请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。
所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。
*/
public class _09_垒骰子 {
  static int op[] = new int[7];
  private static int n;
  private static int m;
  private static final long MOD = 1000000007;
 
  static void init() {
    op[1] = 4;
    op[4] = 1;
    op[2] = 5;
    op[5] = 2;
    op[3] = 6;
    op[6] = 3;
  }
 
  public static void main(String[] args) {
    init();
    Scanner sc = new Scanner(System.in);
    n = sc.nextInt();
    m = sc.nextInt();
    long conflict[][] = new long[6][6];
    for (int i = 0; i < 6; i++) {
      for (int j = 0; j < 6; j++) {
        conflict[i][j]=1;
      }
    }
    //建立冲突矩阵
    for (int i = 0; i < m; i++) {
      int a = sc.nextInt();
      int b = sc.nextInt();
      conflict[op[a] - 1][b - 1] = 0;
      conflict[op[b] - 1][a - 1] = 0;
    }
    //  求冲突矩阵的n-1次方
    long[][] mPow_n_1 = mPow(conflict, n - 1);
    //累加矩阵的每个元素
    long ans = 0;
    for (int i = 0; i < 6; i++) {
      for (int j = 0; j < 6; j++) {
        ans = (ans + mPow_n_1[i][j]) % MOD;
      }
    }
    //ans*4^n
    System.out.println(ans * power(4, n) % MOD);
  }
 
  private static long power(long i, int n) {
    long ans = 1;
    while (n != 0) {
      if ((n & 1) == 1) ans = (ans * i) % MOD;
      i = i * i % MOD;
      n >>= 1;
    }
    return ans;
  }
 
  /*矩阵的快速幂*/
  private static long[][] mPow(long[][] conflict, int n) {
    long[][] e = new long[6][6];
    for (int i = 0; i < 6; i++) {
      for (int j = 0; j < 6; j++) {
        if (i == j) e[i][j] = 1;
        else e[i][j] = 0;
      }
    }
    while (n != 0) {
      if ((n & 1) == 1) {
        e = mMul(e, conflict);
      }
      conflict = mMul(conflict, conflict);
      n >>= 1;
    }
 
    return e;
  }
 
  private static long[][] mMul(long[][] a, long[][] b) {
    long[][] ans = new long[6][6];
    for (int i = 0; i < 6; i++) {
      for (int j = 0; j < 6; j++) {
        for (int k = 0; k < 6; k++) {
          ans[i][j] = (ans[i][j] + a[i][k] * b[k][j]) % MOD;
        }
      }
    }
    return ans;
  }
}

10.生命之树

在X森林里,上帝创建了生命之树。

他给每棵树的每个节点(叶子也称为一个节点)上,都标了一个整数,代表这个点的和谐值。
上帝要在这棵树内选出一个非空节点集S,使得对于S中的任意两个点a,b,都存在一个点列 {a, v1, v2, ..., vk, b} 使得这个点列中的每个点都是S里面的元素,且序列中相邻两个点间有一条边相连。

在这个前提下,上帝要使得S中的点所对应的整数的和尽量大。
这个最大的和就是上帝给生命之树的评分。

经过atm的努力,他已经知道了上帝给每棵树上每个节点上的整数。但是由于 atm 不擅长计算,他不知道怎样有效的求评分。他需要你为他写一个程序来计算一棵树的分数。

「输入格式」
第一行一个整数 n 表示这棵树有 n 个节点。
第二行 n 个整数,依次表示每个节点的评分。
接下来 n-1 行,每行 2 个整数 u, v,表示存在一条 u 到 v 的边。由于这是一棵树,所以是不存在环的。

「输出格式」
输出一行一个数,表示上帝给这棵树的分数。

「样例输入」
5
1 -2 -3 4 5
4 2
3 1
1 2
2 5

「样例输出」
8

「数据范围」
对于 30% 的数据,n <= 10
对于 100% 的数据,0 < n <= 10^5, 每个节点的评分的绝对值不超过 10^6 。

资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 3000ms


请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。

所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。

这题正解是树状dp,无根树转有根树,思维难度很大,但是30%数据是10以内的,搜索应该能拿下,原则尽量拿更多的分0.0,暴力解的话,可以枚举所有的子集,再判断所有的子集中是否符合联通,这里的判断可以用dfs搜索或者并查集拿下30%

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
 
/*
生命之树
在X森林里,上帝创建了生命之树。
他给每棵树的每个节点(叶子也称为一个节点)上,都标了一个整数,代表这个点的和谐值。
上帝要在这棵树内选出一个非空节点集S,使得对于S中的任意两个点a,b,都存在一个点列 {a, v1, v2, ..., vk, b} 使得这个点列中的每个点都是S里面的元素,且序列中相邻两个点间有一条边相连。
在这个前提下,上帝要使得S中的点所对应的整数的和尽量大。
这个最大的和就是上帝给生命之树的评分。
经过atm的努力,他已经知道了上帝给每棵树上每个节点上的整数。但是由于 atm 不擅长计算,他不知道怎样有效的求评分。他需要你为他写一个程序来计算一棵树的分数。
「输入格式」
第一行一个整数 n 表示这棵树有 n 个节点。
第二行 n 个整数,依次表示每个节点的评分。
接下来 n-1 行,每行 2 个整数 u, v,表示存在一条 u 到 v 的边。由于这是一棵树,所以是不存在环的。
「输出格式」
输出一行一个数,表示上帝给这棵树的分数。
「样例输入」
5
1 -2 -3 4 5
4 2
3 1
1 2
2 5
「样例输出」
8
「数据范围」
对于 30% 的数据,n <= 10
对于 100% 的数据,0 < n <= 10^5, 每个节点的评分的绝对值不超过 10^6 。
资源约定:
峰值内存消耗(含虚拟机) < 256M
CPU消耗  < 3000ms
请严格按要求输出,不要画蛇添足地打印类似:“请您输入...” 的多余内容。
所有代码放在同一个源文件中,调试通过后,拷贝提交该源码。
注意:不要使用package语句。不要使用jdk1.7及以上版本的特性。
注意:主类的名字必须是:Main,否则按无效代码处理。
*/
public class _10生命之树 {
 
  private static int n;
  private static long[] w;
  private static List[] g;
  private static long ans ;
 
  public static void main(String[] args) throws FileNotFoundException {
    System.setIn(new FileInputStream(new File("/Users/zhengwei/workspace/lanqiaobei2019/src/2015_Java_B/data10/in5.txt")));
    Scanner sc = new Scanner(System.in);
    n = sc.nextInt();
    w = new long[n + 1];
    g = new ArrayList[n + 1];
    initG();
    for (int i = 1; i <= n; i++) {
      w[i] = sc.nextLong();
    }
    for (int i = 0; i < n - 1; i++) {
      int a = sc.nextInt();
      int b = sc.nextInt();
      g[a].add(b);
      g[b].add(a);
    }
    dfs(1, 0);
    System.out.println(ans);
  }
 
  /**
   * u做为根所代表的子树有一个最大权和,将其存储在w[u]中
   * @param u
   * @param fa
   */
  private static void dfs(int u, int fa) {
    for (int i = 0; i < g[u].size(); i++) {
      Integer child = g[u].get(i);
      if (child == fa) continue;
      dfs(child, u);
      if (w[child] > 0)
        w[u] += w[child];
    }
    if (w[u] > ans) ans = w[u];
  }
 
  private static void initG() {
    for (int i = 0; i < n + 1; i++) {
      g[i] = new ArrayList();
    }
 
  }
}
 

小结:

01 三角形面积 热身 不用编程
02 立方变自身 简单枚举
03 三羊献瑞 简单枚举 小技巧
*04 循环节长度 有坑 逻辑
05 九数组分数 全排列 带分数
06 加法变乘法 简单枚举 小技巧
07 牌型种数 递归
08 饮料换购 模拟
****09 垒骰子 递归-动规-矩阵快速幂
*****10 生命之树 Java中递归最多1万层
 

文章知识点与官方知识档案匹配,可进一步学习相关知识
算法技能树蓝桥杯-简单第几天5290 人正在系统学习中

一叶之修
关注

14


3

16


专栏目录
2015年蓝桥杯省赛B组C/C++(试题+答案分析)
weixin_44683914的博客
 1206
2015年蓝桥杯省赛B组C/C++(试题+答案分析) 第一题 结果填空 (3分) 奖券数目 有些人很迷信数字,比如带“4”的数字,认为和“死”谐音,就觉得不吉利。 虽然这些说法纯属无稽之谈,但有时还要迎合大众的需求。某抽奖活动的奖券号码是5位数(10000-99999),要求其中不要出现带“4”的号码,主办单位请你计算一下,如果任何两张奖券不重号,最多可发出奖券多少张。 请提交该数字(一个整数),...
蓝桥杯真题 15省Ca8-饮料 乐羊羊饮料厂正在举办一次促销优惠活动。乐羊羊C型饮料,凭3个瓶盖可以再换一瓶C型饮料,并且可以一直循环下去(但不允许暂借或赊账)。 请你计算一下,如果小明不浪费瓶盖,
qq_45281807的博客
 1121
问题描述 乐羊羊饮料厂正在举办一次促销优惠活动。乐羊羊C型饮料,凭3个瓶盖可以再换一瓶C型饮料,并且可以一直循环下去(但不允许暂借或赊账)。 请你计算一下,如果小明不浪费瓶盖,尽量地参加活动,那么,对于他初始买入的n瓶饮料,最后他一共能喝到多少瓶饮料。 输入 一个整数n,表示开始购买的饮料数量(0 评论3


 


心里没有一点AC数
2022.02.28

1
牌型种数那道题可以看成多重背包问题,
//物品是1-13
//物品个数是4
//物品体积是1
//背包容量是13
//f[i][j]:前i个物品的体积恰好是j的选法

_小花
2021.04.13

package 蓝桥杯第六届JavaB组真题;
 
import java.util.Scanner;
 
public class t08_饮料换购 {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int n=sc.nextInt();
        int ans=0;
        while(n>2) {
            ans+=3;
            n-=2;
        }
        ans=ans+n;
        System.out.println(ans);
    }
 
}
 

你可能感兴趣的:(c++,c语言,python)