遗传算法GA原理详解及实例应用 附Python代码

article/2025/11/7 0:06:13

遗传算法GA

遗传算法(Genetic Algorithm, GA)是模拟达尔文生物进化论的自然选择和遗传学机理的生物进化过程的计算模型,是一种通过模拟自然进化过程搜索最优解的方法。

生物在自然界中的生存繁衍,显示了其对自然环境的优异的自适应能力。遗传算法所借鉴的生物学基础就是生物的进化和遗传。

生物在其延续生存的过程中,逐渐适应其生存环境,使得其品质不断得到改良,这种生命现象称为进化(Evolution)。生物的进化是以集团的形式共同进行的,这样的一个团体称为群体(Population),组成群体的单个生物称为个体(Individual),每个个体对其生存环境都有不同的适应能力,这种适应能力称为个体的适应度(Fitness)。按照达尔文的讲化论,那些具有较强适应环境变化能力的生物个体具有更高的生存能力容易存活下来,并有较多的机会产生后代;相反,具有较低生存能力的个体则被淘汰,或者产生后代的机会越来越少,直至消亡。---->自然选择,适者生存

生物的遗传和变异

生物从其亲代继承特性或性状,这种生命现象就称为遗传(Heredity)。控制生物遗传的物质单元称为基因(Gene),它是有遗传效应的DNA片段。

  • 细胞在分裂时,遗传物质DNA通过复制(Reproduction)而转移到新产生的细胞中,新细胞就继承了旧细胞的基因。

  • 有性生物在繁殖下一代时,两个同源染色体之间遗过**交叉(Crossover)**而重组。

  • 在进行复制时,可能以很小的概率产生某些差错,从而使DNA发生某种变异(Mutation),产生出新的染色体。

生物进化的本质:染色体的改变和改进===>生物进化过程本质是一种优化过程

在这里插入图片描述

遗传算法的基本思想

遗传算法是根据问题的目标函数构造一个适值函数(Fitness Function),对一个由多个解(每个解对应一个染色体)构成的种群进行评估、遗传运算、选择,经多代繁殖,获得适应值最好的个体作为问题的最优解。具体如下:

  1. 产生一个初始种群
  2. 根据问题的目标函数构造Fitness Function 适值函数
  3. 根据适应值的好坏不断选择和繁殖
  4. 若干代后得到适应值最好的个体即为最优解

遗传算法的构成要素

  • 种群和种群大小

    -种群由染色体构成,每个个体就是一个染色体,每个染色体对应着问题的一个解。一般设为100-1000

  • 编码方法

    正确的对染色体进行编码来表示问题的解释遗传算法的基础工作,也是最重要的工作 一般是二进制编码、有意义的实数、符号等等

  • 遗传算子

    • 包括交叉变异,是遗传算法的精髓

    • 双亲染色体是否进行交叉由交叉率进行控制。交叉率为各代中交叉产生的后代数与种群中个体数的比

    • 染色体是否进行变异由变异率来进行控制。变异率为种群中变异基因数在总基因数中的百分比

      变异率的选择很重要,太大会将上一代的最优解杀死

  • 选择策略

    • 选择策略是从当前种群中选择适应值高的个体以生成交配池的过程。使用最多的是正比选择策略

      适应值大=>生存至下一代的概率更大

  • 停止准则

    一般为最大迭代次数为停止准则

基本遗传算法的运算过程

  1. 初始种群的产生

  2. 编码

    将实际问题转化为计算机能够“看懂”的代码。(比如二进制码) ==>编码方法

  3. 选择(复制):

    根据各个个体的适应度,按照一定的规则或方法,从第t代群体P(t) 中选择出一些优良的个体遗传到下一代群体**P(t+1)**中; ==> 筛选方法

  4. 交叉:

    将群体P(t)内的各个个体随机搭配成对,对每一对个体,以交叉概率交换它们之间的部分染色体;

  5. 变异:

    对群体P(t)中的每一个个体,以变异概率改变某一个或某一些基因座上的基因值为其他基因值。

  6. 检验:

    是否已达到要求或达到遗传代数。

  7. 结束:

    达到目标要求或达到遗传代数。

在这里插入图片描述

