算法
一丶时间复杂度
时间复杂度排序
O(1 ) < O(logn) < O(n) < O(nlogn) < O(n^2 ) < O(n^3 ) < O(2 ^n) < O(n!) < O(n^n)
二丶数据结构
# 概念:
对数据(基本数据类型(int ,float ,char ))的组织方式被称作数据结构. 数据结构解决的是一组数据如何进行保存.
三丶python测试代码执行的时长
timeit模块:
原型为:class timeit .Timer(stmt='pass' ,setup='pass' )。
stmt参数:表示即将进行测试的代码块语句。
setup:运行代码块语句时所需要的设置。
timeit函数:timeit.Timer.timeit(number=100000 ),该函数返回代码块语句执行number次的平均耗时。
from timeit import Timer
def test01 ():
alist = []
for i in range (1000 ):
alist.append(i)
return alist
def test02 ():
alist = []
for i in range (1000 ):
alist.insert(0 ,i)
return alist
def test03 ():
alist = []
for i in range (1000 ):
alist += [i]
return alist
def test04 ():
alist = list (range (1000 ))
return alist
if __name__=='__main__' :
t=Timer('test01()' ,'from __main__ import test01' )
print (t.timeit(1000 ))
t1=Timer('test02()' ,'from __main__ import test02' )
print (t1.timeit(1000 ))
四丶栈
#### 使用python 类 实现栈
# 需求:
Stack () 创建一个空的新栈。 它不需要参数,并返回一个空栈。
push (item)将一个新项添加到栈的顶部。它需要 item 做参数并不返回任何内容。
pop () 从栈中删除顶部项。它不需要参数并返回 item 。栈被修改。
peek () 从栈返回顶部项,但不会删除它。不需要参数。 不修改栈。
isEmpty () 测试栈是否为空。不需要参数,并返回布尔值。
size () 返回栈中的 item 数量。不需要参数,并返回一个整数。
class Stack ():
def __init__ (self ):
self.items=[]
def push (self,item ):
'''入栈'''
return self.items.append(item)
def pop (self ):
'''出栈'''
return self.items.pop()
def peek (self ):
'获取栈顶元素的"索引"位置'
return len (self.items)-1
def isEmpty (self ):
'''判断是否是空栈'''
return self.items==[]
def size (self ):
'''返回栈的大小'''
return len (self.items)
五丶队列
Queue() 创建一个空的新队列。 它不需要参数,并返回一个空队列。
enqueue(item) 将新项添加到队尾。 它需要 item 作为参数,并不返回任何内容。
dequeue() 从队首移除项。它不需要参数并返回 item。 队列被修改。
isEmpty() 查看队列是否为空。它不需要参数,并返回布尔值。
size() 返回队列中的项数。它不需要参数,并返回一个整数。
class Queue ():
def __init__ (self ):
self.items=[]
def enqueue (self,item ):
'''入队'''
return self.items.append(item)
def dequeue (self ):
'''出队'''
return self.items.pop(0 )
def isEmpty (self ):
'''判断是否是空队'''
return self.items==[]
def size (self ):
'''返回队的大小'''
return len (self.items)
烫手山芋游戏介绍:6 个孩子围城一个圈,排列顺序孩子们自己指定。第一个孩子手里有一个烫手的山芋,需要在计时器计时1 秒后将山芋传递给下一个孩子,依次类推。规则是,在计时器每计时7 秒时,手里有山芋的孩子退出游戏。该游戏直到剩下一个孩子时结束,最后剩下的孩子获胜。请使用队列实现该游戏策略,排在第几个位置最终会获胜。
class Queue ():
def __init__ (self ):
self.items = []
def enqueue (self,item ):
self.items.insert(0 ,item)
def dequeue (self ):
return self.items.pop()
def size (self ):
return len (self.items)
kids = ['A' ,'B' ,'C' ,'D' ,'E' ,'F' ]
q=Queue()
for kid in kids:
q.enqueue(kid)
while q.size()>1 :
for i in range (6 ):
kid=q.dequeue()
q.enqueue(kid)
q.dequque()
print (q.dequque())
六丶双端队列
Deque() 创建一个空的新 deque。它不需要参数,并返回空的 deque。
addFront(item) 将一个新项添加到 deque 的首部。它需要 item 参数 并不返回任何内容。
addRear(item) 将一个新项添加到 deque 的尾部。它需要 item 参数并不返回任何内容。
removeFront() 从 deque 中删除首项。它不需要参数并返回 item。deque 被修改。
removeRear() 从 deque 中删除尾项。它不需要参数并返回 item。deque 被修改。
isEmpty() 测试 deque 是否为空。它不需要参数,并返回布尔值。
size() 返回 deque 中的项数。它不需要参数,并返回一个整数。
class Deque ():
def __init__ (self ):
self.items=[]
def addFront (self,item ):
return self.items.insert(0 ,item)
def addRear (self ):
return self.items.append(item)
def removeFront (self ):
return self.items.pop(0 )
def removeRear (self ):
return self.items.pop()
def isEmpty (self ):
return self.items == []
def size (self ):
return len (self.items)
q = Deque()
s = 'radar'
for i in s:
q.addFront(i)
while q.size() > 1:
if q.removeFront() != q.removeRear():
print ('不是回文' )
break
else :
print ('是回文' )
七丶内存
变量就是引用。变量其实表示的就是计算机中的一块内存。(即:变量起始就是内存地址)
bit:位
byte:字节
kb:1020 字节
mb
gb
tb
作用:寻址
八丶顺序表
九丶链表
1. 相对于顺序表,链表结构可以充分利用计算机内存空间,实现灵活的内存动态管理且进行扩充时不需要进行数据搬迁。
2. 链表(Linked list )是一种常见的基础数据结构,是一种线性表,但是不像顺序表一样连续存储数据,而是每一个结点(数据存储单元)里存放下一个结点的信息(即地址)
is_empty():链表是否为空
length():链表长度
travel():遍历整个链表
add(item):链表头部添加元素
append(item):链表尾部添加元素
insert(pos, item):指定位置添加元素
remove(item):删除节点
search(item):查找节点是否存在
class Node ():
def __init__ (self,item ):
self.item=item
self.next =None
class Link ():
def __init__ (self ):
self.head=None
def add (self,item ):
' 给链表头 添加节点'
node=Node(item)
node.next =self.head
self.head=node
def append (self,item ):
'链表尾部添加元素'
node=Node(item)
if self.head==None :
retrun self.head=node
cur = self.head
pre=None
while cur:
pre=cur
cur=cur.next
pre.next =node
def search (self,item ):
find=False
cur=self.head
while cur:
if cur.item==item:
find=True
retrun
cur=cur.next
return find
def insert (self,pos,item ):
node=Node(item)
if pos==0 :
self.add(item)
cur=self.head
pre=None
for i in range (pos)
pre=cur
cur=cur.next
pre.next =node
node.next =cur
def remove (self,item ):
cur=self.head
pre=None
if self.head.item==item:
self.head=self.head.next
return
while cur:
if cur.item==item:
pre.next =cur.next
return
pre=cur
cur=cur.next
def is_empty (self ):
retrun self.head==None
def length (self ):
count=0
cur = self.head
while cur:
count+=1
cur=cur.next
return cur
def travel (self ):
'遍历'
cur = self.head
while cur:
print (cur)
cur=cur.next
return cur
十丶二分查找
def search (data,item ):
start=0
end=len (data)-1
while start <= end:
mid=(start+end)//2
if data[mid]==item:
return True
elif data[mid]>item:
end=mid-1
elif data[mid]<item:
start=mid+1
data=[i for i in range (1 , 10000 )]
print (search(data,33 ))
十一丶二叉树排序
- 每一颗子树根节点可以作为另一颗子树的左右叶子节点
- 每一个根节点都可以做为一颗子树的根节点
class Node ():
def __init (self,item ):
self.item=item
self.left=None
self.right=None
class Tree ():
def __init__ (self ):
self.root=None
def insert (self,item ):
node=Node(item)
if self.root==None :
self.root=node
return
cur=self.root
queue=[cur]
while True :
leaf=self.queue.pop(0 )
if leaf.left==None :
leaf.left=node
break
else :
queue.append(leaf.left)
if leaf.right==None :
leaf.right=node
break
else :
queue.append(leaf.right)
def travel (self ):
cur=self.root
queue=[cur]
while queue:
leaf=queue.pop(0 )
print (leaf.item)
if leaf.left!=None :
queue.append(leaf.left)
if leaf.right!=None :
queue.append(leaf.right)
def front_sort (self,root ):
if root==None :
return
print (root.item)
self.front_sort(root.left)
self.front_sort(root.right)
def middle_sort (self,root ):
if root==None :
return
self.middle_sort(root.left)
print (root.item)
self.middle_sort(root.right)
def after_sort (self,root ):
if root==None :
return
self.after_sort(root.left)
self.after_sort(root.right)
print (root.item)
class Node ():
def __init__ (self,item ):
self.item=item
self.left=None
self.right=None
class SortTree ():
def __init__ (self ):
self.root=None
def inert (self,item ):
node=Node(item)
if self.root==None :
self.root=node
cur=self.root
while True :
if cur.left>item:
if cur.left==None :
cur.left=node
return
else :
cur=cur.left
else :
if cur.right==None :
cur.right=None :
return
else :
cur=cur.right
十二丶排序算法
def sort (data ):
for i in range (len (data) - 1 ):
for j in range (len (data) - 1 - i):
if data[j] > data[j + 1 ]:
data[j], data[j + 1 ] = data[j + 1 ], data[j]
return data
def sort (data ):
for i in range (len (data)-1 ):
max_index=0
for j in range (len (data)-1 -i):
if data[max_index]<data[j+1 ]:
max_index=j+1
data[max_index],data[len (data)-1 -i]=data[len (data)-1 -i],data[max_index]
return data
def sort (data ):
for i in range (1 ,len (data)):
while i >0 :
if data[i]>data[i-1 ]:
data[i],data[i-1 ]=data[i-1 ],data[i]
i-=1
else :
break
return data
def sort (data ):
first=0
end=len (data)-1
def sort (data ):
gap=len (data)//2
while gap>0 :
for i in range (1 ,len (data)):
while i>0 :
if data[i]<data[i-gap]:
data[i],data[i - gap]=data[i-gap],data[i]
i-=gap
else :
break
gap//=2
return data
data=[8 ,5 ,2 ,1 ,3 ,7 ,6 ,4 ,9 ]
print (sort(data))
设定一个基数mid,基数的初始值就是乱序序列中的第一个元素值
将除了基数剩下所有的数值跟基数做比较。比较之后需要达到的一个效果就是:
基数左侧放置的都是比它小的数
基数右侧放置的都是比它大的数
def sort (data,start,end ):
low=start
high=end
if low>high:
return
mid=data[start]
while low<high:
while low<high:
if data[high]<mid:
data[low]=data[high]
break
else :
high-=1
while low<high:
if data[low]<mid:
low+=1
else :
data[high]=data[low]
break
if low==high:
data[high]=mid
sort(data,start,high-1 )
sort(data,high+1 ,end)
return data
alist = [6 ,1 , 2 , 7 , 9 , 3 , 4 , 5 , 10 , 8 ]
print (sort(alist,0 ,len (alist)-1 ))
六丶堆排序
def sift (data,low,high ):
i =low
j=2 *i+1
tmp=data[i]
while j<=high:
if j<high and data[j]<data[j+1 ]
j+=1
if data[j] > tmp :
data[i]=data[j]
i=j
j=2 *i+1
else :
break
data[i]=tmp
def heap_sort (data ):
n=len (data)
for i in range (n//2 -1 ,-1 ,-1 ):
sift(data,i,n-1 )
for j in range (n-1 ,-1 ,-1 ):
data[0 ],data[j]=data[j],data[0 ]
sift(data,0 ,j-1 )
def megre (li,low,mid,high )
i=0
j=mid+1
li_data=[]
while i<=mid and j<=high:
if li[i]<li[j]:
li_data.append(li[i])
i+=1
else :
li_data.append(li[j])
j+=1
while i<=mid:
li_data.append(li[i])
i+=1
while j<=hight:
li_data.append(li[j])
j+=1
li[low:hiht+1 ]=li_data
def megre_sort (li,low,high ):
if low <high:
mid=(low+high)//2
megre_sort(li,low,mid)
megre_sort(li,mid+1 ,high)
megre(li,low,mid,high)
#
# 三种算法的时间复杂度都是O(nlogn)
# 运行时间:快速<归并<堆排
# 特点:
# 快速排序: 极端情况下的效率极低
# 归并排序:需要额外的内存,当数据量大时,不得不考虑内存的空间
# 堆排序: 速度相对较慢,但是稳定
def insertion_sort (arr ):
for i in range (1 , len (arr)):
current = arr[i]
print ('current:' , current)
pre_index = i - 1
print ('pre_index:' , pre_index)
while pre_index >= 0 and arr[pre_index] > current:
print ('数据值是:' , arr[pre_index])
arr[pre_index + 1 ] = arr[pre_index]
pre_index -= 1
print ('变化前:' , arr)
print (arr[pre_index + 1 ])
arr[pre_index + 1 ] = current
print ('变化后:' , arr)
print ('\n' )
return arr
if __name__ == '__main__' :
data = [9 , 2 , 3 , 1 , 5 , 8 , 4 ]
print (insertion_sort(data))
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?