蓝桥杯第1593题——二进制问题

题目描述

小蓝最近在学习二进制。他想知道 1 到 N 中有多少个数满足其二进制表示中恰好有 K 个 1。你能帮助他吗?

输入描述

输入一行包含两个整数 N 和 K。

输出描述

输出一个整数表示答案。

输入输出样例

示例

输入

7 2

输出

3

评测用例规模与约定

对于 30% 的评测用例,1 ≤ N ≤ 10^6,1 ≤ K ≤ 10。

对于 60% 的评测用例,1 ≤ N ≤ 2×10^9,1 ≤ K ≤ 30。

对于所有评测用例,1 ≤ N ≤ 10^18,1 ≤ K ≤ 50。

解题思路

这道题大致的问题就是给定一排位置,填或者不填的问题,我们可以考虑使用数位dp的思想。

对于n个位置填k个1的方案数量是典型的排列组合,虽然K的值最高只有50,计算排列组合C_{m}^{n}也是可以实现的,但这里我们综合考虑使用帕斯卡公式,即C_{n}^{m} = C_{n-1}^{m} + C_{n-1}^{m-1}

于是我们可以定义dp[i][j]:在长度为 i 的二进制序列中填 j 个 1 的组合数。

帕斯卡公式的证明就是这道题的原理,即n个数中取m个元素的组合数——包含第一个数不取,在剩下的n-1个数中取m个数;和第一个数取,在剩下n-1个数中取m-1个数的总和。

题目要求统计包含K个1的二进制数的数量,以N的二进制为1011,取k=3为例,我们可以将1011分解为以下几个区间考虑:0000~0111、1000~1001、1010~1010、1011。

这样分的理由是,第一个数不填1,考虑剩下3个位置填3个1的方法总数,这不就正好是在000~111这个长度为3的二进制序列中填3个1的排列总数吗,即dp[3][3]。

那么比111更大的数即代表着第一个数一定填1,在第二个区间中,我们是在第一个数填1的情况下,考虑第三个数不填1的排列数,即剩下1个位置填2个1满足要求——dp[1][2]。

第三个区间考虑在第一个位置和第三个位置都填1的情况下,第四个位置不填1的情况,那么就要加上在剩下0个位置填1个1的组合数——dp[0][1]。

最后还剩一个单独的1011,其目的是要留着特判,因为我们前面一直都是在遇到1的情况下考虑这个位置不填1有多少种满足要求的可能性,那么我们就会漏掉最后一个位置填1的情况没有计算,在最后一个位置填1,并且刚好满足k个1的时候,就需要增加一种组合数。

根据上述逻辑,此数据的答案即为:dp[3][3] + dp[1][2] + dp[0][1] + 1  =  1 + 0 + 0 + 1  =  2种

import java.util.*;
import java.io.*;