编码

编码是应用遗传算法时要解决的首要问题,也是设计遗传算法的一个关键步骤。编码方法在很大程度上决定了如何进行群体的遗传进化运算以及遗传进化运算的效率。

初始种群:基本遗传算法(SGA)采用随机方法生成若干个个体的集合,该集合称为初始种群。初始种群中个体的数量称为种群规模。

  • 二进制编码方法 [最常见]

    • 最大最小值
    • 背包问题
    • 指派问题
  • 浮点数编码方法

  • 符号编码方法

    • 旅行商问题TP

      约束问题:每个城市在一次路线只能经过一次

二进制编码

优点:

  • 编码、解码操作简单易行;
  • 交叉、变异等遗传操作便于实现;
  • 符合最小字符集编码原则;
  • 便于利用模式定理对算法进行理论分析。

缺点:

  • 对于一些连续函数的优化问题,由于其随机性使得其局部搜索能力较差。如对于一些高精度的问题,当解迫近于最优解后,由于其变异后表现型变化很大,不连续,所以会远离最优解,达不到稳定。

适应度函数

适应度函数用于评价个体的适应度。===>适应度越高,越接近最优解。

最优化问题可分为两大类,一类为求目标函数的全局最大值,另一类为求目标函数的全局最小值。由目标函数值 f(x) 到搜索空间中对应个体的适应度函数值F(x)的转换,对于求最大值的问题,作下述转换:

在这里插入图片描述

初始群体选取

初始群体中的个体是随机产生的。

方法:

​ a)根据问题固有知识,设法把握最优解所占空间在整个问题空间中的分布范围,然后,在此分布范围内设定初始群体。

​ b)先随机生成一定数目的个体,然后从中挑出最好的个体加到初始群体中。这种过程不断迭代,直到初始群体中个体数达到了预先确定的规模。

选择

从群体中选择优胜的个体,淘汰劣质个体的操作。选择的目的是把优化的个体(或解)直接遗传到下一代或通过配对交叉产生新的个体再遗传到下一代。选择操作是建立在群体中个体的适应度评估基础上的。

常用选择算子:

  • 轮盘赌选择法[最常用]

  • 适应度比例方法

  • 随机遍历抽样法

  • 局部选择法

轮盘赌选择法

想象有一个轮盘,现在我们将它分割成 m 个部分,这里的 m 代表我们总体中染色体的个数。每条染色体在轮盘上占有的区域面积将根据适应度分数成比例表达出来。

比如有如下四个染色体及其适应度信息:

在这里插入图片描述

基于上图中的值,我们建立如下「轮盘」。

在这里插入图片描述

轮盘赌选择又称比例选择算子,其基本思想是:各个个体被选中的概率与其适应度函数值大小成正比。

设群体大小为N,个体xi 的适应度为 f(xi),则个体xi的选择概率为:

在这里插入图片描述

轮盘赌选择法模拟:

  1. 在[0, 1]内产生一个均匀分布的随机数r。
  2. r≤q1,则染色体x1被选中。
  3. qk-1<r≤qk(2≤k≤N), 则染色体xk被选中。
  4. 其中的qi称为染色体xi (i=1, 2, …, n)的积累概率

在这里插入图片描述

简单的例子:

四个染色体二进制编码: s 1 = 13 ( 01101 ) , s 2 = 24 ( 11000 ) , s 3 = 8 ( 01000 ) , s 4 = 19 ( 10011 ) s_1= 13 (01101), s_2= 24 (11000), s_3= 8 (01000),s_4= 19 (10011) s1=13(01101)s2=24(11000)s3=8(01000)s4=19(10011)

假定适应度为 f ( s ) = s 2 f(s)=s^2 f(s)=s2 ,则 f ( s 1 ) = 1 3 2 = 169 , f ( s 2 ) = 2 4 2 = 576 , f ( s 3 ) = 8 2 = 64 , f ( s 4 ) = 1 9 2 = 361 f (s_1) = 13^2 = 169,f (s_2) = 24^2 = 576,f (s_3) = 8^2 = 64,f (s_4) = 19^2 = 361 f(s1)=132=169f(s2)=242=576f(s3)=82=64f(s4)=192=361

