C# 高阶语法 —— Winfrom链接SQL数据库的存储过程
存储过程在应用程序端的使用的优点
1 如果sql语句直接写在客户端,以一个字符串的形式体现的,提示不友好,会导致效率降低
2 sql语句写在客户端,可以利用sql注入进行攻击,为了安全性,可以把sql封装在服务器存储过程,在客户端进行
SQL自定义无参数存储过程:
创建存储过程 usp_ScoreQuery1
-- 查询考试成绩,显示:学号、姓名、班级、总成绩,并按成绩的总分高低排序。
-- 统计分析考试成绩,显示班级名称、C#平均分、数据库平均分,按照班级分组实现。
use SMDBgoif exists (select * from sysobjects where name = 'usp_ScoreQuery1')drop procedure usp_ScoreQuery1gocreate procedure usp_ScoreQuery1as-- 查询考试成绩select Students.StudentId,StudentName,ClassName, ScoreSum = (CSharp + SqlserverDB) from Studentsinner join StudentClass on StudentClass.ClassId = Students.ClassIdinner join ScoreList on ScoreList.StudentId = Students.StudentIdorder by ScoreSum DESC-- 分析考试信息select ClassName,C#Avg=AVG(CSharp),DBAvg=AVG(SqlserverDB) from ScoreListinner join Students on Students.StudentId = ScoreList.StudentIdinner join StudentClass on StudentClass.ClassId = Students.ClassIdgroup by ClassNameorder by ClassNamego
针对上面实现的效果,继续修改,改为参数可以带默认值
use SMDB
go
if exists (select * from sysobjects where name = 'usp_ScoreQuery4')
drop procedure usp_ScoreQuery4
go
create procedure usp_ScoreQuery4-- 带默认值@CSharp int = 60,@SqlserverDB int = 60
asselect Students.StudentId,StudentName,CSharp as C#,SqlserverDB as DB from ScoreListinner join Students on Students.StudentId = ScoreList.StudentIdwhere CSharp < @CSharp or SqlserverDB < @SqlserverDB
go-- 调用参数带默认值的存储过程
use SMDB
go
exec usp_ScoreQuery4 -- 两个都走的默认值
exec usp_ScoreQuery4 70,80 -- 第二个参数取默认值
exec usp_ScoreQuery4 @SqlserverDB = 70 -- 第一个参数取默认值
exec usp_ScoreQuery4 default,70 -- 第一个参数取默认值(同上)
3. 自定义带输出参数的存储过程
-- 问题:查询考试成绩,要求自定义分数线,显示查询列表,并输出缺考总人数、不及格总人数?
use SMDB
go
if exists (select * from sysobjects where name = 'usp_ScoreQuery5')
drop procedure usp_ScoreQuery5
go
create procedure usp_ScoreQuery5-- 输出参数(习惯:输出参数放在输入参数的前面)@AbsentCount int output, -- 缺考总人数@FailCount int output, -- 不及格总人数-- 输入参数@CSharp int = 60, -- CSharp分数线@SqlserverDB int = 60 -- SqlserverDB分数线
as-- 查询考试成绩,要求自定义分数线select Students.StudentId,StudentName,CSharp as C#,SqlserverDB as DB from ScoreListinner join Students on Students.StudentId = ScoreList.StudentIdwhere CSharp < @CSharp or SqlserverDB < @SqlserverDB-- 缺考总人数select @AbsentCount = count(*) from Students where StudentId not in (select StudentId from ScoreList)-- 不及格总人数select @FailCount = count(*) from ScoreList where CSharp < @CSharp or SqlserverDB < @SqlserverDB
go-- 调用参数带默认值的存储过程
use SMDB
go
-- 首先定义输出参数(命名可以和上面的保持一致,不一样也行)
declare @AbsentCount int, @FailCount int
-- 调用存储过程时,输出参数后面也必须加上 output 关键字
exec usp_ScoreQuery5 @AbsentCount output,@FailCount output
select @AbsentCount as 缺考总人数,@FailCount as 不及格总人数
-- 打印一下结果
print @AbsentCount
print @FailCount
链接SQL数据库
public string connString = @"Server=.;DataBase=SMDB;Uid=sa;Pwd=123456";
搭建Winfrom窗体

