美文网首页
挑战程序设计竞赛_抽签问题及优化

挑战程序设计竞赛_抽签问题及优化

作者: 掌灬纹 | 来源:发表于2019-03-16 14:49 被阅读0次

问题描述及思路概述:

* 将n个纸片放入口袋中,每张纸片上写一个数

* 每次从中抽取一个,记录并且放回,抽取四次

* 问和能否为m

* 若能输出Yes,否则输出No

* 样例输入:

* n = 3

* m = 10

* k = {1, 3, 5};

* 输出:

* Yes(1+1+3+5)

* 思路:

* 1.暴力枚举,四重循环,枚举所有情况 O(n^4)

* 2.优化最后一次的查询,前三重循环枚举前三次所有抽取的情况

* 最后用二分查找bin(m-A[n] + B[n] + C[n],D) O(n^3*lgn)

* 3.基于第二种方法考虑,枚举前两次抽签的情况,记录sum[n*n];在用两重循环二分查找

* bin(m-(C[n] + D[n]),sum) O(n^2*lgn)

java代码实现如下

import java.util.Arrays;

import java.util.Scanner;

public class 抽签问题及优化 {

static int n;

public static void main(String[] args) {

Scanner sc = new Scanner(System.in);

n = sc.nextInt();//n张纸片

int m = sc.nextInt();//所求和

int[] k = new int[n];//模拟每张纸片所代表的数

for(int i = 0; i < n; i++) {

k[i] = sc.nextInt();

}

//solve1(k, m, n);

//solve2(k, m, n);

solve(k, m, n);

}

/**

* 四个数分隔成两两一对,枚举前两次抽取结果,二分查找

* @param k

* @param m

* @param n2

*/

private static void solve(int[] k, int m, int n) {

boolean ans = false;

int[] towSum = new int[n*n];

for(int i = 0; i < n; i++) {

for(int j = 0; j < n; j++) {

towSum[n*i+j] = k[i] + k[j];//记录

}

}

//二分查找

Arrays.sort(towSum);

for(int i = 0; i < n; i++) {

for(int j = 0; j < n; j++) {

if(Arrays.binarySearch(towSum, m - k[i] - k[j]) >= 0)

ans = true;

}

}

if(ans)

System.out.println("Yes");

else

System.out.println("No");

}

/**

* 枚举前三次抽取结果+二分查找

* @param k

* @param m

* @param n

*/

private static void solve2(int[] k, int m, int n) {

boolean ans = false;

Arrays.sort(k);

for(int i = 0; i < n; i++) {

for(int j = 0; j < n; j++) {

for(int l = 0; l < n; l++) {

if(Arrays.binarySearch(k, m - k[i] - k[j] - k[l]) >= 0)

ans = true;

}

}

}

if(ans)

System.out.println("Yes");

else

System.out.println("No");

}

/**

* 暴力枚举

* @param k

* @param m

* @param n

*/

private static void solve1(int[] k, int m, int n) {

boolean ans = false;

for(int i = 0; i < n; i++) {

for(int j = 0; j < n; j++) {

for(int r = 0; r < n; r++) {

for(int l = 0; l < n; l++) {

if(k[i]+k[j]+k[r]+k[l] == m)

ans = true;

}

}

}

}

if(ans)

System.out.println("Yes");

else

System.out.println("No");

}

}

相关文章

  • 挑战程序设计竞赛_抽签问题及优化

    问题描述及思路概述: * 将n个纸片放入口袋中,每张纸片上写一个数 * 每次从中抽取一个,记录并且放回,抽取四次 ...

  • 《挑战程序设计竞赛》学习笔记(18.07.30-)

    《挑战程序设计竞赛》全书共116个问题,不求速度,只求质量,认认真真地学❤ 18.07.30 000.抽签你的朋友...

  • 面试高级算法梳理笔记

    归去来兮。 1.1 说明 本篇为《挑战程序设计竞赛(第2版)》读书笔记系列,旨在: 梳理算法逻辑 探索优化思路 深...

  • 用快速幂运算求斐波那契,时间复杂度降到O(logn)

    思路来自《挑战程序设计竞赛》 可运行的C++代码如下

  • 简介

    这是关于《挑战程序设计竞赛(第2版)》的刷题记录。因为POJ评测快,全英文,评测结果反馈与ICPC竞赛相同,所以选...

  • 挑战程序设计竞赛11.7

    今天读的挑战程序设计竞赛的图的最短路问题,只看了一个dijkstra算法,但没怎么看明白。 又把昨天的bellma...

  • 挑战程序设计竞赛11.4

    /* 今天读了一种叫做并查集的数据结构,以前做题做到了,但一些解题报告质量参差不齐, 自己只是理解个大概了,不知道...

  • 挑战程序设计竞赛11.2

    今天读了如何实现优先队列,及如何运用。可以用数组来表示二叉树,节点是从上到下从左到右的顺序紧凑排列,它最重要的性质...

  • 挑战程序设计竞赛11.3

    今天读了二叉搜索树的实现以及set和map的简单用法。 二叉搜索树实际上就是一颗二叉树,但它有一个特点,就是每个节...

  • 挑战程序设计竞赛11.11

    今天在高铁上读了一点,只看了辗转相除法。 int gcd(int a,int b){ if(b==0) retur...

网友评论

      本文标题:挑战程序设计竞赛_抽签问题及优化

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