在这里插入图片描述

▸例如设从区间[0, 1]中产生4个随机数:

r1 = 0.450126, r2 = 0.110347, r3 = 0.572496, r4 = 0.98503

在这里插入图片描述

交叉

交叉运算,是指对两个相互配对的染色体依据交叉概率 Pc 按某种方式相互交换其部分基因,从而形成两个新的个体。

  • 单点交叉算法

    它是指在个体编码串中只随机设置一个交叉点, 然后在该点相互交换两个配对个体的部分染色体。

在这里插入图片描述

  • 双点交叉

    指在个体编码串中随机设置了二个交叉点,然后再进行部分基因交换。

在这里插入图片描述

  • 多点交叉

    指在个体编码串中随机设置多个交叉点,然后进行基因交换。多点交叉又称为广义交叉。

变异

遗传算法中使用变异算子主要有以下两个目的:

  • 改善遗传算法的局部搜索能力。
  • 维持群体的多样性,防止出现早熟(可以理解为局部最优解)现象。

变异算子:

  • 基本位变异:对个体编码串中以变异概率、随机指定的某一位或某几位仅因座上的值做变异运算。

在这里插入图片描述

  • 均匀变异:分别用符合某一范围内均匀分布的随机数,以某一较小的概率来替换个体编码串中各个基因座上的原有基因值。(特别适用于在算法的初级运行阶段)
均匀变异

•依次指定个体编码串中的每个基因座为变异点。

•对每一个变异点,以变异概率pm从对应基因的取值范围内取一随机数来替代原有基因值。

比如说:假设有一个体为X=x1x2…xk…xn, 若xk为变异点,其取值范围为[Ukmin,Ukmax], 在该点对个体X进行均匀变异操作后,可得到一个新的个体X=x1x2…xk’…xn, 其中变异点的新基因值是: xk’ = Ukmin + r · (Ukmax – Ukmin)式中,r 为[0, 1] 范围内符合均匀概率分布的一个随机数。

终止

遗传算法是一个反复迭代的过程,每次选代期间,要执行适应度计算、复制、交叉、变异等操作,直至满足终止条件。

终止方法:

  1. 规定最大迭代次数
  2. 规定最小偏差
  3. 观察适应度函数变化趋势

实例

例:求下述二元函数的最大值:
f ( x 1 , x 2 ) = x 1 2 + x 2 2 f(x_1,x_2)=x_1^2+x_2^2 f(x1,x2)=x12+x22
其中:
x 1 ∈ { 1 , 2 , 3 , 4 , 5 , 6 , 7 } x_1 \in \{1,2,3,4,5,6,7\} x1{1,2,3,4,5,6,7}

x 2 ∈ { 1 , 2 , 3 , 4 , 5 , 6 , 7 } x_2 \in \{1,2,3,4,5,6,7\} x2{1,2,3,4,5,6,7}

编码:

​ 因x1, x2 为 0 ~ 7之间的整数,所以分别用3位无符号二进制整数来表示,将它们连接在一起所组成的6位无符号二进制数就形成了个体的基因型,表示一个可行解。

例如,基因型X=101110所对应的表现型是:x=[56]。

初始种群产生:

​ 假设随机生成种群:011101,101011,011100,111001

适应度计算:

​ 遗传算法中以个体适应度的大小来评定各个个体的优劣程度,从而决定其遗传机会的大小。本例中,目标函数总取非负值,并且是以求函数最大值为优化目标,故可直接 利用目标函数值作为个体的适应度。

选择运算:

把当前群体中适应度较高的个体按某种规则或模型遗传到下一代群体中。

具体操作过程:

​ -先计算出群体中所有个体的适应度的总和
∑ i = 1 M f i ( i = 1.2 , … , M ) \sum_{i=1}^{M}f_i ( i=1.2,…,M ) i=1Mfi(i=1.2,,M)

​ -其次计算出每个个体的相对适应度的大小 f i / ∑ f i f_i / \sum f_i fi/fi ,它即为每个个体被遗传到下一代群体中的概率;

​ -每个概率值组成一个区域,全部概率值之和为1;