一:无参数的存储过程的调用
不带参数存储过程的使用
1指定存储过程名称
string proceName = "usp_ScoreQuery5";
2创建指令对象传递连接对象和存储过程
SqlCommand cmd = new SqlCommand(proceName,conn);
3 指定指令执行类型
cmd.CommandType = CommandType.StoredProcedure;
4 执行指令
SqlDataReader dr = cmd.ExecuteReader();
private void button1_Click(object sender, EventArgs e){//1 定义存储过程名称string proceName = "usp_ScoreQuery1";//2 创建一个指令对象SqlCommand cmd = new SqlCommand();//3 添加执行sql语句和设置连接对象cmd.CommandText = proceName;// 添加执行的sqlcmd.Connection = conn; //设置连接对象//4 执行命令类型cmd.CommandType = System.Data.CommandType.StoredProcedure;// 5 取出数据List<Model1> model1s = new List<Model1>();// 存储第一个表的数据List<Model2> models2 = new List<Model2>();//存储第二个表的数据try{SqlDataReader dr = cmd.ExecuteReader(); // 读取数据库数据while (dr.Read()){model1s.Add(new Model1() { StudentId =Convert.ToInt32( dr["StudentId"]),StudentName = dr["StudentName"].ToString(),ClassName = dr["ClassName"].ToString(),ScoreNum = Convert.ToInt32(dr["ScoreSum"])});}//如果有第二个数据源 读取第二个selectif (dr.NextResult()){while (dr.Read()){models2.Add(new Model2() {ClassName = dr["ClassName"].ToString(),CSharpAvg = Convert.ToInt32(dr["C#Avg"]),DBAvg = Convert.ToInt32(dr["DBAvg"]),});}}dr.Close();this.dataGridView1.DataSource = model1s;this.dataGridView2.DataSource = models2;}catch{throw;}}
二:带输入参数的存储过程的使用
带输入参数的存储过程的调用
1指定存储过程名称
string proceName = "usp_ScoreQuery5";
2创建指令对象传递连接对象和存储过程
SqlCommand cmd = new SqlCommand(proceName,conn);
3 指定指令执行类型
cmd.CommandType = CommandType.StoredProcedure;
4 添加输入参数
cmd.Parameters.Add(new SqlParameter()
{
ParameterName = "@CSharp",
Direction = ParameterDirection.Input,
SqlDbType = SqlDbType.Int,
Value = 80
});
5执行指令
SqlDataReader dr = cmd.ExecuteReader();
private void button2_Click(object sender, EventArgs e)
{//1 指明存储过程string proceName = "usp_ScoreQuery4";//2 创建指令对象SqlCommand cmd = new SqlCommand();//3 设置连接和设置执行过程cmd.Connection = conn; cmd.CommandText = proceName;//4 执行类型cmd.CommandType = CommandType.StoredProcedure;//5 设置输入参数//定义参数方法1SqlParameter csharp = new SqlParameter();csharp.ParameterName = "@CSharp";// 设置csharp是存储过程中对应@CSharp输入参数csharp.Direction = ParameterDirection.Input;//设置为输入参数csharp.Value = 180;// 设置参数的值为70csharp.SqlDbType = SqlDbType.Int; //设置参数类型cmd.Parameters.Add(csharp); // 把输入参数添加到参数列表里面// 定义参数方法2 @SqlserverDBcmd.Parameters.Add(new SqlParameter() { ParameterName = "@SqlserverDB",Direction = ParameterDirection.Input,Value = 180,SqlDbType = SqlDbType.Int,});// 6 获取数据List<Model3> list = new List<Model3>();try{SqlDataReader dr = cmd.ExecuteReader();while (dr.Read()){list.Add(new Model3(){StudentId = Convert.ToInt32(dr["StudentId"]),StudentName = dr["StudentName"].ToString(),CSharp = Convert.ToInt32(dr["C#"]),DB = Convert.ToInt32(dr["DB"]),});}dr.Close();this.dataGridView1.DataSource = list;}catch{throw;}
}
三:调用带输出参数的存储过程 对应的是model3对象
带输入参数带输出参数的调用
添加输出参数即可
cmd.Parameters.Add(new SqlParameter()
{
ParameterName = "@AbsentCount",
Direction = ParameterDirection.Output,
SqlDbType = SqlDbType.Int,
});
获取输出参数的值
cmd.Parameters["@AbsentCount"].Value.ToString()
private void button3_Click(object sender, EventArgs e)
{string proceName = "usp_ScoreQuery5";SqlCommand cmd = new SqlCommand(proceName,conn);//cmd.CommandText = proceName;//cmd.Connection = conn;cmd.CommandType = CommandType.StoredProcedure;//设置输出参数cmd.Parameters.Add(new SqlParameter() { ParameterName= "@AbsentCount",Direction = ParameterDirection.Output,SqlDbType=SqlDbType.Int,});cmd.Parameters.Add(new SqlParameter(){ParameterName = "@FailCount",Direction = ParameterDirection.Output,SqlDbType = SqlDbType.Int,});//输入参数cmd.Parameters.Add(new SqlParameter(){ParameterName = "@CSharp",Direction = ParameterDirection.Input,SqlDbType = SqlDbType.Int,Value = 80});cmd.Parameters.Add(new SqlParameter(){ParameterName = "@SqlserverDB",Direction = ParameterDirection.Input,SqlDbType = SqlDbType.Int,Value = 80});//取数据List<Model3> list = new List<Model3>();SqlDataReader dr = cmd.ExecuteReader();while (dr.Read()){list.Add(new Model3(){StudentId = Convert.ToInt32(dr["StudentId"]),StudentName = dr["StudentName"].ToString(),CSharp = Convert.ToInt32(dr["C#"]),DB = Convert.ToInt32(dr["DB"]),});}dr.Close();this.dataGridView1.DataSource = list;//输出参数的值怎么取? 缺考总人数? 不及格人数?this.label1.Text = "缺考总人数:" + cmd.Parameters["@AbsentCount"].Value.ToString() + "人";this.label2.Text = "不及格总人数:" + cmd.Parameters["@FailCount"].Value.ToString() + "人";
}
相关文章:
C# 高阶语法 —— Winfrom链接SQL数据库的存储过程
存储过程在应用程序端的使用的优点 1 如果sql语句直接写在客户端,以一个字符串的形式体现的,提示不友好,会导致效率降低 2 sql语句写在客户端,可以利用sql注入进行攻击,为了安全性,可以把sql封装在…...
vue3+vite+ts配置多个代理并解决报404问题
之前配置接口代理总是报404,明明接口地址是对的但还是报是因数写法不对;用了vue2中的写法 pathRewrite改为rewrite 根路径下创建env文件根据自己需要名命 .env.development文件内容 # just a flag ENVdevelopment# static前缀 VITE_APP_PUBLIC_PREFIX"" # 基础模块…...
开创未来:探索OpenAI首个AI视频模型Sora的前沿技术与影响
Sora - 探索AI视频模型的无限可能 随着人工智能技术的飞速发展,AI视频模型已成为科技领域的新热点。而在这个浪潮中,OpenAI推出的首个AI视频模型Sora,以其卓越的性能和前瞻性的技术,引领着AI视频领域的创新发展。让我们将一起探讨…...
Redis---持久化
Redis是内存数据库,是把数据存储在内存中的,但是内存中的数据不是持久的,如果想要做到持久,那么就需要让redis将数据存储到硬盘上。 Redis持久化有两种策略: RDB > Redis DataBase RDB机制采取的是定期备份AOF …...
从 Flask 切到 FastAPI 后,起飞了!
我这几天上手体验 FastAPI,感受到这个框架易用和方便。之前也使用过 Python 中的 Django 和 Flask 作为项目的框架。Django 说实话上手也方便,但是学习起来有点重量级框架的感觉,FastAPI 带给我的直观体验还是很轻便的,本文就会着…...
状态码转文字!!!(表格数字转文字)
1、应用场景:在我们的数据库表中经常会有status这个字段,这个字段经常表示此类商品的状态,例如:0->删除,1->上架,0->下架,等等。 2、我们返回给前端数据时,如果在页面显示0…...
Pytorch 复习总结 4
Pytorch 复习总结,仅供笔者使用,参考教材: 《动手学深度学习》Stanford University: Practical Machine Learning 本文主要内容为:Pytorch 深度学习计算。 本文先介绍了深度学习中自定义层和块的方法,然后介绍了一些…...
YOLOv9中加入SCConv模块!
专栏介绍:YOLOv9改进系列 | 包含深度学习最新创新,主力高效涨点!!! 一、本文介绍 本文将一步步演示如何在YOLOv9中添加 / 替换新模块,寻找模型上的创新! 适用检测目标: YOLOv9模块…...
代码随想录算法训练营第四十七天丨198. 打家劫舍、 213. 打家劫舍 II、337. 打家劫舍 III
198. 打家劫舍 自己的思路: 初始化两个dp数组,dp[i][0]表示不偷第i户,在0-i户可以偷到的最大金额,dp[i][1]表示偷i户在0-i户可以偷到的最大金额。 class Solution:def rob(self, nums: List[int]) -> int:n len(nums)dp […...
龙蜥Anolis 8.4 anck 安装mysql5.7
el8没有用mysql5.7了,镜像里是mysql8。 禁用 sudo dnf remove mysql sudo dnf module reset mysql sudo dnf module disable mysql 修改Yum源 sudo vi /etc/yum.repos.d/mysql-community.repo [mysql57-community] nameMySQL 5.7 Community Server baseurlhttp:…...
【踩坑】修复xrdp无法关闭Authentication Required验证窗口
转载请注明出处:小锋学长生活大爆炸[xfxuezhang.cn] 问题如下,时不时出现,有时还怎么都关不掉,很烦: 解决方法一:命令行输入 dbus-send --typemethod_call --destorg.gnome.Shell /org/gnome/Shell org.gn…...
python学习笔记 - 标准库常量
Python 中有一些内置的常量,它们是一些特殊的值,通常不会改变。以下是其中一些常见的内置常量及其详细解释以及使用示例: True: 表示布尔值真。给 True 赋值是非法的并会引发 SyntaxError。 x True print(x) # 输出:…...
视频和音频使用ffmpeg进行合并和分离(MP4)
1.下载ffmpeg 官网地址:https://ffmpeg.org/download.html 2.配置环境变量 此电脑右键点击 属性 - 高级系统配置 -高级 -环境变量 - 系统变量 path 新增 文件的bin路径 3.验证配置成功 ffmpeg -version 返回版本信息说明配置成功4.执行合并 ffmpeg -i 武家坡20…...
02| JVM堆中垃圾回收的大致过程
如果一直在创建对象,堆中年轻代中Eden区会逐渐放满,如果Eden放满,会触发minor GC回收,创建对象的时GC Roots,如果存在于里面的对象,则被视为非垃圾对象,不会被此次gc回收,就会被移入…...
R语言数据可视化之美专业图表绘制指南(增强版):第1章 R语言编程与绘图基础
第1章 R语言编程与绘图基础 目录 第1章 R语言编程与绘图基础前言1.1 学术图表的基本概念1.1.1 学术图表的基本作用1.1.2基本类别1.1.3 学术图表的绘制原则 1.2 你为什么要选择R1.3 安装 前言 这是我第一次在博客里展示学习中国作者的教材的笔记。我选择这本书的依据是作者同时…...
网站添加pwa操作和配置manifest.json后,没有效果排查问题
pwa技术官网:https://web.dev/learn/pwa 应用清单manifest.json文件字段说明:https://web.dev/articles/add-manifest?hlzh-cn Web App Manifest:Web App Manifest | MDN 当网站添加了manifest.json文件后,也引入到html中了&a…...
MongoDB聚合运算符:$cosh
文章目录 语法使用举例双曲余弦值角度双曲余弦值弧度 $cosh聚合运算符用来计算双曲余弦值,返回指定表达式的双曲余弦值。 语法 { $cosh: <expression> }<expression>为可被解析为数值的表达式$cosh返回弧度,使用$radiansToDegrees运算符可…...
Jenkins配置在远程服务器上执行shell脚本(两种方式)
Jenkins配置在远程服务器上执行shell脚本 方式一:通过SSH免密方式执行 说明:Jenkins部署在ServerA:10.1.1.74上,要运行的程序在ServerB:10.1.1.196 分两步 第一步:Linux Centos7配置SSH免密登录 Linux…...
Java+SpringBoot,打造社区疫情信息新生态
✍✍计算机编程指导师 ⭐⭐个人介绍:自己非常喜欢研究技术问题!专业做Java、Python、微信小程序、安卓、大数据、爬虫、Golang、大屏等实战项目。 ⛽⛽实战项目:有源码或者技术上的问题欢迎在评论区一起讨论交流! ⚡⚡ Java实战 |…...
js ES6判断字符串是否以某个字符串开头或者结尾startsWith、endsWith
1.前言 startsWith:startsWith方法用于检查字符串是否以指定的字符串开头。 endsWith:endsWith方法用于检查字符串是否以指定的字符串结尾。 2.用法示例 const str Hello, world!;console.log(str.startsWith(Hello)); // true console.log(str.starts…...
从WWDC看苹果产品发展的规律
WWDC 是苹果公司一年一度面向全球开发者的盛会,其主题演讲展现了苹果在产品设计、技术路线、用户体验和生态系统构建上的核心理念与演进脉络。我们借助 ChatGPT Deep Research 工具,对过去十年 WWDC 主题演讲内容进行了系统化分析,形成了这份…...
Redis相关知识总结(缓存雪崩,缓存穿透,缓存击穿,Redis实现分布式锁,如何保持数据库和缓存一致)
文章目录 1.什么是Redis?2.为什么要使用redis作为mysql的缓存?3.什么是缓存雪崩、缓存穿透、缓存击穿?3.1缓存雪崩3.1.1 大量缓存同时过期3.1.2 Redis宕机 3.2 缓存击穿3.3 缓存穿透3.4 总结 4. 数据库和缓存如何保持一致性5. Redis实现分布式…...
Java入门学习详细版(一)
大家好,Java 学习是一个系统学习的过程,核心原则就是“理论 实践 坚持”,并且需循序渐进,不可过于着急,本篇文章推出的这份详细入门学习资料将带大家从零基础开始,逐步掌握 Java 的核心概念和编程技能。 …...
(转)什么是DockerCompose?它有什么作用?
一、什么是DockerCompose? DockerCompose可以基于Compose文件帮我们快速的部署分布式应用,而无需手动一个个创建和运行容器。 Compose文件是一个文本文件,通过指令定义集群中的每个容器如何运行。 DockerCompose就是把DockerFile转换成指令去运行。 …...
Swagger和OpenApi的前世今生
Swagger与OpenAPI的关系演进是API标准化进程中的重要篇章,二者共同塑造了现代RESTful API的开发范式。 本期就扒一扒其技术演进的关键节点与核心逻辑: 🔄 一、起源与初创期:Swagger的诞生(2010-2014) 核心…...
Linux --进程控制
本文从以下五个方面来初步认识进程控制: 目录 进程创建 进程终止 进程等待 进程替换 模拟实现一个微型shell 进程创建 在Linux系统中我们可以在一个进程使用系统调用fork()来创建子进程,创建出来的进程就是子进程,原来的进程为父进程。…...
SAP学习笔记 - 开发26 - 前端Fiori开发 OData V2 和 V4 的差异 (Deepseek整理)
上一章用到了V2 的概念,其实 Fiori当中还有 V4,咱们这一章来总结一下 V2 和 V4。 SAP学习笔记 - 开发25 - 前端Fiori开发 Remote OData Service(使用远端Odata服务),代理中间件(ui5-middleware-simpleproxy)-CSDN博客…...
sipsak:SIP瑞士军刀!全参数详细教程!Kali Linux教程!
简介 sipsak 是一个面向会话初始协议 (SIP) 应用程序开发人员和管理员的小型命令行工具。它可以用于对 SIP 应用程序和设备进行一些简单的测试。 sipsak 是一款 SIP 压力和诊断实用程序。它通过 sip-uri 向服务器发送 SIP 请求,并检查收到的响应。它以以下模式之一…...
Mysql中select查询语句的执行过程
目录 1、介绍 1.1、组件介绍 1.2、Sql执行顺序 2、执行流程 2.1. 连接与认证 2.2. 查询缓存 2.3. 语法解析(Parser) 2.4、执行sql 1. 预处理(Preprocessor) 2. 查询优化器(Optimizer) 3. 执行器…...
视觉slam十四讲实践部分记录——ch2、ch3
ch2 一、使用g++编译.cpp为可执行文件并运行(P30) g++ helloSLAM.cpp ./a.out运行 二、使用cmake编译 mkdir build cd build cmake .. makeCMakeCache.txt 文件仍然指向旧的目录。这表明在源代码目录中可能还存在旧的 CMakeCache.txt 文件,或者在构建过程中仍然引用了旧的路…...
