C语言也能干大事第十三节(如鹏基础)
这门课和《数据库原理》的关系,这门课是对《数据库原理》的应用,通过这门课将能够学会数据库原理的实际应用,不再云里雾里。即使没学过《数据库原理》也没关系,这门课并不假定大家学过《数据库原理》,相当于预习效果。
企业里数据库开发是很大的一部分,不会什么也要会数据库开发。
开发环境的搭建:
(1)如鹏版绿色MYSQL的下载(请使用迅雷下载):http://down1.rupeng.com/download/software/RuPengGreenMYSQL.rar
(2)ODBC连接MYSQL的驱动MYODBC下载:http://www.onlinedown.net/soft/9698.htm
(3)管理工具SQLyog下载:http://www.baidu.com/baidu?word=SQLyog
依次安装三个软件。如鹏版绿色MYSQL的使用,使用SQLyog连接数据库。
注意:如果初始化MYSQL以后移动了MYSQL的文件夹,那么需要重新运行“运行前先初始化.exe”。
1、执行“启动MySQL.bat”
2、运行SQLyog。如鹏版MYSQL,用户名密码都是root。
什么是数据库,数据库能做什么?
可以记录到文件中,比如:
姓名 年龄 工号 职位
Kider 20 001 超版
CALF 21 002 版主
劣势:
1、必须对文件操作非常熟悉
2、比如对算法非常熟悉;一旦算法不好的话很容易造成性能问题。
3、并发操作。
广义的来讲,能够存储数据的地方都可以叫数据库。DBMS(DataBase Management System,数据库管理系统),由DBMS来负责管理数据,使用者只要“描述”要进行什么操作就可以了,DBMS相当于仓库管理员,只要向仓库管理员发出命令就可以,他怎么做我们不用关心,只要告诉他What To Do(要做什么),不关心How To Do(怎么做)。
DBMS和数据库的关系。大家都很懒,所以很多时候说数据库其实指的是DBMS。行业内的潜规则。
不同的仓库管理员有自己的不同的优势。不同品牌的DBMS也有自己的不同的特点。
MYSQL、MSSQLServer、DB2、Oracle、Access。。。
OS/2
Sybase SQLServer、Microsoft SQLServer
主流数据库(DBMS)有哪些?
SQL<>SQLServer<>MSSQLServer。最常见的错误。行业内的潜规则。
和仓库管理员打交道的方式:1、跑过去和他说;2、打电话;3、通过电脑传递信息(自动化的方式);
操作数据库的两种方式:管理工具和程序代码。
什么是Catalog(分类)(数据库、表空间)
表(Table)
把仓库分成不同的区域。不同的区域放不同类型的物品。
将一个数据库(Catalog)分成不同的表,每个表放不同的数据。公司机密信息数据库:发票信息;合同信息;公司帐号;。。。。建不同的表。
列(Column)
已经将生肉放到单独的生肉区域里,每块肉都有不同的特性,取肉部位、重量。。。。为每块肉都贴一个标签,
规定每一列的格式,重量应该是数字。生产日期应该是日期类型。数据类型(DataType),Int、Char、double一个道理。
数据库,表、列、数据类型、记录。
SQLYog中左边是数据库。
Int:整数;varchar:字符串(String),Var(可变的),Char(字符);
Boolean、char、date
怎么使用Varchar,要指定长度,就像申明char buff = new char[200]
使用工具创建数据库表,插入一条记录。表的命名规则、字段命名规则。常见数据类型说明。
下节课内容:SQL语句、数据的增删改查。
课下参考《程序员的SQL金典》进行深一步的学习和预习。
本课程的参考教材:杨中科的《程序员的SQL金典》第三章
什么是SQL语句。SQL语句是和DBMS“交谈”专用的语句,和C、Java等的代码不一样,SQL语句你需要你告诉DBMS What To Do就可以,不需要告诉它How To Do。
本课程的命名规范:所有表以T_开头,字段(列、Column、Field)以F开头,这样可以很容易的看清哪个是表、哪个是字段。而且不容易和关键字冲突。
增删改查:Insert、Delete、Update、Select。
SQL语句是大小写不敏感的
1、简单的Insert语句。向数据库中插入数据。Into后的列名和values一一对应,字符串用单引号
Insert Into T_Person(FName,FAge) values('Jim',25)
Insert into T_Person(FName) values('lily')
2、怎么样查看表中数据
Select * from T_Person
Select * from 表名
3、简化的Insert语句格式,不推荐
Insert into T_Person values('poly',33)
4、数据的更新Update
Update T_Person Set FAge=30
5、多字段更新
6、带Where语句的Update
update T_Person Set FAge=50 where FName='Tom' OR FName='Jim'
7、数据的删除
Delete From T_Person
是删除T_Person表中的数据,并不是删除T_Person整个表结构。表还在,数据没了,人去楼空。
8、带Where语句的删除
delete from T_Person where FName='Jim'
delete from T_Person where FAge>30
下节课内容:数据的检索。
《C语言也能干大事》第十六节
数据库开发3
本课程的参考教材:杨中科的《程序员的SQL金典》第四章
1、SELECT基本用法
a)
检索所有列、检索指定列
b)
按条件过滤。通配符、Between and
select * from T_Employee where FSalary>4000 and FSalary<8000
select * from T_Employee where FSalary BETWEEN 4000 And 8000
c)
数据汇总
select SUM(FSalary),AVG(FSalary),MAX(FSalary),MIN(FSalary) from T_Employee
select SUM(FSalary),AVG(FSalary),MAX(FSalary),MIN(FSalary) from T_Employee where FSalary<8000
select COUNT(*) from T_Employee where FSalary>5000。满足条件的数据个数
d)
排序
Ascending:ASC,升序
Descending:Desc,降序
select * from T_Employee order by FSalary desc
2、C语言中访问数据库
a)
ODBC简介。ODBC是微软提供的访问数据库的一种标准接口,通过ODBC可以连接MSSQLServer、MYSQL、DB2、Oracle、Access等各种数据库,通过统一的函数进行访问,也就是访问各种数据库都可以使用统一的函数。屏蔽了连接不同数据库的差异性。
b)
除了ODBC之外还有ADO、ADO.net等,Java中有JDBC等。都有连接、结果集、游标、事务、参数化SQL等概念,一通百通。
c)
没安装MYODBC(MYSQL的ODBC驱动)的首先安装MYODBC。http://down1.rupeng.com/download/software/MYODBC.rar
d)
sql.h、sqlext.h、sqltypes.h
e)
添加连接库“odbc32.lib odbccp32.lib”。如果使用的是rupeng的DialogBased向导则已经自动添加。如果使用其他向导或者C-Free、PellesC等开发工具,则需要手动添加
f)
看模板代码。不用关心每个函数,用的时候copy以后改一改就可以,理解只要流程、主要概念即可,不要深究。有兴趣的可以研究CHECKDBSTMTERROR宏的实现。
g)
访问数据库可能遇到的错误:连接错误、执行错误。
h)
连接数据库、执行SQL、断开连接。连接字符串。数据库错误处理。
SQLHDBC hdbc:代表一个数据库连接句柄。和Socket里边的Socket连接类似,要访问数据库,先要连接到数据库。SQLHDBC:SQL、H句柄、DB(DataBase)、C(Connection)
SQLHSTMT hstmt:代表一个SQL语句。STMT(Statement,语句)
SQLRETURN:执行结果。
ODBC中字符串用SQLCHAR,SQLCHAR其实就是char的别名。
SQLCHAR ConnStrIn[MAXBUFLEN]和char ConnStrIn[MAXBUFLEN]一样。
ConnStrIn:连接字符串,你要连接到的数据库的驱动、ip地址、用户名密码、数据库名(Catalog)等等都在连接字符串里描述。DRIVER:使用的驱动名;SERVER:ip地址;UID:用户名(UserID);PWD(Password):密码。DataBase:数据库名,Catalog。
SQLDriverConnect:创建到数据库的连接,使用ConnStrIn连接。result表示执行结果。如果失败了SQL_ERROR==result。ShowDBConnError(hwnd,hdbc);来显示“连接错误”。
result = SQLPrepare(hstmt,(SQLCHAR*)"insert into T_Person(FAge,FName) values(20,'kider')",SQL_NTS)。创建SQL语句的句柄。
result =SQLExecute(hstmt);:执行SQL语句。
SQLFreeStmt(hstmt,SQL_CLOSE);:释放SQL语句
SQLDisconnect(hdbc);:断开数据库连接。
课下参考《程序员的SQL金典》进行深一步的学习和预习。
模板代码:
购买此贴后可以得到整个工程的源代码:
1
2 #include "stdafx.h"
3 #include <windows.h>
4 #include <windowsx.h>
5 #include <sql.h>
6 #include <sqlext.h>
7 #include <sqltypes.h>
8 #include "resource.h"
9 #include "MainDlg.h"
10 #define LOGIN_TIMEOUT 30
11 #define MAXBUFLEN 255
12 #define CHECKDBSTMTERROR(hwnd,result,hstmt) if(SQL_ERROR==result){ShowDBStmtError(hwnd,hstmt);return;}
13
14 BOOL WINAPI Main_Proc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
15 {
16 switch(uMsg)
17 {
18 HANDLE_MSG(hWnd, WM_INITDIALOG, Main_OnInitDialog);
19 HANDLE_MSG(hWnd, WM_COMMAND, Main_OnCommand);
20 HANDLE_MSG(hWnd,WM_CLOSE, Main_OnClose);
21 }
22 return FALSE;
23 }
24 BOOL Main_OnInitDialog(HWND hwnd, HWND hwndFocus, LPARAM lParam)
25 {
26 return TRUE;
27 }
28 void Main_OnCommand(HWND hwnd, int id, HWND hwndCtl, UINT codeNotify)
29 {
30 switch(id)
31 {
32 case IDC_OK:
33 DBTest(hwnd);
34 break;
35 default:
36 break;
37 }
38 }
39 void Main_OnClose(HWND hwnd)
40 {
41 EndDialog(hwnd, 0);
42 }
43 void ShowDBError(HWND hwnd,SQLSMALLINT type,SQLHANDLE sqlHandle)
44 {
45 char pStatus[10], pMsg[101];
46 SQLSMALLINT SQLmsglen;
47 char error[200] = {0};
48 SQLINTEGER SQLerr;
49 long erg2 = SQLGetDiagRec(type, sqlHandle,1,
50 (SQLCHAR *)pStatus,&SQLerr,(SQLCHAR *)pMsg,100,&SQLmsglen);
51 wsprintf(error,"%s (%d)\n",pMsg,(int)SQLerr);
52 MessageBox(hwnd,error,TEXT("数据库执行错误"),MB_ICONERROR|MB_OK);
53 }
54 void ShowDBConnError(HWND hwnd,SQLHDBC hdbc)
55 {
56 ShowDBError(hwnd,SQL_HANDLE_DBC,hdbc);
57 }
58 void ShowDBStmtError(HWND hwnd,SQLHSTMT hstmt)
59 {
60 ShowDBError(hwnd,SQL_HANDLE_STMT,hstmt);
61 }
62
63 void DBTest(HWND hwnd)
64 {
65 SQLHENV henv = NULL;
66 SQLHDBC hdbc = NULL;
67 SQLHSTMT hstmt = NULL;
68 SQLRETURN result;
69 SQLCHAR ConnStrIn[MAXBUFLEN] = "DRIVER={MySQL ODBC 5.1 Driver};SERVER=127.0.0.1;UID=root;PWD=root;DATABASE=test;CharSet=gbk;";
70 SQLCHAR ConnStrOut[MAXBUFLEN];
71 //分配环境句柄
72 result = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &henv);
73 //设置管理环境属性
74 result = SQLSetEnvAttr(henv, SQL_ATTR_ODBC_VERSION, (void*)SQL_OV_ODBC3, 0);
75 //分配连接句柄
76 result = SQLAllocHandle(SQL_HANDLE_DBC, henv, &hdbc);
77 //设置连接属性
78 result = SQLSetConnectAttr(hdbc, SQL_LOGIN_TIMEOUT, (void*)LOGIN_TIMEOUT, 0);
79 //连接数据库
80 result = SQLDriverConnect(hdbc,NULL,
81 ConnStrIn,SQL_NTS,
82 ConnStrOut,MAXBUFLEN,
83 (SQLSMALLINT *)0,SQL_DRIVER_NOPROMPT);
84 if(SQL_ERROR==result)
85 {
86 ShowDBConnError(hwnd,hdbc);
87 return;
88 }
89 //初始化语句句柄
90 result = SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt);
91 //SQL_NTS telling the function the previous parameter is Null-Terminated String,
92 //please alculate the string length for me
93 result = SQLPrepare(hstmt,(SQLCHAR*)"insert into T_Person(FAge,FName) values(20,'kider')",SQL_NTS);
94 CHECKDBSTMTERROR(hwnd,result,hstmt);
95 result =SQLExecute(hstmt);
96 CHECKDBSTMTERROR(hwnd,result,hstmt);
97 SQLFreeStmt(hstmt,SQL_CLOSE);
98 SQLDisconnect(hdbc);
99 SQLFreeHandle(SQL_HANDLE_DBC,hdbc);
100 SQLFreeHandle(SQL_HANDLE_ENV,henv);
101 MessageBox(hwnd,TEXT("执行成功"),TEXT("标题"),MB_OK);
102 }
购买此贴后可以得到全部源代码的下载
板书:
1、处理数据库查询
序号从1开始,不是0
1
2
3 SQLINTEGER cbsatid=SQL_NTS;
4 while (SQLFetch(hstmt)!=SQL_NO_DATA_FOUND)
5 {
6 SQLCHAR name[20];
7 SQLGetData(hstmt,1,SQL_C_CHAR,name,20,&cbsatid);
8 }
9
复制代码
10
11 SQLINTEGER cbsatid=SQL_NTS;
12 while (SQLFetch(hstmt)!=SQL_NO_DATA_FOUND)
13 {
14 SQLINTEGER i;
15 SQLGetData(hstmt,2,SQL_C_LONG,&i,sizeof(SQLINTEGER),&cbsatid);
16 }
复制代码
乱码问题解决方式,连接字符串使用GBK,修改数据库默认编码为gbk
4、保存HDBC到全局变量中,长连接、短连接。比如Java、C#中访问数据库复杂多少。一通百通。
要掌握调试的技巧,分析问题可能出错的原因和出错的地方,然后调试分析。一定不能和书上不一致,就懵了
5、自己动手写用户管理系统:新增密码字段、新建用户,检验登录;
17 <font face="宋体"><font style="font-size: 12pt">
18 SQLINTEGER cbsatid=SQL_NTS;
19 //需要一行一行的读取,这种方式就叫做通过游标读取,无论是在JDBC、ADO/ADO.net。。。结果集
20 //调用SQLFetch一次就向下读取一行,直到返回值为SQL_NO_DATA_FOUND的时候表示读到了最后
21 //是不是和C语言文件访问中EOF有点像。
22 while (SQLFetch(hstmt)!=SQL_NO_DATA_FOUND)
23 {
24 TCHAR name[20]; //字符数组,SQLCHAR其实就是char的一个别名,所以和char name[20]一样。
25 //调用SQLGetData来取列(Column)的内容
26 //第一个参数就是代表SQL语句的hstmt、第二是要读取的列的序号(从1开始)
27 //第三个是列的类型(SQL_C_CHAR字符串,在SQLExt.h中所有以SQL_C_开头的都是可选值)
28 //第四个参数就是要接收的值的指针!!!
29 //第五个是指针指向的缓冲区的大小
30 //第六个不用管,那么调就行
31 SQLGetData(hstmt,1,SQL_C_CHAR,name,sizeof(name)/sizeof(SQLCHAR),&cbsatid);
32 MessageBox(hwnd,name,TEXT(""),MB_OK);
33 }
34
35 while (SQLFetch(hstmt)!=SQL_NO_DATA_FOUND)
36 {
37 SQLINTEGER i; //字符数组,SQLCHAR其实就是char的一个别名,所以和char name[20]一样。
38 //调用SQLGetData来取列(Column)的内容
39 //第一个参数就是代表SQL语句的hstmt、第二是要读取的列的序号(从1开始)
40 //第三个是列的类型(SQL_C_CHAR字符串,在SQLExt.h中所有以SQL_C_开头的都是可选值)
41 //第四个参数就是要接收的值的指针!!!
42 //第五个是指针指向的缓冲区的大小
43 //第六个不用管,那么调就行
44 SQLGetData(hstmt,2,SQL_C_LONG,&i,sizeof(i),&cbsatid);
45 TCHAR name[20];
46 SQLGetData(hstmt,1,SQL_C_CHAR,name,sizeof(name)/sizeof(TCHAR),&cbsatid);
47 TCHAR s[20];
48 wsprintf(s,TEXT("%s年龄是:%d"),name,i);
49
50 MessageBox(hwnd,s,TEXT(""),MB_OK);
51 }
52 result = SQLPrepare(hstmt,(SQLCHAR*)"select FUserName,FPassword from T_User",SQL_NTS);
53 CHECKDBSTMTERROR(hwnd,result,hstmt);
54 result =SQLExecute(hstmt);
55 CHECKDBSTMTERROR(hwnd,result,hstmt);
56 SQLINTEGER cbsatid=SQL_NTS;
57 TCHAR inputUserName[20];
58 GetDlgItemText(hwnd,IDC_EDITUSERNAME,inputUserName,sizeof(inputUserName)/sizeof(TCHAR));
59 TCHAR inputPassword[20];
60 GetDlgItemText(hwnd,IDC_EDITPASSWORD,inputPassword,sizeof(inputPassword)/sizeof(TCHAR));
61
62 BOOL found=FALSE;
63 while (SQLFetch(hstmt)!=SQL_NO_DATA_FOUND)
64 {
65 TCHAR userName[20];
66 SQLGetData(hstmt,1,SQL_C_CHAR,userName,sizeof(userName)/sizeof(TCHAR),&cbsatid);
67 TCHAR password[20];
68 SQLGetData(hstmt,2,SQL_C_CHAR,password,sizeof(password)/sizeof(TCHAR),&cbsatid);
69 if(0==lstrcmp(inputUserName,userName))
70 {
71 if(0==lstrcmp(inputPassword,password))
72 {
73 MessageBox(hwnd,TEXT("输入正确,登陆成功!"),TEXT("提示"),MB_OK);
74 found = TRUE;
75 break;
76 }
77 }
78 }
79 if(FALSE==found)
80 {
81 MessageBox(hwnd,TEXT("输入错误"),TEXT("报错"),MB_OK|MB_ICONERROR);
82 }
83 </font></font>
缺点是???
数据量大了以后运行速度很慢。比如说咱们如鹏100万会员。
Wsprintf
课下作业:
(1)
细化报错信息:当用户名不存在的时候提示“用户名不存在”,当用户名存在而密码错误的时候报告“密码错误”。
(2)
保存用户的时候,如果用户已经存在则更新已有的用户信息;否则新增用户信息。
(3)删除指定用户名的用户;
(4)有能力的同学研究ListView控件的使用,列出当前数据库中的所有用户信息,选择某个用户可以删除、可以更新。
下节课内容:
作业点评:ListView控件的使用与用户管理系统。
SQL注入漏洞及参数化SQL
C语言也能干大事第十三节(如鹏基础)相关推荐
- 如鹏网C语言也能干大事精华帖
如鹏网 http://www.rupeng.com/ 1.尘封 俄罗斯方块 hity 俄罗斯方块 小马_xiao 由写俄罗斯方块引发的种种 2.Diao_Cow 很funny的程序 ...
- c语言开发网站教程,C语言也能干大事之C语言开发网站教程
教程名称:C语言也能干大事之C语言开发网站教程 课程简介: 本章主干知识点:现在做桌面窗口程序开发的工作已经不多了,目前企业需求量最大的技术是"网站开发".因此发布一套<C语 ...
- 【C语言也能干大事】第五讲 组合框控件,下拉列表
获得组合框控件的句柄 HWND hwndCombo1 = GetDlgItem(hwnd, IDC_COMBO1); 确定目前选项的索引 int curSel = ComboBox_GetCurSel ...
- php能做的事,PHP也能干大事 随机函数
写在前面 PHP也能干大事是我总结的PHP语法特性及相关函数类库的经典用法,并不一定是真正能实现四两拨千斤的功效,但是掌握这些方法,可以在你的工作和学习上有一些帮助,希望大家能集思广益,将<PH ...
- C 语言究竟能干什么
C语言究竟能干什么 序言 鉴于现在已经大三了,很多同学很迷茫,自己学的东西到底能做什么,将来自己到底能干什么?我不想看着同学迷茫的面孔, 特别是几个好兄弟,有几个想学习编程,但又苦苦找不到门路的兄弟, ...
- c++ 结构体赋值_《零基础看得懂的C语言入门教程》—(十二)结构体是这么回事
一.学习目标 了解C语言的结构体的使用方法 了解C语言结构体的结构的赋值 了解多种C语言结构体变量的赋值方法和取值方法 目录 <零基础看得懂的C语言入门教程>--(二)简单带你了解流程 & ...
- Python编程基础:第五十三节 匿名函数Lambda Function
第五十三节 匿名函数Lambda Function 前言 实践 前言 匿名函数是一种非常优雅的表达方式,它可以将函数定义用一行代码进行表示.其书写方式为参数列表:函数实现,其中多个参数之间用逗号隔开, ...
- Python编程基础:第四十三节 多继承Multiple Inheritance
第四十三节 多继承Multiple Inheritance 前言 实践 前言 多继承是指一个子类可以拥有多个父类,其所有父类的属性和方法都能被其调用.其中多个父类之间用逗号隔开. 实践 我们先定义两个 ...
- Python编程基础:第三十三节 文件复制Copy a File
第三十三节 文件复制Copy a File 前言 实践 前言 当我们需要将一个文件中的内容复制到另一个文件中时,就需要用到copyfile()函数,该函数一共有两个参数copyfile(src, ds ...
- Python编程基础:第二十三节 嵌套函数调用Nested Functions Calls
第二十三节 嵌套函数调用Nested Functions Calls 前言 实践 前言 当一个函数的返回结果是另一个函数的输入的时候,我们就可以采用嵌套调用的方式来书写代码.举例来说,y=f(x)=x ...
最新文章
- unix odbc php 连接sqlserver,Ubuntu下通过unixODBC连接MS SqlServer2005
- 题解-bzoj4221 JOI2012kangaroo
- python 文件读取报错 ‘utf-8‘ codec can‘t decode
- python卸载opencv_20.Windows python,opencv的安装与卸载
- python爬虫实战(1)——爬取知乎热门回答图片
- Lecture Notes: Macros
- Python优化算法01——差分进化算法
- tftpd获取文件失败
- Three.js图像波动特效
- roms netcdf结构体用法(弃用)
- 全球与中国粒子测量系统市场现状及未来发展趋势
- QQ空间日志导出(php)
- 一个low逼的boofuzz脚本生成器
- Super Socks5cap使用教程
- ctf-web入门-php特性
- 注册好ChatGPT帐号了,按照教程很快搞定
- 使用docker构架服务 jekyll 和 java应用程序
- 0111总结-函数与极限-高等数学
- 人民币大写与数字互转
- ESP8266_21基于ESP8266的一键配网