​ -最后再产生一个0到1之间的随机数,依据该随机数出现在上述哪一个概率区域内来确定各个个体被选中的次数。

在这里插入图片描述

交叉运算:

•先对群体进行随机配对;

•其次随机设置交叉点位置;

•最后再相互交换配对染色体之间的部分基因

在这里插入图片描述

变异运算:

​ 变异运算是对个体的某一个或某一些基因座上的基因值按某一较小的概率进行改变,它也是产生新个体的一种操作方法。

​ •首先确定出各个个体的基因变异位置,下表所示为随机产生的变异点位置,其中的数字表示变异点设置在该基因座处;

​ •然后依照某一概率将变异点的原有基因值取反。

在这里插入图片描述

经过选择,交叉,变异后,便可以得到新一代群体p(t+1)如下:

在这里插入图片描述
下面附上一个python版代码,具体注释已经加上:

import numpy as np
import matplotlib.pyplot as plt
from matplotlib import cm
from mpl_toolkits.mplot3d import Axes3D#染色体长度
DNA_SIZE = 24
#种群规模
POP_SIZE = 200
#交叉率 一般在0.6~0.9之间
CROSSOVER_RATE = 0.8
#变异率 一般小于0.1
MUTATION_RATE = 0.005
#种群迭代次数
N_GENERATIONS = 200
#自变量x和y的范围
X_BOUND = [-3, 3]
Y_BOUND = [-3, 3]GET_MAX = 0#定义函数
def F(x, y):return x ** 2 + y ** 2#获取最大适应度
def get_Maxfitness(pop):x, y = translateDNA(pop)pred = F(x, y)# 减去最小的适应度是为了防止适应度出现负数,通过这一步fitness的范围为[0, np.max(pred)-np.min(pred)],最后在加上一个很小的数防止出现为0的适应度return (pred - np.min(pred)) + 1e-3    #np.min(pred) 获得pred中的最小值 相减是为了获得非负数 加上一个很小的数防止出现为0的适应度#获取最小适应度
def get_Minfitness(pop):x, y = translateDNA(pop)pred = F(x, y)#减去最大值后fitness范围:[np.min(pred) - np.max(pred),0] 加上-号后范围为[0, np.max(pred) - np.min(pred)]   加上一个很小的数防止出现为0的适应度return -(pred - np.max(pred)) + 1e-3def translateDNA(pop):  # pop表示种群矩阵,一行表示一个二进制编码表示的DNA,矩阵的行数为种群数目#友情提示:pop是二维的哦~x_pop = pop[:, 1::2]  # 奇数列表示Xy_pop = pop[:, ::2]  # 偶数列表示y# pop:(POP_SIZE,DNA_SIZE)*(DNA_SIZE,1) --> (POP_SIZE,1)     dot() 矩阵乘法计算x = x_pop.dot(2 ** np.arange(DNA_SIZE)[::-1]) / float(2 ** DNA_SIZE - 1) * (X_BOUND[1] - X_BOUND[0]) + X_BOUND[0]y = y_pop.dot(2 ** np.arange(DNA_SIZE)[::-1]) / float(2 ** DNA_SIZE - 1) * (Y_BOUND[1] - Y_BOUND[0]) + Y_BOUND[0]#返回的是x与y染色体的实数值(解码值)return x, ydef crossover_and_mutation(pop, CROSSOVER_RATE=0.8):new_pop = []for father in pop:  # 遍历种群中的每一个个体,将该个体作为父亲child = father  # 孩子先得到父亲的全部基因if np.random.rand() < CROSSOVER_RATE:  # 产生一个0~1随机值,如果小于0.8则交叉mother = pop[np.random.randint(POP_SIZE)]  # 再种群中选择另一个个体,并将该个体作为母亲cross_points = np.random.randint(low=0, high=DNA_SIZE * 2)  # 随机产生交叉的点 [low, high)child[cross_points:] = mother[cross_points:]  # 孩子得到位于交叉点后的母亲的基因mutation(child)  # 后代变异new_pop.append(child) #加入下一代种群return new_pop #返回新一代种群#变异
def mutation(child, MUTATION_RATE=0.003):if np.random.rand() < MUTATION_RATE:  # 以MUTATION_RATE的概率进行变异mutate_point = np.random.randint(low=0, high=DNA_SIZE * 2)  # 随机产生一个实数,代表要变异基因的位置child[mutate_point] = child[mutate_point] ^ 1  # 将变异点的二进制为反转def select(pop, fitness):  # nature selection wrt pop's fitnessidx = np.random.choice(np.arange(POP_SIZE), size=POP_SIZE, replace=True,p=(fitness) / (fitness.sum()))'''介绍以下choice方法的参数:numpy.random.choice(a, size=None, replace=True, p=None)#从a(只要是ndarray都可以,但必须是一维的)中随机抽取数字,并组成指定大小(size)的数组#replace:True表示可以取相同数字,False表示不可以取相同数字#数组p:与数组a相对应,表示取数组a中每个元素的概率,默认为选取每个元素的概率相同。也就是说,从种群中根据适应度函数的大小为挑选概率,挑选POP_SIZE个元素作为下一代'''return pop[idx]def print_info(pop):if GET_MAX == 1:fitness = get_Maxfitness(pop)else:fitness = get_Minfitness(pop)#获取适应度最大的下标索引max_fitness_index = np.argmax(fitness)print("max_fitness:", fitness[max_fitness_index])x, y = translateDNA(pop)print("最优的基因型:", pop[max_fitness_index])print("(x, y):", (x[max_fitness_index], y[max_fitness_index]))def plot_3d(ax):X = np.linspace(*X_BOUND, 100) #等价于 np.linspace(-3,3,100)Y = np.linspace(*Y_BOUND, 100)X, Y = np.meshgrid(X, Y) #扩展为二维矩阵,方便建图Z = F(X, Y) #计算函数值ax.plot_surface(X, Y, Z, rstride=1, cstride=1, cmap=cm.coolwarm)#设置绘图参数ax.set_zlim(-10, 10)ax.set_xlabel('x')ax.set_ylabel('y')ax.set_zlabel('z')plt.pause(3)plt.show()if __name__ == "__main__":#创建画布fig = plt.figure()ax = Axes3D(fig)#更改为交互模式plt.ion()  #交互模式,程序遇到plt.show不会暂停,而是继续执行#绘制3D图plot_3d(ax)pop = np.random.randint(2, size=(POP_SIZE, DNA_SIZE * 2))  # 生成随机数的范围是[0,2) 矩阵大小为 rows: POP_SIZE cols:DNA_SIZE*2,因为两个自变量for _ in range(N_GENERATIONS):  # 迭代N代x, y = translateDNA(pop)if 'sca' in locals():#'sca'判断是不是一个全局变量,如果是,则将其移除sca.remove()#定义sca为scatter返回对象,scatter就是在函数图像上画出当前种群每个个体的位置sca = ax.scatter(x, y, F(x, y), c='black', marker='o');plt.show();plt.pause(0.1)#交叉变异,产生新一代种群pop = np.array(crossover_and_mutation(pop, CROSSOVER_RATE))#计算适应度if GET_MAX == 1:fitness = get_Maxfitness(pop)else:fitness = get_Minfitness(pop)#选择pop = select(pop, fitness)  # 选择生成新的种群#打印最后的全局最优信息print_info(pop)plt.ioff() #关闭交互模式plot_3d(ax)

