题目地址:https://pintia.cn/problem-sets/14/problems/739

前言

咱目前还只能说是个小白,写题解是为了后面自己能够回顾。如果有哪些写错的/能优化的地方,也请各位多指教。( •̀ ω •́ )

题目描述

本题要求实现一个函数,判断任一给定整数N是否满足条件:它是完全平方数,又至少有两位数字相同,如144、676等。

展开查看详情

函数接口定义

int IsTheNumber ( const int N );

其中N是用户传入的参数。如果N满足条件,则该函数必须返回1,否则返回0。

裁判测试程序样例

#include <stdio.h>
#include <math.h> int IsTheNumber ( const int N ); int main()
{
int n1, n2, i, cnt; scanf("%d %d", &n1, &n2);
cnt = 0;
for ( i=n1; i<=n2; i++ ) {
if ( IsTheNumber(i) )
cnt++;
}
printf("cnt = %d\n", cnt); return 0;
} /* 你的代码将被嵌在这里 */

输入样例

105 500

输出样例

cnt = 6

限制

限制内容 限制条件
代码长度限制 16 KB
时间限制 400 ms
空间限制 64 MB

想法

注:完全平方数指的是一个可以由 某一个整数的平方 表达的数。

判断完全平方数

首先观察给出的裁判测试程序样例,发现程序在预处理部分引入了math.h,很明显,要判断完全平方数,我们得用到math.h头文件中声明的sqrt()(开平方根)函数:

double sqrt ( double arg );

该函数返回的是一个双精度浮点数,如果其小数部分为0,则说明该数是完全平方数。

这样想,其实将sqrt()函数的返回值转换为整型,将这个整型的平方和原数进行比较,就可以判断是否为完全平方数了:

int squareRoot = (int) sqrt(N);
if (squareRoot * squareRoot == N) {
// N是完全平方数
}

我最开始用了种危险的写法

double squareRoot = sqrt(N);
if (squareRoot == (int) squareRoot) {
// N是完全平方数
}

运行起来可能不会出问题,但实际上是有隐患的。这里的逻辑其实是在将整型浮点型在进行比较,而计算机中的浮点数储存是不精确的,不要这样写。

至少有两位数字相同

虽然题目中给出的样例数都是三位数,但是PTA吧,肯定不会这么容易就让我过,那我肯定要再上升一层进行思考。

我的想法是从最低位开始,用数组储存每一位的数字。而在每次迭代中,将当前位的数字与数组中的每一位进行比较,只要遇到相同的,就能保证至少有两位数字相同:

// 判断整数number中是否至少有两位数字相同
int HasTwoSameNum(const int number) {
int quotient = number; // 商
int remainder; // 余数
int arrLen = 0;
int arr[10]; // int型最多10位数字
int i;
while (quotient > 0) {
remainder = quotient % 10; // 余数
quotient = quotient / 10; // 商
for (i = 0; i < arrLen; i++) {
if (arr[i] == remainder)
return 1;
}
arr[arrLen++] = remainder;
}
return 0;
}

为什么定义数组时将元素个数定为10呢?因为题目中处理的数据类型是整型。

目前来说,一般的计算机中一个整型int占用4个字节,即32位,而32位的整型在计算机储存时要用到31个二进制位来表示数值(最高位表示符号),因此int的取值范围是-2^312^31-1,即-21474836482147483647

很明显,题目关注的是十进制数,观察2147483648能发现,int型的整数在十进制下最多只有10位,所以我才将数组的元素个数定为10


关于提取整数的每一位数字这部分,实际上用取模和取整就可以实现。

上述代码中,quotient % 10能得到quotient的最低位数字;而quotient / 10能得到quotient除去最低位数字的整数,这个数值就是下一次迭代的quotient

迭代至quotient0时,就已经把原整数中的每一位数都取遍了。

题解代码

OJ端提交的代码:

int HasTwoSameNum(const int number) {
int quotient = number; // 商
int remainder; // 余数
int arrLen = 0;
int arr[10]; // int型最多10位数字
int i;
while (quotient > 0) {
remainder = quotient % 10; // 余数
quotient = quotient / 10; // 商
for (i = 0; i < arrLen; i++) {
if (arr[i] == remainder)
return 1;
}
arr[arrLen++] = remainder;
}
return 0;
} int IsTheNumber(const int N) {
int squareRoot = (int) sqrt(N);
// 如果平方根都不是,就没必要调用HasTwoSameNum了
if (squareRoot * squareRoot == N && HasTwoSameNum(N))
return 1;
else
return 0;
}

本地测试可用:

#include <stdio.h>
#include <math.h> int IsTheNumber(const int N); int HasTwoSameNum(const int number); int main() {
int number;
printf("Input an integer: ");
fflush(stdout);
scanf("%d", &number);
printf("IsTheNumber = %d\n", IsTheNumber(number)); return 0;
} int HasTwoSameNum(const int number) {
int quotient = number; // 商
int remainder; // 余数
int arrLen = 0;
int arr[10]; // int型最多10位数字
int i;
while (quotient > 0) {
remainder = quotient % 10; // 余数
quotient = quotient / 10; // 商
for (i = 0; i < arrLen; i++) {
if (arr[i] == remainder)
return 1;
}
arr[arrLen++] = remainder;
}
return 0;
} int IsTheNumber(const int N) {
int squareRoot = (int) sqrt(N);
// 如果平方根都不是,就没必要调用HasTwoSameNum了
if (squareRoot * squareRoot == N && HasTwoSameNum(N))
return 1;
else
return 0;
}

提交结果

