【Sql Server】通过Sql语句批量处置惩罚数据,使用变量且遍历数据进行逻辑 ...

海哥  金牌会员 | 2024-6-14 21:57:05 | 显示全部楼层 | 阅读模式
打印 上一主题 下一主题

主题 536|帖子 536|积分 1608

接待来到《小5讲堂》,大家好,我是全栈小5。
这是《Sql Server》系列文章,每篇文章将以博主明白的角度睁开讲解,
特殊是针对知识点的概念进行叙说,大部分文章将会对这些概念进行现实例子验证,以此达到加深对知识点的明白和掌握。
温馨提示:博主能力有限,明白水平有限,如有不对之处望指正!
  


  
前言

最近在进行汗青数据处置惩罚,刚开始是想着通过在后端写个逻辑处置惩罚,也非常简单。
对于数据库而言,通过sql语句处置惩罚就是最好的,方便下次再处置惩罚时有个sql语句参考,
或者也方便运维人员直接使用,后端代码逻辑处置惩罚运维人员并不肯定都懂。
因此,本篇文章将模拟批量数据进行sql语句遍历处置惩罚。
创建表

创建一张学生都会表,主要字段如下
  1. -- 创建学生城市表
  2. create table student_table
  3. (
  4.     id int identity(1,1),
  5.     name_value nvarchar(50),
  6.     city_value nvarchar(50),
  7.     city_value_temp nvarchar(50),
  8.     create_time datetime default getdate()
  9. )
复制代码
模拟数据

模拟添加10条记载数据,且设置几条重复记载
  1. -- 模拟10条记录
  2. insert into student_table(name_value,city_value) values
  3. ('张三','广州'),
  4. ('张三','广州'),
  5. ('张三','广州'),
  6. ('李四','深圳'),
  7. ('李四','深圳'),
  8. ('王五','佛山'),
  9. ('刘六','佛山'),
  10. ('刘六','佛山'),
  11. ('张七','东莞'),
  12. ('吴八','惠州')
复制代码

分组查询

按学生和都会分组查询,且having筛选有重复记载的数据
  1. -- 学生和城市分组查询 - 有重复记录的数据
  2. select name_value,city_value,count(1) repeatcount,max(id) maxid
  3. from student_table
  4. group by name_value,city_value having count(1)>1
复制代码

while实现

进行两次while遍历,然后将学生重复的都会值,除了编号最大那条记载外,其他重复记载则加序号值并赋值到city_value_temp字段里

1)界说变量表 - 生存重复的学生记载
2)定量变量
3)将源表中的数据插入到表变量中
4)第一层遍历
5)第一层,每次都获取第一条记载
6)界说变量表 - 生存当前学生重复记载
7)第二层遍历
8)第二层,每次都获取第一条记载
9)将当前第二层遍历记载移除
10)更新表字段
11)将当前第一层遍历记载移除
  1. -- =====遍历处理重复数据 - 编写处理逻辑=====
  2. -- 定义变量表 - 保存重复的学生记录
  3. declare @temp_one_table table
  4. (
  5.     name_value nvarchar(50),
  6.     city_value nvarchar(50),
  7.     repeatcount int,
  8.     maxid int
  9. )
  10. -- 定量变量
  11. declare @maxid int
  12. declare @name_value varchar(50)
  13. declare @city_value varchar(50)
  14. -- 将源表中的数据插入到表变量中
  15. insert into @temp_one_table(name_value,city_value,repeatcount,maxid)
  16. select name_value,city_value,count(1) repeatcount,max(id) maxid
  17. from student_table
  18. group by name_value,city_value having count(1)>1
  19. -- 第一层遍历
  20. while exists(select city_value from @temp_one_table) begin
  21.    
  22.     -- 每次都获取第一条记录
  23.     select top 1 @maxid=maxid,@name_value=name_value,@city_value=city_value from @temp_one_table
  24.     --print(@name_value)
  25.     -- 定义变量表 - 保存当前学生重复记录
  26.     declare @temp_two_table table
  27.     (
  28.         id int,
  29.         name_value nvarchar(50),
  30.         city_value nvarchar(50),
  31.         create_time datetime
  32.     )
  33.     insert into @temp_two_table(id,name_value,city_value,create_time)
  34.     select id,name_value,city_value,create_time from student_table
  35.     where name_value=@name_value and city_value=@city_value
  36.     -- 第二层遍历
  37.     declare @id int
  38.     while exists(select id from @temp_two_table) begin
  39.                 -- 第二层,每次都获取第一条记录
  40.         select top 1 @id=id from @temp_two_table
  41.         print(@name_value+convert(varchar,@id))
  42.         -- 将当前第二层遍历记录移除
  43.         delete from @temp_two_table where id=@id
  44.         -- 更新表字段
  45.         if @id!=@maxid begin
  46.             update student_table set city_value_temp=(@city_value+convert(varchar,@id)) where id=@id
  47.         end
  48.     end
  49.     -- 将当前第一层遍历记录移除
  50.     delete from @temp_one_table where name_value=@name_value and city_value=@city_value
  51. end
  52. select * from student_table
  53. -- =====/遍历处理重复数据 - 编写处理逻辑=====
复制代码
游标实现

输出编号

下面举例通过游标遍历,逐行输出编号值

  1. -- 定义变量
  2. declare @id int
  3. -- 定义游标并赋值
  4. declare cursor_name cursor for
  5. select id from student_table
  6. -- 打开游标
  7. open cursor_name
  8. -- 逐行获取数据
  9. fetch next from cursor_name into @id
  10. while @@fetch_status=0 begin
  11.    
  12.     print(@id)
  13.     -- 下一条记录
  14.     fetch next from cursor_name into @id
  15. end