在次代码中我们设置迭代次数为200次,并设置程序运行期间plot图不会被刷掉,让我们看一下运行过程。
在开始时,我们生成初始种群。
在这里插入图片描述
接下来开始不断地迭代种群,交叉、变异、选择…
在这里插入图片描述
在这里插入图片描述
如果你仔细观察地话,在种群迭代过程中总会有一些变异地染色体突然出现在四个角地地方,但随着选择地进行,其最终都将被淘汰。
在这里插入图片描述
随着迭代地不断进行,种群最终会逐渐趋向最优解
最终结果如图:
在这里插入图片描述
终端打印信息如下:

max_fitness: 0.0010000039026706524
最优的基因型: [1 0 0 1 0 1 0 1 0 1 0 1 0 1 0 1 0 1 0 1 1 1 0 1 1 1 1 1 0 1 0 0 0 0 1 0 00 0 1 0 1 1 0 0 0 0 1]
(x, y): (-0.00017398596846973646, 0.004052818063069452)

有兴趣的小伙伴赶紧去试试吧!


http://chatgpt.dhexx.cn/article/WBWJA1Zi.shtml

相关文章

vue实现点击下载exe,运行报错shellexecuteex失败 代码2

页面效果 exe插件放在vue项目的public文件夹里&#xff0c;然后用a标签实现点击下载 <a href"/VideoWebPlugin.exe">下载插件</a> 成功下载后运行报错 解决方法&#xff1a;选择在文件夹中显示&#xff0c;右击属性&#xff0c;在兼容性设置里的以管理员…

