博主整理了包含:数据库、模式、表、视图、约束、触发器、变量、函数等等SQL-server中差不多所有类型的sql语言,希望对你有所帮助,后续有新的发现还会继续更新的!
学习之前要解有关数据库、文件、日志文件等属性:
1)逻辑名称:数据文件和日志文件名称;
2)文件类型:数据文件及日志文件 ;
3)文件组:各个数据文件所属的文件组名称;
4)初始大小:文件的最原始大小;
5)自动增长:文件按指定的大小增长,也可限制到最大容量;
6)路径:存放文件的物理目录;
7)文件名:显示数据文件和日志文件的物理名称;
默认数据库属性:
1)主数据文件为xx.mdf,日志文件为xx_log.ldf;
2)只有一个文件组Primary;
3)主数据文件初始大小为5MB(sql server2008及低版本初始大小基本都为3MB),增量为1MB;
4)日志文件初始大小1MB,增量为10%;
5)5) 主数据文件和日志文件都存放在C:\Program Files\Microsoft SQL Server\MSSQL10.MSSQLSERVER\MSSQL\DATA目录下,文件分别为xx.mdf 和xx_log.ldf 。
1. 数据库的修改
修改数据库的命令如下:
Alter database database_name
{
add file <filespec>[,…n] [to filegroup filegroupname]
add log file <filespec>[,…n]
remove file logical_file_name [with delete]
modify file <filespec>}
增加数据文件
例如:在数据库中增加数据文件db2,初始大小为10MB,最大大小为50 MB,按10%增长;
alter database student
add file
(
name = db2,
filename = 'D:\db2.ndf',
size = 10mb,
maxsize = 50mb,
filegrowth = 10%
)
增加日志文件
例:在数据库student中添加日志文件,保存在D盘中,初始大小为1MB,最大无限制,增长方式按照1MB增长;
alter database student
add log file
(
name = stu_log2,
filename = 'D:\stu_log2.ldf',
size = 1mb,
maxsize = unlimited,
filegrowth = 1mb
)
修改数据库
例:修改数据库student主数据文件的大小,将主数据文件的初始大小修改为10Mb,增长方式为20%;
alter database student
modify file
( //修改文件用modify file
name = stu, //修改日志文件是modify log file
size = 10mb,
filegrowth =20%
)
删除数据文件及日志文件
例:删除数据库student辅助数据文件和第二个日志文件;
alter database student
romove file stu2
go //注意go语句是让多条语句分别执行
alter database student
remove file stu_log2
2.模式的创建
模式定义语句如下:
CREATE SCHEMA<模式名>AUTHORIZTION<用户名>;
注意:如果没有指定<模式名>,则<模式名>隐含为<用户名>。要创建模式时,调用该命令的用户必须拥有数据库管理员权限,或者获得了数据库管理员授予的 CREATE SCHEMA 的权限。
例如:
为用户WANG定义一个学生-课程模式S-T。
CREATE SCHEMA"S-T" AUTHORIZATION WANG;
用户可以在创建模式的同时在这个模式定义中进一步创建表、视图,定义授权。
例如:
为用户ZHANG创建一个模式TEST,并且在其中定义一个表TAB。
CREATE SCHEMA TEST AUTHORIZATION ZHANG
CREATE TABLE TAB(COL1 SMALLINT,
COL2 INT,
COL3 CHAR(20),
COL4 NUMERLC(10,3)
......
);
3.定义基本表
SQL语言使用 CREATE TABLE 语句来定义基本表,其格式:
CREATE TABLE <表名> (<列名><数据类型>[列级完整性约束条件]
[,<列名><数据类型>[列级完整性约束条件]]
....
[,<表级完整性约束条件>]);
例如:
建立一个"学生表"Student.
CREATE TABLE Student
(Sno CHAR(9) PRIMARY KEY, /*列级完整性约束条件,Sno是主码*/
Sname CHAR(20) UNIQUE, /*Sname 取唯一值*/
Ssex CHAR(2),
Sage SMALLINT,
Sdept CHAR(20)
);
定义两个码
如:建立学生选课表SC。
CREATE TABLE SC
(Sno CHAR(9),
Cno CHAR(4),
Grade SMALLINT,
PRIMARY KEY(Sno,Cno), /*主码由两个属性组成,必须作为表级完整性进行定义*/
FOREIGN KEY(Sno) REFERENCES Student(Sno), /*表级完整性约束条件,Sno是外码,被参照表是Student*/
FOREIGN KEY(Cno) REFERENCES Course(Cno), /*表级完整性约束条件,Cno是外码,被参照表是Course*/
4.数据表查询、修改操作
1、 显示学号最后一位为1或者2或者3的学生的学号、姓名、性别年龄及院系;
select sno,sname,ssex,sdept
from student
where sno like '&[1-3]';
2、 查询所有院系不是CS、IS的男同学信息。
select all*
from student
where sdept not in('cs','is') and ssex='男';
3、 修改student表,将cs系姓名为“李咏”的学生姓名为“李勇”
update student
set sname='李勇'
where sdept='cs' and sname='李咏'
4、 将学号为“200515010”的学生信息重新设置为“王丹丹、女、20、MA”;
update student
set sname='王丹丹',ssex='女',sage=20,sdept='MA'
where sno=200515010;
5、 修改course表,将“数据处理”的学分改为3学分;
update course
set ccredit=3
where cname='数据处理';
6、 修改CS表,将选修课程“1”的同学成绩加5分;
update sc
set grade=grade+5
where cno=01;
7、 删除数据表student中无专业的学生记录;
delete
from student
where sdept is null;
8、删除数据表course中学分低于1学分的课程信息;
delete
from course
where ccredit<1;
9、按照院系降序显示所有学生的 “院系,学号、姓名、性别、年龄”等信息,其中院系按照以下规定显示:院系为CS显示为计算机系,院系为IS显示为信息系,院系为MA显示为数学系,院系为EN显示为外语系,院系为CM显示为中医系,院系为WM显示为西医系,其他显示为院系不明;
select 院系=case
when sdept='CS' then '计算机系'
when sdept='IS' then '信息系'
when sdept='MA' then '数学系'
when sdept='EN' then '外语系'
when sdept='CM' then '中医系'
when sdept='WM' then '西医系'
else '院系不明'
end,sno 学号,sname 姓名,ssex 性别,sage 年龄
from student
order by sdept desc;
10、查询同时选修“1”号课程和“2”号课程的所有学生的学号;
select sno
from sc
where cno=1
intersect
select sno
from sc
where cno=2;
11、 查询所有院系(要求不能重复,不包括空值),并在结果集中增加一列字段“院系规模”,其中若该院系人数>=5则该字段值为“规模很大”,若该院系人数大于等于4小于5则该字段值为“规模一般”, 若该院系人数大于等于2小于4则该字段值为“规模稍小”,否则显示“规模很小”;
select 院系规模=case
when COUNT(*)>=5 then '规模很大'
when COUNT(*)=4 then '规模一般'
when COUNT(*)>=2 and COUNT(*)<4 then '规模稍小'
else '规模很小'
end,sdept 院系
from student
group by sdept;
12、查询学生信息表中的学生总人数及平均年龄,在结果集中列标题分别指定为“学生总人数,平均年龄”;
select count(*) 学生总人数,AVG(sage) 平均年龄
from student
13、查询选修的课程数大于3的各个学生的选修课程数;
select COUNT(cno) 选修课程数
from sc
group by sno
having COUNT(*)>3;
14、查询IS系学生的学号、姓名、性别、年龄,并统计出IS系的学生个数;
select count(sno) as 人数
from student
where sdept='IS'
go
select sno,sname,ssex,sage
from student
where sdept='IS'
/*本题我用的是go,也可以使用computer方法,主要区别就是server的版本了,
08版的支持computer,12版以上就不支持了*/
15、查询每个院系的学生前两条记录,并组成新表ceshi;
select a.* into ceshi1 from student a
where Sno in (select top 2 Sno from student
where Sdept=a.Sdept
order by Sno desc)
16、查询平均成绩大于“赵菁菁”平均成绩的各个学生的学号、平均成绩;
select sno,avg(grade) 平均成绩
from sc
group by sno
having avg(grade)>(select avg(grade)
from sc
where sno=(select sno
from student
where sname='赵菁菁'
)
);
17、查询选修了‘数学’或者‘大学英语’的学生学号、姓名、所在院系、选修课程号及成绩;
select student.sno,sname,sdept,course.cno,grade
from student,course,sc
where student.sno=sc.sno and sc.cno=course.cno and cname='数学' or cname='大学英语';
18、查询与‘张力’(假设姓名唯一)年龄不同的所有学生的信息;
select *
from student
where sage<>(
select sage
from student
where sname='张力');
19、按照“学号,姓名,所在院系,已修学分”的顺序列出学生学分的获得情况。其中已修学分为考试已经及格的课程学分之和;
select student.sno,student.sname,sdept,sum(course.ccredit) 已修学分
from student,sc,course
where grade>=60 and student.sno=sc.sno and sc.cno=course.cno
group by student.sno,student.sname,sdept;
20、查找选修了至少一门和张力选修课程一样的学生的学号、姓名及课程号;
select student.sno,sname,cno
from student,sc
where cno in (
select cno
from sc,student
where sname='张力' and student.sno=sc.sno) /*通过student.sno=sc.sno连接*/
and student.sno=sc.sno;
/*将表student与表sc连接起来*/
21、查询只被一名学生选修的课程的课程号、课程名;
select course.cno,cname
from course,sc,student
where student.sno in(select sc.sno
from sc
group by sno
having count(cno)='1')
and student.sno=sc.sno and sc.cno=course.cno;
/*三表连接*/
22、使用嵌套查询出选修了“数据结构”课程的学生学号和姓名;
select sno,sname
from student
where sno=(select sno
from sc
where cno=(select cno
from course
where cname='数据结构'));
23、使用嵌套查询查询其它系中年龄小于CS系的某个学生的学生姓名、年龄和院系;
select sname,sage,sdept
from student
where sage< any (select sage
from student
where sdept='cs')
and sdept<>'cs';
/*“<>”表示不等于*/
/*本题用到any方法*/
24、使用ANY、ALL 查询,列出其他院系中比WM系所有学生年龄小的学生的姓名;
select sname 姓名
from student
where sage< all (select sage
from student
where sdept='WM')
and sdept<>'WM'
/*用到all方法*/
25、使用集合查询查询选修1号课程同时选修2号课程的同学的学号与姓名;
select student.sno 学号,sname 姓名
from student,sc
where cno='01' and student.sno=sc.sno
intersect
select student.sno 学号,sname 姓名
from student,sc
where cno='02' and student.sno=sc.sno;
/*集合查询*/
5.视图创建与查询
1、创建v_CS视图,包括CS系各学生的学号、姓名及年龄,要求进行修改和插入操作时仍需保证该视图只有CS系的学生;
create view v_cs
as
select sno,sname,sage
from XSKC.student
where sdept='cs'
with check option;;
2、创建v_CS_age20视图,包括CS系学生年龄在20岁以上的基本信息;并保证对视图文本的修改都要符合年龄大于20这个条件。
create view v_cs_age20
as
select sno,sname,sage,ssex,sdept
from student
where sdept='cs' and sage>20
with check option;
3、创建一个视图vstu_cg,用于查看学生学号、姓名、课程和成绩信息,并用WITH ENCRYPTION加密。
create view vstu_cg
with encryption
as
select student.sno,sname,cno,grade
from student,sc
where student.sno=sc.sno;
4、 试着向视图v_CS中插入一个新的学生记录,(‘200515026’,‘赵红平’,‘21’),是否能插入成功,原因是什么?如何修改视图才可以插入成功?
insert
into v_cs
values('200515026','赵红军','21');
不能插入,因为有with check option语句限制,插入的学生必须是
cs系的,将新建视图的限制条件去掉即可。
5、 利用视图v_CS修改学号为200515001的学生姓名为“赵青青”;
update v_cs
set sname='赵青青'
where sno='200515001';
6、 利用视图v_CS删除CS系学号为200515003的记录;
delete
from v_cs
where sno='200515003';
7、 删除视图v_CS_age20;
drop view v_cs_age20;
6.数据库的完整性约束
use stu
create table kc
(cno int constraint cno_pk primary key,
cname char(20),
cpno int,
ccredit int);
alter table kc
add constraint cname_uk unique (cname);
1.删除student表中记录的同时删除sc表中与该记录sno字段值相同的记录;
2.修改student表某记录的sno时,若sc表中与该字段值对应的有若干条记
录,则拒绝修改;
3.修改course表cno字段值时,该字段在sc表中的对应值也应修改;
4.删除course表一条记录时,若该字段在在sc表中存在,则删除该字段
对应的记录;
5.向sc表添加记录时,如果该记录的sno字段的值在student中不存在,
则拒绝插入;
alter table sc
add constraint sc_fk
foreign key (sno) references student(sno)
on delete cascade on update cascade,
foreign key (cno) references course(cno)
on delete cascade on update cascade
4)定义check约束,要求学生学号sno必须为9位数字字符,且不能以0开头,第二三位皆为0;
alter table student
add constraint sno_ck
check (sno like '[0-9] [0-9] [0-9] [0-9] [0-9] [0-9] [0-9] [0-9] [0-9]' and sno<>'0_ _ _ _ _ _ _ _' and sno like '_00_ _ _ _ _ _')
5)定义stu数据库中student表中学生年龄值在16~25范围内;
CREATE TABLE student
(Sno char(9) Primary Key,
Sname char(8),
ssex char(2),
Sage smallint,
Sdept varchar(20),
CHECK(SAGE>=16 AND ( SAGE<=25) ))
6)定义stu数据库student表中学生年龄值默认值为20;
alter table student
add constraint sage_default
default 20 for sage;
7) 修改student表学生的年龄值约束可以为15~30范围内;
alter table student
add constraint sage_ck
check (sage between 15 and 30)
8) 删除表course中字段cname的唯一值约束;
ALTER TABLE course
Drop constraint cname_uk
7.触发器
create trigger course_insert on course for insert
as
declare @pr_ccredit char(4)
select @pr_ccredit=ccredit from inserted
if @pr_ccredit>7 or @pr_ccredit<1
begin
raiserror('不能插入',16,10)
rollback tran
end
2)为course表再创建一个UPDATE触发器,当更新了某门课程的课程号信息时,就激活该触发器级联更新sc表中相关的课程号信息,并使用PRINT语句返回一个提示信息。
create trigger cno_update on course
after update
as
begin
declare @old_cno char(9),@new_cno char(9)
select @old_cno=cno from deleted
select @new_cno=cno from inserted
update sc set cno=@new_cno where cno=@old_cno
end
3)为student表创建DELECT触发器,在删除中的一条记录的同时将sc表中的相应记录也删除。
create trigger sno_delete on student
after delete
as
begin
delete from sc where sno in(select sno from deleted)
endv
4)创建INSTEAD OF触发器,当向sc表中插入记录时,先检查sno列上的值在student中是否存在,如果存在执行插入操作,如果不存在则提示“该学生不存在”。
create trigger ttble on sc
instead of
insert
as
declare @pr_sno char(9)
select @pr_sno = sno from inserted
if @pr_sno not in(select sno from student)
begin
raiserror('该学生不存在!',6,10)
rollback tran
end
5)比较约束与触发器的执行顺序。(在一个表中创建CHECK约束和触发器,然后向表中插入一条不符合约束和触发器的记录,察看谁先发生作用。)
Insert 语句执行时首先验证约束,同时约束本身也有先后顺序
1 、验证非空约束
2 、验证主键约束
3 、验证唯一性约束
再次验证相关 Check
最后执行触发器,如果触发器中也必须保证不违反相关约束和 Check
1.变量的使用
(1)创建局部变量@xh(char(9))并使用set将student表中“李勇”的学号字段赋给该变量,然后使用select显示变量的值;
declare @xh char(9)
set @xh=(select sno
from student
where sname='李勇')
select @xh
go
(2)计算学生信息表student中学生最高年龄和最低年龄之差,并使用select将结果赋值给@cz,并使用print显示变量的值。
declare @cz float(5)
select @cz=MAX(sage)-MIN(sage) from student
print @cz
2.应用内置函数
(1)求course表中课程号为“03”的课程名称的长度,并在消息提示框中输出结果。结果格式为:“03号课程名称的长度为:**”。提示:使用CONVERT函数。
declare @int int
select @int=len(cname)
from course
where cno=3
print('3号课程名称长度为:'+CONVERT(varchar(4),@int))
(2)使用字符串串联运算符“+”,将student表中的所有字段串联在一起用一个“学生信息”字段显示出来。
select sno+sname+sdept+CONVERT(varchar(4),sage)+ssex as 学生信息
from student
3. 流程控制语句
(1)判断student表中是否存在编号为2005150026的学生,如果存在,则显示该学生基本信息;若不存在,则显示“查无此人”。
if exists(select * from student
where sno='2005150026')
begin
select * from student
where sno='2005150026'
end
else
print('没有此人')
(2)查询学号为“200515002”的学生的平均分是否超过了85分,若超过则输出“XX(学生姓名)考出了高分”,否则输出“XX(学生姓名)考的一般”。
declare @int int,@sum int,@name char(15)
set @int=85
select @sum=AVG(grade)
from sc
where sno=200515002
select @name=sname
from student
where sno=200515002
if @sum>@int
print(@name+'考出了高分')
else
print(@name+'考的一般')
4. 定义函数
(1)定义一个函数CHECK_SNO实现如下功能:对于一个给定的sno值,查询该值在sc表中是否存在,若存在则返回0,否则返回-1。
create function check_sno(@sno char(20))
returns integer as
begin
declare @bool char(20)
if exists(select sno from sc where @sno=sno)
select @bool =0
else
select @bool = -1
return @bool
end
(2)写一段T-sql程序调用上述函数。当向sc表插入一行记录时,首先调用函数CHECK_SNO检索该记录的sno值在表student中是否存在对应值,若存在,则将该记录插入记录(‘200515023’,’02’,75)到sc表中。
DECLARE @num int
SELECT @num=dbo.CHECK_sno('2')
IF @num=0
INSERT sc
VALUES('200515023','02',75)
go
(3)定义一函数,按系别统计当前所有学生的平均年龄,
CREATE FUNCTION aver_age(@sdept char(2))
RETURNS int AS
BEGIN
declare @aver int
select @aver =(select avg(sage) from student where sdept=@sdept)
Return @aver
END
并调用该函数求出“CS”系学生的平均年龄。
declare @sdept char(2)
select @sdept='CS'
select dbo.aver_age(@sdept)
5.存储过程
(1)创建一个无参存储过程pr_StuScore,查询以下信息:班级、学号、姓名、性别、课程名称、考试成绩。
create proc pr_StuScore
as
select *
from sc,student
go
(2)创建一个带参数的存储过程pr_StuScoreInfo2,该存储过程根据传入的学生编号和课程名称查询以下信息:班级、学号、姓名、性别、课程名称、考试成绩。
create proc pr_StuScoreInfo2
@cname char(4),@sno int
as
select *
from student,sc,course
where course.cname=@cname and student.sno=@sno
go
(3)创建一个带参数的存储过程pr_xxscore,该存储过程根据传入的学生编号和课程号,并通过变量输出该学生的课程成绩。
create proc pr_xxscore
@cname char(4),@sno int,@gread int
as
select @gread=sc.grade
from student,sc,course
where course.cname=@cname and student.sno=@sno
print(@gread)
go
(4)创建存储过程,通过给定两个学生的学号,比较两个学生的年龄,若前者比后者高就输出0,否则输出1。(调用时比较200515001号和200515002号的年龄)。
create procedure compa @sno1 char(10),@sno2 char(10),@result int output
as
begin
declare @sage1 int,@sage2 int
set @sage1=(select sage from student where sno=@sno1)
set @sage2=(select sage from student where sno=@sno2)
if @sage1>@sage2
set @result=0
else
set @result=1
end
执行操作:
exec compa '200515001','200515002' ,@result output
select @result
(5)编写带参数的存储过程pr_cavg,根据传入的课程名称统计该课程的平均成绩。
create proc pr_cavg @cname char(6),@avg float
as
set @avg=(select AVG(grade)
from sc,course
where sc.cno=course.cno and course.cname=@cname)
go
(6)创建一存储过程pr_age,用于统计某年龄段所有学生的学号、姓名及所选课程信息。
create proc pr_age
(@maxage int,
@minage int)
as
select a.sno,sname,b.cno,cname,grade
from student a,course b,sc c
where a.sno=c.sno and b.cno=c.cno and sage<@maxage and sage>@minage
执行操作:
exec pr_age 21,15
(7)创建一个添加学生记录的存储过程stduentadd,用来给student表添加一条记
(‘200515028’,‘徐小明’,‘男’,24,‘CS’)
create proc pr_studentadd @sno char(10),@sname char(50),@ssex char(2),@sage int,@sdept char(10)
as
begin
set @sno='200515028'set @sname='徐小明' set @ssex='男' set @sage=24 set @sdept='CS'
insert into student(sno,sname,ssex,sage,sdept)values(@sno,@sname,@ssex,@sage,@sdept)
end
go
==================
作者:@2000亿颗星星
文章:https://mp.csdn.net/mdeditor/90177902#
转载请注明出处哦!:https://mp.csdn.net/mdeditor/90177902#