复制代码
结合临时表


1)界说变量
2)界说游标并赋值
3)打开游标
4)逐行获取数据
5)创建局部临时表
6)第二层遍历
7)将当前第二层遍历记载移除
8)更新表字段
9)下一条记载
10)关闭游标
11)开释游标
  1. -- 定义变量
  2. declare @name_value nvarchar(50)
  3. declare @city_value nvarchar(50)
  4. declare @repeatcount int
  5. declare @maxid int
  6. -- 定义游标并赋值
  7. declare cursor_name cursor for
  8. select name_value,city_value,count(1) repeatcount,max(id) maxid
  9. from student_table
  10. group by name_value,city_value having count(1)>1
  11. -- 打开游标
  12. open cursor_name
  13. -- 逐行获取数据
  14. fetch next from cursor_name into @name_value,@city_value,@repeatcount,@maxid
  15. while @@fetch_status=0 begin
  16.    
  17.     --print(@name_value)
  18.     -- 创建局部临时表并赋值
  19.     drop table #temp_table
  20.     create table #temp_table
  21.     (
  22.         id int,
  23.         name_value nvarchar(50),
  24.         city_value nvarchar(50),
  25.         create_time datetime
  26.     )
  27.     insert into #temp_table(id,name_value,city_value,create_time)
  28.     select id,name_value,city_value,create_time from student_table
  29.     where name_value=@name_value and city_value=@city_value
  30.     -- 第二层遍历
  31.     declare @id int
  32.     while exists(select id from #temp_table) begin
  33.         select top 1 @id=id from #temp_table
  34.         print(@name_value+convert(varchar,@id))
  35.         -- 将当前第二层遍历记录移除
  36.         delete from #temp_table where id=@id
  37.         -- 更新表字段
  38.         if @id!=@maxid begin
  39.             update student_table set city_value_temp=(@city_value+convert(varchar,@id)),remark='游标加临时表处理' where id=@id
  40.         end
  41.     end
  42.     -- 下一条记录
  43.     fetch next from cursor_name into @name_value,@city_value,@repeatcount,@maxid
  44. end
  45. -- 关闭游标
  46. close cursor_name
  47. -- 释放游标
  48. deallocate cursor_name
  49. select * from student_table
复制代码
知识点

在 SQL Server 中,游标和临时表都是用于处置惩罚数据的工具,但它们的使用方式和目的略有差别。
游标(Cursor):

游标是一种用于逐行处置惩罚数据的数据库对象。通常在需要逐行访问数据并执行复杂操作时使用。游标可以使用以下步调创建和操作:


  • 声明游标:界说一个游标并指定查询的结果集。
  • 打开游标:执行查询并将结果集放入游标中。
  • 逐行获取数据:使用 FETCH 语句一次从游标中获取一行数据。
  • 处置惩罚数据:对获取的数据进行操作。
  • 关闭游标:处置惩罚完数据后关闭游标,开释资源。
    示例:
  1. DECLARE @id INT
  2. DECLARE cursor_name CURSOR FOR
  3. SELECT id FROM table_name
  4. OPEN cursor_name
  5. FETCH NEXT FROM cursor_name INTO @id
  6. WHILE @@FETCH_STATUS = 0
  7. BEGIN
  8.     -- Process data
  9.     FETCH NEXT FROM cursor_name INTO @id
  10. END
  11. CLOSE cursor_name
  12. DEALLOCATE cursor_name
复制代码
临时表(Temporary Table):

临时表是一种临时存储数据的表,它们一般用于在当前会话中临时存储和处置惩罚数据。SQL Server 提供了两种类型的临时表:全局临时表和局部临时表。


  • 局部临时表:以 # 开头,在当前会话中可见,在会话结束时自动删除。
  • 全局临时表:以 ## 开头,对所有会话可见,当创建它的会话结束时自动删除。
    示例:
  1. -- 创建局部临时表
  2. CREATE TABLE #temp_table (
  3.     id INT,
  4.     name VARCHAR(50)
  5. )
  6. -- 插入数据
  7. INSERT INTO #temp_table VALUES (1, 'Alice'), (2, 'Bob')
  8. -- 查询数据
  9. SELECT * FROM #temp_table
  10. -- 删除临时表(在会话结束时会自动删除)
  11. DROP TABLE #temp_table
复制代码
  游标用于逐行处置惩罚数据,实用于复杂逐行操作;而临时表用于临时存储和处置惩罚数据,实用于需要临时生存中间结果的环境。
在现实应用中,要根据具体需求选择符合的工具来处置惩罚数据。
  文章推荐

【Sql Server】通过Sql语句批量处置惩罚数据,使用变量且遍历数据进行逻辑处置惩罚
【新星筹划回首】第六篇学习筹划-通过自界说函数和存储过程模拟MD5数据
【新星筹划回首】第四篇学习筹划-自界说函数、存储过程、随机值知识点
【Sql Server】Update中的From语句,以及常见更新操作方式
【Sql server】假设有三个字段a,b,c 以a和b分组,怎样查询a和b唯一,但是c差别的记载
【Sql Server】新手一分钟看懂在已有表根本上修改字段默认值和数据类型
   总结:温故而知新,差别阶段重温知识点,会有不一样的认识和明白,博主将巩固一遍知识点,并以实践方式和大家分享,若能有所帮助和劳绩,这将是博主最大的创作动力和荣幸。也等待认识更多良好新老博主。

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

x
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

海哥

金牌会员
这个人很懒什么都没写!

标签云

快速回复 返回顶部 返回列表