VC++分别使用WinExec、CreateProcess、ShellExecute和ShellExecuteEx来启动程序(附源码)

VC++常用功能开发汇总(专栏文章列表,欢迎订阅,持续更新...)https://blog.csdn.net/chenlycly/article/details/124272585C++软件异常排查从入门到精通系列教程(专栏文章列表,欢迎订阅,持续更新...)

API函数ShellExecute与ShellExecuteEx用法

ShellExecute: 1.函数功能:你可以给它任何文件的名字,它都能识别出来并打开它。2.函数原型: HINSTANCE ShellExecute( HWND hwnd, LPCTSTR lpOperation, LPCTSTR lpFile, LPCTSTR lpParameters, LPCTSTR lpDirectory, INT nShowCmd ); 3.参数说明:hwnd:用于指定父窗口句…

C/C++ 使用 API 函数 ShellExecuteEx 实现文件打印

本文章主要介绍使用ShellExecuteEx实现打印文件的功能。 函数原型&#xff1a;BOOL ShellExecuteExA(__inout SHELLEXECUTEINFOA *pExecInfo) 输入输出参数都是 SHELLEXECUTEINFO 结构体。 SHELLEXECUTEINFO定义&#xff1a; typedef struct _SHELLEXECUTEINFO { DWORD c…

Windows函数 ShellExecuteEx

点击进入视频教程 代码&#xff1a; #include<windows.h> #include<tchar.h> #pragma comment(lib, "Urlmon.lib") int WINAPI _tWinMain(HINSTANCE hinstance, HINSTANCE hPreInstance, LPTSTR lpCmdLine, int nShowCmd) {// 下载图片&#xff0c;并保…

UpdatePanel终于可以上传文件了!

我们要做的&#xff0c;只是在页面上添加一个控件而已。 不过&#xff0c;其实这只是个半成品&#xff0c;或者说是一个原型&#xff0c;但是很明显&#xff0c;我们做对了。:) 在实现上&#xff0c;我曾经在两个做法上斟酌了许久&#xff0c;第一种是继承ScriptManager&#x…

updatepanel 排版问题

使用 ASP.NET AJAX 開發人員&#xff0c;一定不會錯過 UpdatePanel 這個超級控制項&#xff0c;它可以讓輕易的讓原有設計的頁面很輕易的具有 AJAX 的效果。可是在設計階段使用 UpdatePanel 去排版常造成我們的困擾&#xff0c;放置在 UpdatePanel 中的控制項無法正確呈現實際的…

学习UpdatePanel控件-

原文可以显示图片&#xff08;转载&#xff1a;http://blog.csdn.net/ILOVEMSDN/archive/2007/11/11/1879343.aspx&#xff09; UpdatePanel控件的使用 2008-10-07 05:46 P.M. ScriptManager和UpdatePanel控件联合使用可以实现页面异步局部更新的效果。其中的UpdatePanel就是…

UpdatePanel的用法

UpdatePanel控件也是Ajax里用得最多的控件之中的一个&#xff0c;UpdatePanel控件是用来局部更新网页上的内容&#xff0c;网页上要局部更新的内容必须放在UpdatePanel控件里&#xff0c;他必须和上一次说的ScriptManager控件一起使用。如今来看UpdatePanel的属性 UpdatePanel …

浅谈UpdatePanel