【题解笔记】PTA基础6-7:统计某类完全平方的更多相关文章

  1. 线段树学习笔记(基础&进阶)(一) | P3372 【模板】线段树 1 题解

    什么是线段树 线段树是一棵二叉树,每个结点存储需维护的信息,一般用于处理区间最值.区间和等问题. 线段树的用处 对编号连续的一些点进行修改或者统计操作,修改和统计的复杂度都是 O(log n). 基础 ...

  2. (转)深度学习word2vec笔记之基础篇

    深度学习word2vec笔记之基础篇 声明: 1)该博文是多位博主以及多位文档资料的主人所无私奉献的论文资料整理的.具体引用的资料请看参考文献.具体的版本声明也参考原文献 2)本文仅供学术交流,非商用 ...

  3. 深度学习word2vec笔记之基础篇

    作者为falao_beiliu. 作者:杨超链接:http://www.zhihu.com/question/21661274/answer/19331979来源:知乎著作权归作者所有.商业转载请联系 ...

  4. [学习笔记] Numpy基础 系统学习

    [学习笔记] Numpy基础 上专业选修<数据分析程序设计>课程,老师串讲了Numpy基础,边听边用jupyter敲了下--理解+笔记. 老师讲的很全很系统,有些点没有记录,在PPT里就不 ...

  5. 从头开始学JavaScript 笔记(一)——基础中的基础

    原文:从头开始学JavaScript 笔记(一)--基础中的基础 概要:javascript的组成. 各个组成部分的作用 . 一.javascript的组成   javascript   ECMASc ...

  6. MyBatis:学习笔记(1)——基础知识

    MyBatis:学习笔记(1)--基础知识 引入MyBatis JDBC编程的问题及解决设想 ☐ 数据库连接使用时创建,不使用时就释放,频繁开启和关闭,造成数据库资源浪费,影响数据库性能. ☐ 使用数 ...

  7. bootstrap学习笔记之基础导航条 http://www.imooc.com/code/3111

    基础导航条 在Bootstrap框中,导航条和导航从外观上差别不是太多,但在实际使用中导航条要比导航复杂得多.我们先来看导航条中最基础的一个--基础导航条. 使用方法: 在制作一个基础导航条时,主要分 ...

  8. Django学习笔记(基础篇)

    Django学习笔记(基础篇):http://www.cnblogs.com/wupeiqi/articles/5237704.html

  9. ArcGIS案例学习笔记-聚类点的空间统计特征

    ArcGIS案例学习笔记-聚类点的空间统计特征 联系方式:谢老师,135-4855-4328,xiexiaokui@qq.com 目的:对于聚集点,根据分组字段case field,计算空间统计特征 ...

  10. C#学习笔记(基础知识回顾)之值类型与引用类型转换(装箱和拆箱)

    一:值类型和引用类型的含义参考前一篇文章 C#学习笔记(基础知识回顾)之值类型和引用类型 1.1,C#数据类型分为在栈上分配内存的值类型和在托管堆上分配内存的引用类型.如果int只不过是栈上的一个4字 ...

随机推荐

  1. js 实现俄罗斯方块(二)

    上篇已经看过整个游戏的样子了,本节我们来分析下整个游戏 和实现的逻辑! 首先看下游戏规则: 首先确定这几个形状原型   这7个基础图形都是由4个格子组成. 规则: 1.当所有色块填满一整行以后自动清理 ...

  2. mysql 重置主键

    开发时总是要向数据库写入测试数据,删掉以后id(自增主键)依然还是在增长,这个问题我遇到好多次,也都没有在意. 最近这个习惯被朋友嫌弃 = =||| 就在网上搜索了下mysql重置主键的办法: ALT ...

  3. Golang在整洁架构基础上实现事务

    前言 大家好,这里是白泽,这篇文章在 go-kratos 官方的 layout 项目的整洁架构基础上,实现优雅的数据库事务操作. 视频讲解 :B站:白泽talk,公众号[白泽talk] 本期涉及的学习 ...

  4. Minnaert

    Minnaert 假设气泡关闭时发生周期性膨胀和收缩,周围水也跟着振动,就嗷地一声叫了出来!设有个半径为 \(r\) 的泡形成后开始简谐振动,半径有 \[r=r_0+a\sin\frac{2\pi t ...

  5. CF650D Zip-line

    CF650D Zip-line 大概题面: 给定一个长度为 \(n\) 的序列以及\(m\)个操作,每个操作形如" \(a_i,b_i\) ",表示将序列中第 \(a_i\) 个数 ...

  6. element-ui 表格控制列显隐简单方案

    核心是使用v-if控制列的显隐 <template> <div> <div v-for="(item, index) in tables" :key= ...

  7. WIN32下的模拟时钟

    #include <Windows.h> #include <math.h> #include <tchar.h> #include "resource. ...

  8. 一种PyInstaller中优雅的控制包大小的方法

    PyInstaller会在打包时自动为我们收集一些依赖项,特别是我们在打包PyQt/PySide相关的应用时,PyInstaller会自动包含我们程序通常不需要的文件,如'tanslations'文件 ...

  9. 【测试平台开发】——04Flask后端api开发实战(一)

    一.测试平台开发模式 要开发一套平台有两种开发模式,一个[大而全],一个[小而简]. 说道[大而全]想到目前大型项目都使用的语言[JAVA],[小而简]想到的是[Python]语言. 重武器(大而全) ...

  10. 【测试平台开发】——01后端web开发框架Flask

    官方中文地址:https://flask.net.cn/ 官方英文地址:https://flask.palletsprojects.com/en/2.1.x/ github地址:https://git ...