public class Main {
    static long n;
    static int k;
    static long[][] dp;
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        n = sc.nextLong();
        k = sc.nextInt();
        init();
        System.out.println(solve(n));
    }
    public static long solve(long n) {
        char[] s = Long.toBinaryString(n).toCharArray();
        long ans = 0;
        // ones 用于记录已经填的1的数量
        int ones = 0;
        for (int i = 0; i < s.length; i++) {
            int po = s.length - i;
            if (s[i] == '1') {
                // 先考虑位置po不填1的可能性
                ans += dp[po - 1][k - ones];
                // 然后填上一个1并记录
                ones++;
                // 由于在ones等于k的时候还有一次后续什么都不填的可能性,即dp[xxx][0] = 1
                // 所以只在填超了以后才break
                if (ones > k) {
                    break;
                }
            }
            // 如果最后一位刚好填够k个1,会漏计算1种情况,需要补上
            if (po == 1 && ones == k) {
                ans++;
            }
        }
        return ans;
    }
    public static void init() {
        dp = new long[65][65];
        dp[0][0] = 1;
        for (int i = 1; i < 65; i++) {
            for (int j = 0; j <= i; j++) {
                if (j == 0) {
                    dp[i][j] = 1;
                } else {
                    dp[i][j] = dp[i - 1][j] + dp[i - 1][j - 1];
                }
            }
        }
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/507956.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

软件测试工作中需要的Linux知识,一篇文章就够了

01、Linux基础 1、Linux系统简单介绍 Linux是一套免费使用, 支持多用户、多任务、支持多线程和多个核心CPU的操作系统&#xff1b;很多中型, 大型甚至是巨型项目都在使用Linux。 Linux的发行版说简单点就是将Linux与应用软件做一个打包, 目前市面上比较知名的发行版有: Ubun…

Free RTOS day2

1.思维导图 2.使用PWMADC光敏电阻完成光控灯的实验 int adc_val0;//用于保存ADC采样得到的数值 float volt0;//用于保存电压值 int main(void) {MX_GPIO_Init();MX_DMA_Init();MX_TIM1_Init();MX_USART1_UART_Init();MX_ADC_Init();MX_TIM3_Init();HAL_TIM_PWM_Start(&hti…

代码随想录算法训练营第二十七天|131.分割回文串、93.复原IP地址

文档链接&#xff1a;https://programmercarl.com/ LeetCode131.分割回文串 题目链接&#xff1a;https://leetcode.cn/problems/palindrome-partitioning/ 思路&#xff1a;把回溯的树画出来就好很多。startIndex用来控制切割的位置 例如对于字符串abcdef&#xff1a; 组…

实现offsetof宏以及交换一个整数二进制奇偶位的宏

目录 1. offsetof宏2. 交换奇偶位 1. offsetof宏 我们想用宏来实现offsetof函数,首先要了解这个函数的用法。 1.1 offsetof函数的介绍及用法 &#xff08;1&#xff09;功能&#xff1a;用来计算结构体中一个成员在该结构体中的相对起始位置的偏移量&#xff0c;单位是字节。 …

Golang goroutine 同步原语:sync 包让你对并发控制得心应手

在 Go 语言中&#xff0c;不仅有 channel 这类比较易用且高级的同步机制&#xff0c;还有 sync.Mutex、sync.WaitGroup 等比较原始的同步机制。通过它们&#xff0c;我们可以更加灵活地控制数据的同步和多协程的并发。 资源竞争 在一个 goroutine 中&#xff0c;如果分配的内存…

Python多任务处理---多线程

引入 生活中&#xff0c;我们在电脑上打开了一个word, 这个word对操作系统来说就是一个进程。我们在进行word操作的时候&#xff0c;比如在你打字的时候&#xff0c;该word同时可以进行文字检查。发现了没&#xff0c;在同一个进程中&#xff0c;我们也可以进行同时操作。…

【Pytorch学习笔记(二)】张量的创建(补充)

一、知识回顾 我们在博客《张量的创建与访问》中已经讨论了一些张量的创建方法如torch.CharTensor()、torch.FloatTensor()以及torch.zeros()等张量创建方法&#xff0c;但由于其仅仅介绍了cpu版本torch下张量的创建方法和只有具体数据类型张量&#xff0c;本节内容旨在补充gp…

论文速览 | IEEE TCI, 2022 | 单光子级非视距成像:估计强度与优化重建

注1:本文系"计算成像最新论文速览"系列之一,致力于简洁清晰地介绍、解读非视距成像领域最新的顶会/顶刊论文(包括但不限于 Nature/Science及其子刊; CVPR, ICCV, ECCV, SIGGRAPH, TPAMI; Light‑Science & Applications, Optica 等)。 本次介绍的论文是:<2…

【Git】命令行使用体验大大优化的方法

Git的优化使用 相信很多人&#xff0c;在使用git作为版本管理工具时都会感受到它的方便&#xff0c;但是也会有一些问题困扰着我们&#xff0c;让我们觉得使用体验不是很好。我在使用git的过程中就发现了几个问题&#xff1a;写commit费时、怎么做多人开发的代码审查等等。今天…

代码随想录算法训练营第二十五天| 216.组合总和III,17.电话号码的字母组合

题目与题解 216.组合总和III 题目链接&#xff1a;216.组合总和III 代码随想录题解&#xff1a;216.组合总和III 视频讲解&#xff1a;和组合问题有啥区别&#xff1f;回溯算法如何剪枝&#xff1f;| LeetCode&#xff1a;216.组合总和III_哔哩哔哩_bilibili 解题思路&#xf…

Linux之用户账号、用户组和与账号有关的系统文件

目录 一、基本介绍 1.用户和用户组 2.UID和GID 二、 账户管理 1.查看用户的UID和GID 2.添加账户 3.删除账号 4.修改账号 5.账户口令 三、分组管理 1.新增用户组 2.删除用户组 3.修改用户组 4.用户组切换 四、与账号有关的系统文件 1./etc/passwd 2./etc/shado…

组蛋白脱乙酰酶介导的胃癌肿瘤微环境特征及协同免疫治疗(多组学文献学习)

目录 ①HDAC转录组多数据NMF一次聚类 ②ACRG队列中HDAC单独NMF聚类 ③HDS评分在胃癌中的临床特征和基因组特征 ④高 HDS 可能提示胃癌的“热”肿瘤状态 ⑤HDS是胃癌免疫治疗效果的有力预测指标 ⑥单细胞转录组测序揭示了高HDS和低HDS患者的TME ⑦内皮细胞和成纤维细胞可…

Prometheus+grafana环境搭建mysql(docker+二进制两种方式安装)(三)

由于所有组件写一篇幅过长&#xff0c;所以每个组件分一篇方便查看&#xff0c;前两篇 Prometheusgrafana环境搭建方法及流程两种方式(docker和源码包)(一)-CSDN博客 Prometheusgrafana环境搭建rabbitmq(docker二进制两种方式安装)(二)-CSDN博客 1.监控mysql 1.1官方地址:…

文本评估指标 BLEU,METEOR,ROUGE

文本评估指标 这里注意库包的版本&#xff0c;亲测这个很包敏感&#xff0c;所以一定要调好库版本 nltk 3.6.3 如果这个包的版本不对会报错&#xff0c;很难理解的那种 rouge1.0.1 定义函数 import jieba from rouge import Rouge from nltk.translate.meteor_score import …

CrossOver玩游戏会损害电脑吗 CrossOver玩游戏会卡吗 Mac玩游戏 crossover24免费激活

CrossOver是一款可以在macOS上运行Windows应用程序的软件&#xff0c;它利用了Wine技术&#xff0c;无需安装虚拟机或双系统&#xff0c;可以直接在苹果系统下运行Windows游戏。那么&#xff0c;使用CrossOver玩游戏会损害电脑吗&#xff1f;CrossOver玩游戏会卡吗&#xff1f;…

java中:print与println的区别

目录 区别 区别 print是直接打印输出 println是输出后自动回车到下一行 例如 public class test {public static void main(String[] args){System.out.println("换行");System.out.print("不换行");System.out.println();}}——————————————…

Scala第十五章节(递归的相关概述、Scala阶乘案例、Scala斐波那契数列案例、Scala打印目录文件案例)

章节目标 了解递归的相关概述掌握阶乘案例掌握斐波那契数列案例掌握打印目录文件案例 1. 递归 递归指的就是 方法自己调用自己的情况 . 在涉及到复杂操作时, 我们会经常用到它. 在使用递归时, 要注意以下三点: 递归必须有出口, 否则容易造成 死递归 .递归必须要有规律.构造…

跑spark的yarn模式时RM连不上的情况

在linux控制台跑spark on yarn一个测试案例&#xff0c;日志中总显示RM连yarn服务的时候是&#xff1a;0.0.0.0:8032 具体情况如下图&#xff1a; 我问题出现的原因&#xff0c;总结如下&#xff1a; 1.防火墙没关闭&#xff0c;关闭 2.spark-env.sh这个文件的YARN_CONF_DIR…

爱上数据结构:二叉树的基本概念

​ ​ &#x1f525;个人主页&#xff1a;guoguoqiang. &#x1f525;专栏&#xff1a;数据结构 ​ 一、树的基本概念 1.概念 树是一种非线性的数据结构&#xff0c;它是由n&#xff08;n>0&#xff09;个有限结点组成一个具有层次关系的集合。把它叫做树是因 为它看起…

鸿蒙OS开发案例:【ArkTS类库多线程CPU密集型任务Worker】

使用Worker进行长时间数据分析 通过某地区提供的房价数据训练一个简易的房价预测模型&#xff0c;该模型支持通过输入房屋面积和房间数量去预测该区域的房价&#xff0c;模型需要长时间运行&#xff0c;房价预测需要使用前面的模型运行结果&#xff0c;因此需要使用Worker。 …