这是我以前刚学习asp.net ajax的时候总结的&#xff0c;如果有什么错误的地方&#xff0c;请大家指出&#xff0c;以便我能早日改正。 1. 作用&#xff1a; UpdatePanel控件用来控制页面的局部更新&#xff0c;这些更新依赖于ScriptManager的EnablePartialRendering属性&…

UpdatePanel 控件简介

UpdatePanel 控件简介 全部折叠全部展开 代码&#xff1a;全部 代码&#xff1a;多种 代码&#xff1a;Visual Basic 代码&#xff1a;C# 代码&#xff1a;Visual C 代码&#xff1a;F# 代码&#xff1a;JScript UpdatePanel 控件简介 在本教程中&#xff0c;您将使用两…

ScriptManager updatepanel

在项目开发中&#xff0c;遇到了一个ajax更新问题&#xff0c;母版上有个通知区域&#xff08;通知区域为ajax定时更新&#xff08;updatepanel&#xff09;&#xff09;&#xff0c;上面有需要显示的几列信息&#xff0c;如最新文章数&#xff0c;批阅数&#xff0c;FTP受信状…

使用 UpdatePanel

1 概述 ASP.NET UpdatePanel 控件能让你创建丰富的、以客户为中心的 Web 应用程序。使用 UpdatePanel 控件&#xff0c;可以刷新选择的页面部分而不是使用回发来刷新整个页面&#xff0c;这就像是执行了一个局部页面更新一样。包含一个 ScriptManager 和一个或多个 UpdatePanel…

UpdatePanel控件

ASP.NET UpdatePanel控件可用于生成功能丰富、以客户端为中心的Web应用程序。通过使用UpdatePanel控件&#xff0c;可以在回发期间刷新网页的选定部分而不是刷新整个网页。这称为执行部分页更新。包含一个ScriptManager控件和一个或多个UpdatePanel控件的ASP.NET网页&#xff0…

ASP.NET AJAX入门系列(4):使用UpdatePanel控件(一)

UpdatePanel可以用来创建丰富的局部更新Web应用程序&#xff0c;它是ASP.NET 2.0 AJAX Extensions中很重要的一个控件&#xff0c;其强大之处在于不用编写任何客户端脚本&#xff0c;只要在一个页面上添加几个UpdatePanel控件和一个ScriptManager控件就可以自动实现局部更新。通…

UpdatePanel的用法及 UpdatePanel与JS冲突的解决方法

UpdatePanel的用法 ScriptManager和UpdatePanel控件联合使用可以实现页面异步局部更新的效果。其中的UpdatePanel就是设置页面中异 步局部更新区域&#xff0c;它必须依赖于ScriptManager存在&#xff0c;因为ScriptManger控件提供了客户端脚本生成与管理UpdatePanel的功 能。…

Java定时器 @Scheduled注解的使用

1.定时器Scheduled简介 Scheduled注解可以用于做定时任务&#xff0c;再方法上加上Scheduled注解&#xff0c;可以将这个方法定义为一个任务发放&#xff0c;可以搭配cron表达式进行任务的控制。 开启定时任务时在类上加注解 EnableScheduling 2.cron表达式的用法 1.按顺序…

java定时器的实现_java定时器实现总结

前言&#xff1a;Java定时器目前主要有3种实现方式&#xff1a;JDK组件&#xff0c;Spring Task&#xff0c;Quartz框架。 1. JDK组件 (1) java.util.TimerTask MyTimerTask.java&#xff1a; public class MyTimerTask extendsTimerTask { Overridepublic voidrun() { System.…

简单实现Java定时器

✨✨hello&#xff0c;愿意点进来的小伙伴们&#xff0c;你们好呐&#xff01; &#x1f43b;&#x1f43b;系列专栏&#xff1a;【JavaEE】 &#x1f432;&#x1f432;本篇内容&#xff1a;自己实现Java定时器 &#x1f42f;&#x1f42f;作者简介:一名现大二的三非编程小白&…

java 定时器框架_java定时器

java定时器 什么是Java定时器&#xff1f; Java 定时器就是在给定的间隔时间执行自己的任务; Java实现定时器有以下几种: 通过Timer来实现定时任务 Timer 是来自 java.util.Timer 指定时间执行任务 /** * author spp * date 2020-10-14 09:04 **/ public class TimerTest { pub…