CodeWars-Find the next perfect square!

今天的题目,加深了关于对象类型以及函数和对象方法的理解。

一.题目

You might know some pretty large perfect squares. But what about the NEXT one?

Complete the findNextSquare method that finds the next integral perfect square after the one passed as a parameter. Recall that an integral perfect square is an integer n such that sqrt(n) is also an integer.

If the parameter is itself not a perfect square, than -1 should be returned. You may assume the parameter is positive.

Examples:

findNextSquare(121) --> returns 144
findNextSquare(625) --> returns 676
findNextSquare(114) --> returns -1 since 114 is not a perfect

一些英语单词:

1.perfect square
完全平方数
完全平方数是指例如一个数能表示成某个整数的平方。例如

9=3×3
121=11×11

9和121就是完全平方数。

  1. parameter
    /pəˈræmɪtə(r)/
    n.参数

关于上面的翻译:

你也许知道一些很大的完全平方数,但是这个完全平方数下一个完全平方数你又知道吗?

完成这个名为findNextSquare的函数,这个函数当输入一个参数后,可以找到下一个完全平方数。回想一下,一个整数完全平方数是这个整数开根号后还是一个整数。

如果这个参数本身并不是一个完全平方数,那么就返回-1吧。假定输入的参数都是正数。

初始代码

CodeWars-Find the next perfect square!_第1张图片
Find the next perfect square!

举个栗子

Test.describe("find_next_square")

Test.it("should return the next square for perfect squares")
Test.assert_equals(find_next_square(121), 144, "Wrong output for 121")
Test.assert_equals(find_next_square(625), 676, "Wrong output for 625")
Test.assert_equals(find_next_square(319225), 320356, "Wrong output for 319225")
Test.assert_equals(find_next_square(15241383936), 15241630849, "Wrong output for 15241383936")

Test.it("should return -1 for numbers which aren't perfect squares")
Test.assert_equals(find_next_square(155), -1, "Wrong output for 155")
Test.assert_equals(find_next_square(342786627), -1, "Wrong output for 342786627")

二.代码和思路

思路

先想想函数大概的框架

输入:一个整数
操作:判断是否是完全平方数,然后按要求返回
输出:-1或完全平方数数

开始的思路是,121开根号是整数,120开根号不是整数。那就将121开根号然后判断是不是整型,这样就知道是不是完全平方数了
所以判断的语句是

    if isinstance(math.sqrt(sq),int):

isinstance是python的内置函数,用来判断对象是不是某种类型。

当时的思路是:
如果sq是完全平方数。那么math.sqrt(sq)就是整型。
如果sq不是完全平方数,那么math.sqrt(sq)就是浮点数。

但是!!!
错误来了哦,无论sq是不是完全平方数,这条if语句都判定为错。
即使sq=121,isinstance(math.sqrt(sq),int)的结果是:False !!!

问题出在哪呢?
用type()函数后发现,原来math.sqrt()的返回结果,都是浮点数(float)。
这里就是我们判断整数和计算机判断整数的不同:
我们对121开根号结果是11,11是整数。对120开根号,10.954....不是整数。
但计算机不是,用math.sqrt()计算后,返回的结果都是float。math.sqrt(121)是等于11,但不是(int) 11 , 而是(float) 11.0
!!! 计算机并不会把(float)11.0自动变为(int)11

既然不能通过类型判断整数,接着可以通过值判断。
例如 11.0(float)=11(int) 结果为True
(PS:后面最优解会更简单的判断是不是整数的方法)
将if语句改成

    if math.sqrt(sq) == math.trunc(math.sqrt(sq)):

math.trunc()方法即直接舍弃该数字的小数部分。
例如math.trunc(10.51) 会返回 10(int)

当时以这样值比较的方式,就写了下面的代码

代码

import math
def find_next_square(sq):
    if math.sqrt(sq) == math.trunc(math.sqrt(sq)):
        return (math.sqrt(sq) + 1) ** 2
    else:
        return -1

三.最优代码解

CodeWars-Find the next perfect square!_第2张图片
Best Practics

我们前面想用函数isinstance()来判断是不是整数行不通
但其实Python是有办法的,就是浮点数里面有个方法is_integer()

    if root.is_integer():

是的,就这么简单。

另外一种用值来判断的话,也很简单的就是

    if x%1 :

四.总结

1.对象类型
对象类型在做类型判断的时候是很关键。像本题中math.sqrt()返回值就是float,并不会和我们想的再自行判断是不是整数。

2.函数和方法
之前关于函数和方法就一直在困惑我。
该怎么区分函数和表达式?

一个数x开根号:

    x**0.5 #表达式
    pow(x,0.5) # 函数
    math.sqrt(x) #方法

抛开表达式,我们来看看函数和方法。
其实方式就是一种特殊的函数。他写在了对象里面,所以要使用这个方法的时候,得先写出该对象的变量名,然后加个 ‘.’ 再写该方法名。

    x='abcdefgh' #x是变量名字,x对象类型是字符串
    x.replace(‘a’,'b') #字符串里面有replace()方法    

如果想知道这个对象类型有什么方法的话,可以查阅文档或在python中用dir()函数

x='abc' #字符串
dir(a)
x=1.0 #浮点数
dir(x)
x=1 #整数
dir(x)

以浮点数为例输出结果(打印输出)

__abs__
__add__
__bool__
__class__
__delattr__
__dir__
__divmod__
__doc__
__eq__
__float__
__floordiv__
__format__
__ge__
__getattribute__
__getformat__
__getnewargs__
__gt__
__hash__
__init__
__init_subclass__
__int__
__le__
__lt__
__mod__
__mul__
__ne__
__neg__
__new__
__pos__
__pow__
__radd__
__rdivmod__
__reduce__
__reduce_ex__
__repr__
__rfloordiv__
__rmod__
__rmul__
__round__
__rpow__
__rsub__
__rtruediv__
__setattr__
__setformat__
__sizeof__
__str__
__sub__
__subclasshook__
__truediv__
__trunc__
as_integer_ratio
conjugate
fromhex
hex
imag
is_integer
real

双下划线开头和结尾的是函数,可以传入浮点数的一些函数。
而后面没有以双下划线开头的,就是浮点数里面的方法。

当然也不用刻意去记,方法和函数用的多了,自然就记住了。(就像这次记住了浮点数里面有个is_integer()方法 )

你可能感兴趣的:(CodeWars-Find the next perfect square!)