剑指offer-31:整数中1出现的次数(从1到n整数中1出现的次数)
参考: https://troywu0.gitbooks.io/interview/整数中出现1的次数(从1到n整数中1出现的次数).html
题目描述
解题思路1 (暴力法,时间复杂度: O(nlog(n))
public int NumberOf1Between1AndN_Solution(int n) {
int count = 0;
while (n > 0) {
String nStr = String.valueOf(n);
for (int i = 0; i < nStr.length(); i++) {
if (nStr.charAt(i) == '1')
count++;
}
n--;
}
return count;
}
这种方法的思路简单,统计每一个数中出现1的次数,能够快速写出代码。但是,这种方法的时间复杂度很高,O(nlog(n)),面试这么写,估计不会留下好的印象。
解题思路2 (数学规律法,时间复杂度: O(log(n))
public int NumberOf1Between1AndN_Solution(int n) {
int low = 0, cur = 0, high = 0;
int count = 0;
int factor = 1;
while (factor <= n) {
high = n / (factor * 10);
low = n % factor;
// cur = (n - high * (factor * 10) - low) / factor;
cur = (n / factor) % 10;
if (cur == 0)
count += high * factor;
else if (cur == 1)
count += high * factor + low + 1;
else
count += (high + 1) * factor;
factor *= 10;
}
return count;
}
这一个思路利用了数字的规律和特点,解决问题的效率非常的高,时间复杂度只与数的位数有关。
首先看一个规律:
- 从1 - 10中,个位中 1 出现的次数是1,即1这个数;
- 从1 - 100中,十位中 1 出现的次数是10, 即10, 11, ..., 18, 19;
- 从1 - 1000中,百位中 1 出现的次数是100,即100, 101, ..., 198, 199;
- 以此类推。
假设有一个四位数,使用 cur 来表示当前位数对应的数值,high表述cur左边的数,low表示cur右边的数。会有三种情况产生:
- 第一种:cur = 0,1出现的次数等于 high * (该位数对应的基数)
- 假设四位数为1023,求百位上1出现的次数;
- 此时 high = 1, cur = 0, low = 23;
- 次数 = 1 * 100;
- 即100, 101, ..., 198, 199。
- 第二种:cur = 1,1出现的次数等于 high * (该位数对应的基数) + low + 1
- 假设四位数为1123,求百位上1出现的次数;
- 此时 high = 1, cur = 1, low = 23;
- 次数 = 1 * 100 + 23 + 1;
- 即100, 101, ..., 198, 199 + 1100, 1101, ..., 1122, 1123。
- 第三种:cur > 1,1出现的次数等于 (high + 1) * (该位数对应的基数)
- 假设四位数为1223,求百位上1出现的次数;
- 此时 high = 1, cur = 2, low = 23;
- 次数 = (1 + 1) * 100;
- 即100, 101, ..., 198, 199 + 1100, 1101, ..., 1198, 1199。
根据这一规律,从最低位至最高位,依次求出1出现的次数,最后相加得到最终的结果。
剑指offer-31:整数中1出现的次数(从1到n整数中1出现的次数)的更多相关文章
- 剑指 Offer 31. 栈的压入、弹出序列 + 入栈顺序和出栈顺序的匹配问题
剑指 Offer 31. 栈的压入.弹出序列 Offer_31 题目详情: 解析: 这里需要使用一个栈来模仿入栈操作. package com.walegarrett.offer; /** * @Au ...
- 剑指 Offer 31. 栈的压入、弹出序列
剑指 Offer 31. 栈的压入.弹出序列 输入两个整数序列,第一个序列表示栈的压入顺序,请判断第二个序列是否为该栈的弹出顺序.假设压入栈的所有数字均不相等.例如,序列 {1,2,3,4,5} 是某 ...
- 【强烈推荐】《剑指Offer:名企面试官精讲典型编程题》一书中IT名企经典面试题
各位程序猿: <剑指Offer>一书源自该书作者何海涛坚持更新与编写的博客(http://zhedahht.blog.163.com/),该博客收集整理了大量如微软.Goo ...
- 【Java】 剑指offer(31) 栈的压入、弹出序列
本文参考自<剑指offer>一书,代码采用Java语言. 更多:<剑指Offer>Java实现合集 题目 输入两个整数序列,第一个序列表示栈的压入顺序,请判断第二个序列是否 ...
- 【剑指Offer面试编程题】题目1508:把字符串转换成整数--九度OJ
题目描述: 将一个字符串转换成一个整数,要求不能使用字符串转换整数的库函数. 输入: 输入可能包含多个测试样例. 对于每个测试案例,输入为一个合法或者非法的字符串,代表一个整数n(1<= n&l ...
- 剑指Offer 31. 整数中1出现的次数(从1到n整数中1出现的次数) (其他)
题目描述 求出1~13的整数中1出现的次数,并算出100~1300的整数中1出现的次数?为此他特别数了一下1~13中包含1的数字有1.10.11.12.13因此共出现6次,但是对于后面问题他就没辙了. ...
- 剑指offer第12题打印从1到n位数以及大整数加法乘法
字符和数字加减就是字符的ASCII码和数字直接加减. 方法一: 1)在字符串操作中给一个整形数字加(字符0)就是把它转化为字符,当然给一个字符减去(字符0)就可以把它转化为数字了:如果确实是最后 ...
- [剑指Offer] 31.整数中1出现的次数
题目描述 求出1~13的整数中1出现的次数,并算出100~1300的整数中1出现的次数?为此他特别数了一下1~13中包含1的数字有1.10.11.12.13因此共出现6次,但是对于后面问题他就没辙了. ...
- 剑指offer——31序列化二叉树
题目描述 请实现两个函数,分别用来序列化和反序列化二叉树 二叉树的序列化是指:把一棵二叉树按照某种遍历方式的结果以某种格式保存为字符串,从而使得内存中建立起来的二叉树可以持久保存.序列化可以基于先 ...
- 每日一题 - 剑指 Offer 31. 栈的压入、弹出序列
题目信息 时间: 2019-06-25 题目链接:Leetcode tag:栈 难易程度:中等 题目描述: 输入两个整数序列,第一个序列表示栈的压入顺序,请判断第二个序列是否为该栈的弹出顺序.假设压入 ...
随机推荐
- Python实现发送邮件代码
代码如下: # -*- coding: utf-8 -*- #!/usr/bin/env python # @Time : 2017/12/22 17:50 # @Desc : # @File : m ...
- php+mysql 实现无限极分类
php+mysql 实现无限极分类<pre>id name pid path 1 电脑 0 0 2 手机 0 0 3 笔记本 1 0-1 4 超级本 3 0-1-3 5 游戏本 3 0-1 ...
- Unity中用Mesh画一个圆环(二)
中目标-生成完整面 在之前的内容中我们已经成功生成了一个面,接下来我们要生成剩下的面就很容易了. 我们把之前生成的面当作顶面,接着我们来生成底面. 还记得前面说过\(\color{#1E90FF}{D ...
- ES6学习笔记01 -- 暂时性死区 ( temporal dead zone )
参考文档: let 和 const 命令 - ECMAScript6入门 暂时性死区(temporal dead zone) 理解ES6中的TDZ(暂时性死区) ES6 中 let 暂时性死区详解 ...
- element 动态合并表格
前言 element 官方的例子太简单了,不满足实际的需求 数据肯定是动态的,合并的行数,列数都是动态的,该如何知道每一行的合并数呢 需求 动态合并表格,数据来源于数据库 正文 一开始,我的数据源是单 ...
- 理解clientWidth,offsetWidth,clientLeft,offsetLeft,clientX,offsetX,pageX,screenX
1. clientWidth:表示元素的内部宽度,以像素计.该属性包括内边距,但不包括垂直滚动条(如果有).边框和外边距.(clientWidth = width + padding) 2. offs ...
- nginx+uWSGI+django+virtualenv+superviso发布web服务器
1.环境依赖 yum groupinstall "Development tools" -y yum install zlib-devel bzip2-devel pcre-dev ...
- Linq三表连接查询加分组
1.Linq查询 2.数据库事例: 3.效果图:
- 你必须知道的容器日志 (2) 开源日志管理方案 ELK
本篇已加入<.NET Core on K8S学习实践系列文章索引>,可以点击查看更多容器化技术相关系列文章.上一篇<你必须知道的容器日志(1)>中介绍了Docker自带的log ...
- Itellij idea2019.2 激活码,有效期2020.5
Itellij idea2019.2 激活码,有效期2020.5 MNQ043JMTU-eyJsaWNlbnNlSWQiOiJNTlEwNDNKTVRVIiwibGljZW5zZWVOYW1lIjoi ...