5. 条件和递归

5. 条件和递归

本章主要话题是if表达式, 它根据程序的状态执行不同的代码.
但首先介绍两个操作符号: 向下取整除法操作符和求模操作符.
5.1 向下取整除法操作符和求模操作符
向下取整除法操作符(//)对两个数除法运算, 并向下取整得到一个整数.
假设, 一个电影的播放时长为105分钟, 你肯能会想知道按小时算这是多长.
传统的除法会得到一个浮点数: (但是, 在写小时数时通常并不用小数点.)
>>> minutes = 105
>>> minutes / 60
1.75
向下取整除法, 则丢弃小数部分, 得到整数的小时数:
>>> minutes = 105
>>> hours = minutes // 60
>>> hours
1
要求得余数, 可以从分钟数中减去1小数:
>>> remainder = minutes - hours * 60
>>> remainder
45
另一种办法是使用求模操作符(%)将两个数相除, 得到余数:
>>> remainder = minutes % 60
>>> remainder 
45
求模操作符其实有很多实际用途. 
例如, 可以用它来检测一个数是不是另一个的倍数-如果x % y是0, 则x可以被y整除(x除以y的意思).
另外, 也可以用它来获取一个数后一位或后几位数字(这个数字是余数).
例如, x % y可以得到x的个位数(10进制).
类似地, x % 100可以获得最后两位数.如果使用的是Pythond2, 除法机制会有所不同,
除法操作符(/)在两个操作数都是整数的情况下, 实际进行的是向下取整数除法操作, 
而当两个操作数中有一个是浮点数时, 则进行的浮点数除法.
>>> 5 / 2
2
>>> 5.0 /2
2.5
>>> 5 / 2.0
2.5
5.2 布尔表达式
布尔表达式是值为真或假的表达式.
下面的例子中使用了==操作符, 来比较两个操作对象是否相等, 如果相等, 则得到True, 否则为False.
True和False是类型bool的两个特殊值, 它们不是字符串.
>>> 5 == 5
True
>>> 5 == 4
False>>> type(True)
<class 'bool'>>>> type(False)
<class 'bool'>
== 操作符是一个关系操作符, 其它的关系操作符有:
x != y   x不等于x
x > y    x大于y
x < y    x小于y
x >= y   x大于或等于y
x <= y   x小于或等于y
* 千万要注意不要写成 =>, =<.Python的操作符和数学的操作符还是有区别的, 最常见的错误是使用单等号(=)而不是双等号(==).
请注意=是一个赋值操作符, ==是一个关系操作符.
5.3 逻辑操作符
逻辑操作符有三个: and, or, not. 这些操作符的语义和他们在英语中的意思差不多.
例如, x > 0 and x < 10, 只有当x大于0且比10要小, 结果才为真, 否则为假.
n % 2 == 0 or n % 3 == 0, 当其中任意一个条件为真, 结果才为真, 否则为假.
最后, not操作符可以否定一个布尔表达式, 所以not(x > y)在x大于y时结果为假, x小于y时结果为真.
严格地说, 逻辑操作符的操作对象应该是布尔值表达式,
但是Python并不那么严格, 任何非0, 非空(None, 空字符串, 空列表... )的数都被解释为True.
>>> 42 and True
True
这种灵活性可能会很有用, 但有时候也会带一些小困惑, 
除非你很确切地知道自己在做什么, 否则因该避免使用它.
5.4 条件执行
为了编写有用的程序, 我们几乎总是需要检查条件并据此改变程序的行为. 条件语句给我们带来这种能力.
简单的形式是if表达式:
if x > 0:print('x is positive')
if之后的布尔表达式被称为条件(condition). 如果它为真, 则会执行后面缩进的语句, 否则什么都不做.
if表达式的结构和函数定义一样, 一个语句头, 接着是缩进的语句体. 这种类型的语句称为复合语句.
语句体中出现的语句数量并没有限制, 但是最少需要一行.
偶尔可能会遇到一个语句体什么都不做(通常是标记一个你还没有来得及写的代码的位置).
这个时候可以使用pass语句, pass语句什么都不做. (使用pass占位, 避免语法错误.)
if x < 0:pass  # TODO: 需要处理负责的情况.
5.5 选择执行
if语句的第二种形式是选择执行, 这种形式下, 有两种可能, 而if的条件决定哪一种运行.
语句看起来是这样的:
if x % 2 == 0:# 偶数print('x is even')else:# 奇数print('x is odd')
如果x除以2的余数是0, 则我们知道x是偶数(even), 并且程序会显示合适的消息'x is even'.
如果条件为假, 则第二段语句会运行, 因为条件必定是真假之一, 所以必然只会有一段语句运行.
这两段不同的语句成为分支(branch), 因为它们是程序执行流程中的两个支流.
5.6 条件链
有时候有超过两种可能, 所有我们需要更多的分支.
表达这种计算的一种方式是条件链(chained conditional): 
if x < y: # x小于y.print('x is less than y.')elif x > y:# x大于y.print('x is greater than y.')
else:# x和y相等.print('x and y are equal.')
elif是'else if'的缩写, 和之前一样, 只有一个分支会运行. elif语句的数量没有限制.
如果有一个else语句, 则它必须放在最后, 但也可以没有else语句.
# 前一章练习的代码片段.s
if choice == 'a':draw_a()
elif choice == 'b':draw_b()
elif choice == 'c':draw_c()
每个条件都按顺序检查, 如果第一个条件是False, 则检查下一个条件, 依次类推.
如果有一个条件为真, 则运行相应的分支, 而整个语句结束.
即使有很多个条件为真, 也只有第一个为真的分支会运行.
5.7 嵌套条件
条件判断可以再嵌套条件判断, 我们可以修改前一节中的示例, 如下:
if x == y:print('x and y are equal.')
else:if x < y:print('x is less than y.')else:print(x is greater than y.)
外侧的条件语句包含两个分支(顶格书写的语句), 第一个分支包含一行简单的语句.
第二个分支则包含了另一个if语句, 它本身也有两个分支, 
这两个分支也都是简单语句, 虽然它们其实也可以是条件语句(意思是说, 这些简单的语句可以是条件语句). 虽然语句的缩进让结构非常清晰, 但嵌套条件语句会很快随着嵌套层数增多而变得非常难以阅读, 
应该尽量避免它.
逻辑操作符常常能够用来简化嵌套条件语句. 例如, 我们可以将下面的语句替换为单独的一个条件:
if 0 < x:if x < 10:print('x is a positive single-digit number.')
对于这种类型的条件, Python还提供了一个更简洁地语法:
if 0 < x < 10:print('x is a positive single-digit number.')
5.8 递归
函数调用另外一个函数时合法的; 函数调用自己也是合法的.
这样做有什么好处可能还不明显, 但它其实是程序能做的最神奇的事情之一. 例如, 考虑下面的函数:
def countdown(n):if n <= 0:print('Blastoff!')else:print(n)countdown(n - 1)countdown(3)
如果n是0或负数, 它会输出单词'Blastoff!', 
其它情况下, 它会输出n, 并调用一个名为countdown的函数(它自己), 并传入实参n-1.
我们调用这个函数时会发生什么?countdown的执行从n=3开始, 因为n比0, 所有会输出3, 并接着调用自己...这时, countdown的执行又从n=2开始, 因为n比0, 所以会输出2, 并接着调用自己...这时, countdown的执行又从n=1开始, 因为n比0, 所以会输出1, 并接着调用自己...这时, countdown的执行又从n=0开始, 因为n不比0, 所以会输出单词'Blastoff!', 并返回.接收n=1的函数countdown返回.接收n=2的函数countdown返回.
接收n=3的函数countdown返回.然后就会到了__main__函数, 所以, 全部的输出如下:
# 运行工具窗口:
3
2
1
Blastoff!
调用自己的函数称为递归的(recursive)函数, 这个执行的过程叫作递归(recursion).
另外举一个例子, 我们可以写一个函数打印某个字符串n次.
def print_n(s, n):if n <= 0:returnprint(s)print_n(s, n - 1)print_n('s', 4)
如果n <= 0, return语句会直接退出当前函数. 执行流程会立即返回到调用者, 之后的语句不会运行.
函数另外的部分和countdown类似, 如果n大于0, 它会打印s并调用自己, 再进行n-1次显示s的操作.
所有输出行数是1 + (n - 1), 也就是n.
# 运行工具窗口显示:
s
s
s
s
对于这样简单的例子来说, 可以使用for循环会更容易.
当我们会在后面见到一些示例, 使用for循环很难写, 但使用递归则会很简单, 所以早早开始了解递归是件好事.
5.9 递归函数和栈图
3.10节中, 使用一个栈图来表示程序在进行函数调用时的状态, 同样的栈图, 可以用来帮助我们解释递归函数.
一个函数每次被调用时, Python会创建一个帧(function frame), 来包含函数的局部变量和参数.
对于递归函数, 栈上可能同时存在多个函数帧.
下图展示了countdown函数在n=3调用时的栈图.

2023-03-09_01739

和往常一样, 栈的顶端是__mian__的函数栈.
因为我们没有在__main__函数例新建任何变量或传入任何参数, 所有它是空的.4个countdown函数帧有不同的参数n, 最低端的栈, 其n=0, 被称为基准情形(base case).
因为它不再镜像递归调用, 所有后面没有其他函数帧了.
作为练习, 为函数print_n画一个栈图, 其调用的实参s='Hello'和n=2. 
然后写一个函数do_n, 接收一个函数对象和一个数字n作为形参, 他会调用给定的函数n次.

2023-03-09_01740

def print_hello(part):print(part)def do_n(func, n):if n <= 0:return do_n(func, n - 1)do_n(print_hello, 3)

2023-03-09_01741

5.10 无限递归
如果一个递归永远达不到基准情形, 则它会永远继续递归调用, 而程序也永远不停止.
这个现象被成为无限递归, 而它并不是个好主意, 下面是一个会引起无限递归的最简单函数:
def recurse():recurse()recurse()
大多数程序环境中, 无限递归的函数并不会真的永远执行, Python会在递归深度达到上限时报告一个出错消息:
Traceback (most recent call last):File "C:\Users\13600\PycharmProjects\test\test.py", line 5, in <module>recurse()File "C:\Users\13600\PycharmProjects\test\test.py", line 2, in recurserecurse()File "C:\Users\13600\PycharmProjects\test\test.py", line 2, in recurserecurse()File "C:\Users\13600\PycharmProjects\test\test.py", line 2, in recurserecurse()[Previous line repeated 996 more times]
RecursionError: maximum recursion depth exceeded.
[上一行重复996]递归错误:超过最大递归深度.
当这个错误发生时, 栈上已经有1000个recurse帧了(默认值为1000, 某些电脑可能只能达到99x层.)! 
如果你不小心写出了一个无线循环, 请复查自己的函数, 确认里面至少有一个基准情况不进行递归调用.
如果已经有了一个基准情形, 检查是否已经确保在运行时能达到它.
5.11 键盘输入
目前为止我们写过的程序都不能接收用户的输入, 它们只能每次做相同的事情.
Python提供了一个内置函数input来从键盘获取输入并等待用户输入一些东西.
当用户按下回车, 程序会恢复运行, 而且input则通过字符串的形式返回用户输入的内容.
在Python 2, 这个函数叫作raw_input.
>>> text = input()
# 输入下面的字符, 结束后按下回车.
Whate are you waiting for?
>>> text
'Whate are you waiting for?'
在从用户那里获得输入之前, 最好打印一个提示信息, 告诉用户希望他们输入什么.
input函数可以接受一个参数作为提示:
>>> name = input('What ... is your name?\n')
What ... is your name?
kid
>>> name
'kid'
提示信息最后的\n表示一个换行符, 它是会引起输出显示换行的特殊字符.
这也是为何用户的输入显示在提示信息的下一行的原因.
如果希望有户输入一个整数, 可以尝试将输入值转换为int:
# 什么 .. 是空载燕子的空速?
>>> pormpt = 'What ... is the airspeed velocity of an unladen swallow?\n'
>>> speed = input(pormpt)
42
>>> int(speed)
42
但如果用户输入不是数字的话, 会得到错误:
>>> speed = input(pormpt)
What ... is the airspeed velocity of an unladen swallow?
# '你是什么意思, 非洲燕子还是欧洲燕子?'
What do you mean, an African or a European swallow?
>>> int(speed)
Traceback (most recent call last):File "<stdin>", line 1, in <module>
ValueError: invalid literal for int() with base 10:
'What do you mean, an African or a European swallow?'
后面我们会看到如何处理这种错误.
5.12 调试
当发生语法错误和运行时错误时, 出错信息包含了大量的信息, 但由时候反而会信息过量, 最有用的信息是:
* 错误的类型;
* 发生错误的地方;
语法错误通常很容易定位, 但也有辣手之处. 空格问题引起的错误很难难处理, 
因为空格和制表符都是不可以见的, 我们已经习惯与忽略它们.
>>> x = 5
>>>  y =6File "<stdin>", line 1y =6
IndentationError: unexpected indent
这个例子中, 问题的原因是第二行多缩进了一个空格.
但出错消息指向的是y, 容易误导.
总的来说, 出错消息会告诉我们发生错误的地址, 
但真正发生的地方可能在更前面的代码中, 有时候甚至在前一行.
运行时错误也是如此, 假设你想要按照分贝来计算信噪比, 公式为:SBRdb = 10lg(Psignal / Pnoise).
在python中会这么写:
import mathsignal_power = 9
noise_power = 10
# 9 // 10 = 0
ratio = signal_power // noise_power
# 0 不能作为log10方法的参数.
decibels = 10 * math.log10(ratio)
print(decibels)
在运行这个程序时, 会得到一个异常:
Traceback (most recent call last):File "C:\Users\13600\PycharmProjects\test\test.py", line 6, in <module>decibels = 10 * math.log10(ratio)
ValueError: math domain error
出错的信息指向第五行, 但那一行其实没有什么错误, 要找到真正的错误, 可能要打印出ratio的值,
结果你会发现是0. 问题出在第四行, 这个是使用向下取整除法而不是浮点数除法.
你因该花一点时间认真阅读出错信息, 但不要认为出现消息上说的每一样都对.
5.13 术语表
向下取整除法(floor division): (//)表示的操作符, 用于将两个数相除, 并对结果进行向下取整-(靠近0取整), 得到整数结果.求模操作符(modulus operator): (%)表示的操作符, 用于两个整数求模, 返回两数相除的余数.布尔表达式(booleam expression): 一种表达式, 其值是True或False.关系操作符(relationnal operator): 用来表示两个操作对象的比较关系的操作符, 如下之一:==, !=, >, <, >=, <=.条件语句(conditional statement): 依照某些条件控制程序执行流程的语句.条件(condition): 条件语句中的布尔表达式, 由它决定执行哪一个分支.复合语句(compound statement): 一个包含语句头和函数体的语句.语句头以冒号(:)结尾, 语句体相对语句头缩进一层.分支(branch): 条件语句中的一个可能性分支语句段.条件链语句(chained conditional): 一种包含多个分支的条件语句.嵌套条件语句(nested conditional): 在其它条件语句的分支中出现的条件语句.返回语句(return statement): 导致一个函数立即结束并返回到调用者的语句.递归(recursion): 在当前函数中调用自己的过程.基准情形(base case): 递归函数中的一个条件分支, 里面不会再继续递归调用.无限递归(infinite recursion): 没有基准情形的递归, 或者永远无法达到基准情形的分支的递归调用.最终, 这种无限递归会导致运行时错误.
5.14 练习
1. 练习1
time模块提供了一个函数, 名字也叫time, 它能返回从'纪元'起到当前的格林尼治时间.
'纪元'其实在认为选作基准点的时间, 在UNIX系统中, 纪元时间点是197011.
>>> import time
>>> time.time()
1678371019.427301
编写一个脚本, 读写当前时间, 并转换为一天中的小时数, 分钟数, 秒数, 以及从纪元到现在的天数.
import timenow_time = time.time()
print(now_time)  # 1678372439.8636642
# 并转换为一天中的小时数, 分钟数, 秒数. 一天的秒数(60 * 60 * 24 = 86400)
seconds_per_day = 86400# 纪元到今天的天数
day = now_time // seconds_per_day
print(day)  # 19425 天, 53年...# 求余数, 不够整除的就是今天的时间(单位为秒)
today_seconds = now_time % seconds_per_day# 现在的小时, 整除3600秒
hours_seconds = 3600
hours = today_seconds // hours_seconds# 现在的时间, 中国属于是中八区加上8.
print(hours + 8)  # 22.0 # 现在的分钟, 整除3600秒
minute = (today_seconds - hours * hours_seconds) // 60
print(minute)  # 33.0 # 现在的秒数
now_seconds = (today_seconds - hours * hours_seconds) % 60
print(now_seconds)  # 59.86366415023804
2. 练习2
费马大定理是说对于任何大于2的n, 不存在任何正整数a, b和c能够满足: a**n + b**n = c**n.
1. 编写一个函数check_fermat, 接收4个形参(即a, b, c和n)并检查费马定理是否成力,如果n比2大并且满足a**n + b**n = c**n,则程序应当打印'天哪, 费马弄错了', 否则程序应当打印'不, 那么样不行'.
def check_fermat(a, b, c, n):num1 = a ** n + b * nnum2 = c ** nprint(num1, num2) if n > 2 and num1 == num2:print('天哪, 费马弄错了')else:print('不, 那样不行')check_fermat(a=1, b=2, c=5, n=3)
2. 编写一个函数, 提示用户输入a, b, c和n的值, 将它们转换为整数,并使用check_fermat来验证它们是否违背了费马定理.
def check_fermat(a, b, c, n):num1 = a ** n + b * nnum2 = c ** nprint(num1, num2)if n > 2 and num1 == num2:print('天哪, 费马弄错了')else:print('不, 那样不行')def input_num():a_str = input('提供参a的值>>>:')b_str = input('提供参b的值>>>:')c_str = input('提供参c的值>>>:')n_str = input('提供参n的值>>>:')a = int(a_str)b = int(b_str)c = int(c_str)n = int(n_str)check_fermat(a, b, c, n)input_num()
3. 练习3
如果给你3更木棍, 你可以将它们摆成一个三角形, 也可能不可以.
例如, 如果一根木棍的长度是12英寸, 而其它两根都只有1英寸, 那么你无法让短的木棍在中间相接.
对于任意三个长度, 有一个简单的测试可以让它们是否可以组成一个三角形:
如果其中任意一个长度的值大于其它两个长度的和, 则你不能组成三角形, 否则可以.
(如果任意一个长度等于第三个, 在这儿它们组成一个'退化'的三角形.)1. 编写一个函数is_triangle, 接收是三个参数, 并根据这组长度的木棍是否能组成三角形来打印'Yes''No'.
def is_triangle(x, y, z):# 任意两边相加, 大于或等于第三边, 则可以组成三角形.if x + y >= z and x + z >= y and y + z >= x:print('Yes')else:print('No')is_triangle(3, 4, 1)  # True
2. 编写一个函数提示用户输入3根木棍的长度, 将其转换为整型, 并使用is_triangle检查这些长度的木棍是否可以组成三角形.
def is_triangle(x, y, z):# 任意两边相加, 大于或等于第三边, 则可以组成三角形.if x + y >= z and x + z >= y and y + z >= x:print('Yes')else:print('No')def stick_length():a_str = input('输入第一条木棍的长度>>>:')b_str = input('输入第一条木棍的长度>>>:')c_str = input('输入第一条木棍的长度>>>:')a = int(a_str)b = int(b_str)c = int(c_str)is_triangle(a, b, c)stick_length()
4. 练习4
下面的程序的输出是什么? 泛化一个栈图来显示程序打印结果时的状态.
def recurse(n, s):if n == 0:print(s)  # 6else:recurse(n - 1, n + s)recurse(3, 0)

2023-03-10_01742

1. 如果像recurse(-1, 0)这样调用这个函数, 会发生什么?
recurse(-1, 0)调用, 永远无法达到基准情形, 程序会无限递归调用, 最终导致运行时错误:
递归错误: 比较中超过了最大递归深度.
2. 编写一段文档字符串, 向人解释清楚要使用这个函数需要知道的东西(并且不多写其它内容).
def recurse(n, s):"""函数递归调用n次, 当n=o时结束递归, 递归时, 计算加法运算 s = n + s.:param n: int, 值必须大于0.:param s: int:return:"""if n == 0:print(s)  # 6else:recurse(n - 1, n + s)recurse(4, 0)
5. 练习5
接下来的练习需要使用第4章描述的turtle模块.
阅读下面的函数, 并看看你能否能清楚它在做什么(参考第4章中的实例), 接着运行它, 看你的理解是否真确.
import turtlebob = turtle.Turtle()def draw(t, length, n):# 递归结束条件if n == 0:return# 角度为50angle = 50# 前进为 边长*nt.fd(length * n)# 左转50度t.lt(angle)# 递归调用draw(t, length, n - 1)# 右转100度t.rt(2 * angle)# 递归调用draw(t, length, n - 1)# 左转50度t.lt(angle)# 前进 边长*nt.bk(length * n)# turtle对象, 边长, 递归次数
draw(bob, length=5, n=5)turtle.mainloop()
6. 练习6
科赫曲线(Koch curve)是一个分形, 它看起来像下图(代码后面)所示.
要绘制一个长度为x的科赫曲线不只需要做:
* 1. 绘制为x/3的科赫曲线.
* 2. 向左转60.* 3. 绘制为x/3的科赫曲线.
* 4. 向右转120.* 5. 绘制为x/3的科赫曲线.
* 6. 向左转60.* 7. 绘制为x/3的科赫曲线.
当x比3小的时候例外: 在那种清理下, 你可u直接绘制一个长度为x的直线.
1. 编写一个函数koch, 接收一个Turtle对象以及长度x作为形参, 并使用Turtle对象绘制指定长度的科赫曲线.
import turtledef koch(t, x):"""绘制科赫曲线的函数.参数:t -- Turtle对象x -- 曲线的长度返回值:None"""# 基准情形.if x < 10:t.fd(x)returnkoch(t, x / 3)t.left(60)koch(t, x / 3)t.right(120)koch(t, x / 3)t.left(60)koch(t, x / 3)# 创建一个Turtle对象
bob = turtle.Turtle()# 绘制一个长度为100的Koch曲线
koch(bob, 100)
turtle.mainloop()

image-20230310012923697

2. 编写一个函数snowflake, 绘制三条科赫曲线, 组成一个雪花形状.
解答: https://github.com/AllenDowney/ThinkPython2/blob/master/code/koch.py
import turtledef koch(t, n):if n < 10:t.fd(n)returnm = n / 3koch(t, m)t.lt(60)koch(t, m)t.rt(120)koch(t, m)t.lt(60)koch(t, m)def snowflake(t, n):for i in range(3):koch(t, n)t.rt(120)bob = turtle.Turtle()bob.pu()
bob.goto(-150, 90)
bob.pd()
snowflake(bob, 300)turtle.mainloop()

image-20230310012814773

3. 科赫曲线而已用几种方法泛化. (看一眼就得了, 国外的网站, 访问不了的.)
查看: http://en.wikipedia.org/wiki/Koch_snowflake

image-20230310013428813

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Java | Leetcode Java题解之第150题逆波兰表达式求值

题目&#xff1a; 题解&#xff1a; class Solution {public int evalRPN(String[] tokens) {int n tokens.length;int[] stack new int[(n 1) / 2];int index -1;for (int i 0; i < n; i) {String token tokens[i];switch (token) {case "":index--;stack…

vi/vim使用命令

你是否在编辑文件时以为键盘坏了&#xff0c;为什么不能删除呢&#xff0c;为什么不能敲代码呢&#xff0c;等你初识vi&#xff0c;会觉得这个东西为什么设计得这么难用&#xff0c;这篇教程带你熟练得用上这款经典的工具 Vi 是在 Unix 系统上广泛使用的编辑器&#xff0c;Vim …

Unity与Js通信交互

目录 1.Js给Unity传递消息 2.Unity给Js传递消息 简介: Unity 与 JavaScript 通信交互是指在 Unity 项目中实现与 JavaScript 代码进行数据交换和功能调用的过程。 在 Unity 中&#xff0c;可以通过特定的接口和技术来与外部的 JavaScript 环境进行连接。这使得 Unity 能够利…

进击算法工程师深度学习课程

"进击算法工程师深度学习课程"旨在培养学员在深度学习领域的专业技能和实战经验。课程涵盖深度学习基础理论、神经网络架构、模型优化方法等内容&#xff0c;通过项目实践和算法实现&#xff0c;帮助学员掌握深度学习算法原理和应用&#xff0c;提升在算法工程师领域…

EasyExcel文件导出,出现有文件但没有数据的问题

一开始由于JDK版本过高&#xff0c;我用的17&#xff0c;一直excel没有数据&#xff0c;表头也没有&#xff0c;后来摸索了好久&#xff0c;找了资料也没有&#xff0c;后来改了代码后报了一个错误&#xff08;com.alibaba.excel.exception.ExcelGenerateException: java.lang.…

【抽代复习笔记】19-群(十三):奇偶置换、循环置换的几个定理及例题

定义&#xff1a; ①在Sn中&#xff0c;能够表示为奇数多个对换乘积的置换称为“奇置换”&#xff0c;能够表示为偶数多个对换乘积的置换称为“偶置换”&#xff1b; ②所有偶置换的集合记为An。 例1&#xff1a;&#xff08;1&#xff09;计算S1和S2中奇、偶置换的数目&…

数据中台-知识图谱平台

【数据分析小兵】专注数据中台产品领域,覆盖开发套件,包含数据集成、数据建模、数据开发、数据服务、数据可视化、数据治理相关产品以及相关行业的技术方案的分享。对数据中台产品想要体验、做二次开发、关注方案资料、做技术交流的朋友们&#xff0c;可以关注我。 1. 概述 随着…

ResNet——Deep Residual Learning for Image Recognition(论文阅读)

1.什么是ResNet ResNet是一种残差网络&#xff0c;咱们可以把它理解为一个子网络&#xff0c;这个子网络经过堆叠可以构成一个很深的网络。下面是ResNet的结构。 2.为什么要引入ResNet 理论上来说&#xff0c;堆叠神经网络的层数应该可以提升模型的精度。但是现实中真的是这…

智慧守护 畅游无忧——北斗应急呼叫柱,为景区安全加码

在大自然的怀抱中&#xff0c;中型及大型公园、景区以其壮丽风光吸引着成千上万的游客前来探索&#xff0c;成为了人们休闲娱乐的好去处。然而&#xff0c;广袤的区域、复杂的地形和分散的人流也给安全保障带来了前所未有的挑战。传统的巡逻方式难以覆盖每一个角落&#xff0c;…

【第六篇】SpringSecurity的权限管理

一、权限管理的实现 服务端的各种资源要被SpringSecurity的权限管理控制可以通过注解和标签两种方式来处理。 放开了相关的注解后在Controller中就可以使用相关的注解来控制了 JSR250注解 /*** JSR250*/ @Controller @RequestMapping("/user") public class UserC…

物理隔离后数据怎么导入和导出?安全U盘一键解决

政府单位、军工和科研所、航空航天企业、金融机构、医疗单位、电力企业、生物制药实验室等企业及单位&#xff0c;因研发和生产过程、或日常经营中涉及大量敏感信息和技术&#xff0c;需要通过物理隔离来确保网络的安全性。因此&#xff0c;多采用物理隔离的方式进行网络建设。…

前端 CSS 经典:在 Vue3 中使用渐进式图片

1. 什么是渐进式图片 当我们网站会加载很多图片的时候&#xff0c;有些图片尺寸很大&#xff0c;加载就会很慢&#xff0c;会导致页面长时间陷入白屏状态&#xff0c;用户体验很不好。所以可以使用渐进式图片&#xff0c;先给用户展示模糊图&#xff0c;这些图尺寸小&#xff…

django学习入门系列之第二点《浏览器能识别的标签3》

文章目录 列表表格往期回顾 列表 无序列表 <!-- <ul </ul> 无序列表 --> <ul><li> 内容1 </li><li> 内容2 </li><li> 内容3 </li><li> 内容4 </li> </ul>有序列表 <!-- <ol> &…

WordPress、Typecho 站点如何让 CloudFlare 缓存加速

众所周知 WordPress、Typecho 都是著名动态博客站点(一个最简单的判断依据就是都要依赖结合数据库),这类站点在 CDN 缓存上都有一个致命的缓存弊端就是动静态请求的区分,理论上要让 CDN 绕过所有的动态请求,缓存所有的静态请求,否则就会造成前端登录和非登录状态的混乱,…

小程序制作成本是多少?揭秘隐藏费用!

在日常生活中&#xff0c;有很多小程序&#xff0c;其中我们最熟悉的是微信小程序&#xff0c;所以小程序对我们每个人来说并不陌生。那么&#xff0c;你知道制作一个小程序要花多少钱吗&#xff1f;制作小程序的成本是多少&#xff1f;今天&#xff0c;本文将带领您揭示小程序…

禁渔期水域监管:EasyCVR视频智能监控方案

一、背景与需求分析 根据农业部印发的《中国渔政亮剑2024系列专项执法行动方案》&#xff0c;我国将持续推进长江十年禁渔、海洋伏季休渔、黄河等内陆重点水域禁渔等专项行动。根据四川省相关规定&#xff0c;每年3月1日至6月30日为禁渔期&#xff0c;在此期间&#xff0c;四川…

颠覆与创新:探寻Facebook未来的发展路径

Facebook&#xff0c;这个曾经引领社交网络革命的巨头&#xff0c;在如今竞争激烈的科技市场中&#xff0c;正面临着前所未有的挑战和机遇。如何在不断变化的数字世界中保持竞争力&#xff0c;成为业界领先者&#xff0c;这是摆在Facebook面前的重要课题。本文将探寻Facebook未…

单位经常要你加班却不发加班费,你想到这一招没有?

单位经常要你加班却不发加班费&#xff0c;你想到这一招没有&#xff1f; 你也许经常在忙碌的工作和繁重的加班中度过&#xff0c;然而&#xff0c;却从未得到过应有的加班费。但你又不想离开这个单位&#xff0c;或许单位的工作环境人性化&#xff0c;同事之间的关系融洽&…

【新手必看】修复Windows11蓝牙连接问题的7个方法!

在Windows11电脑操作中&#xff0c;用户经常会到蓝牙功能&#xff0c;如果蓝牙连接出现问题了&#xff0c;就会导致用户无法成功使用蓝牙。但是&#xff0c;许多新手用户不清楚要怎么操作才能解决蓝牙连接问题&#xff1f;会有不同的因素导致蓝牙连接出现问题&#xff0c;接下来…

3d交互式场景在线编辑平台的好处

在数字化教学的新时代&#xff0c;我们为您带来了革命性的产品——VR全景展示搭建编辑器。它将传统的教学方式升级为三维模式&#xff0c;让课程训练更加真实生动&#xff0c;为您带来前所未有的学习体验。 VR全景展示搭建编辑器不仅支持视频录播、PDF、图文等多种内容承载方式…