彻底理解mysql服务器的字符集转换问题
主要参考这三个文章:
https://www.xiariboke.com/article/4147.html
http://blog.sina.com.cn/s/blog_690c46500100k1nf.html
http://www.cnblogs.com/springmvc-hibernate/archive/2010/01/04/2484353.html
1. 字符集以数据库为对象来说, 可以分为数据库内部操作的字符集, (即: character_set_server, database, table,field)和数据库外部的字符集.
1. 其中 character_set_connection是在存储数据库 前的 经过字符集编码转换的 内容. 是 传人字符集. 而character_set_result则是从数据库内部将数据取出来, 发送到客户端时事先经过的编码内容. 是 输出时的字符集.
也就是说, connect的字符集 只是 管 传人的. 不管 输出的 , 而result才是 管输出的.
注意的是, character_set_client这个字符集, 它只是 向服务器 "声明" 说明的 字符集. 但并不表示 从客户端 (比如Php程序编辑器edit vim notepad等) 传入进来的sql 语句就一定是 (真的是) 这个client, 所以 client具有 欺骗性. 本身没有多大必然的用处.. 但也并不是一定用处都没有 : 当 把传入sql语句 存入 数据库之前, 要把sql语句 从 client指定的字符集 -> 转变为connect字符集. 就起这点作用!
所以, 最好不要去隐藏和欺骗服务器, 要尽量将 编辑器的字符集和 client的字符集一致实际上, 所有的问题, 是 不只是要关注 数据库内部 的存储字符集, 还要关注 从 客户端到 服务器的 连接层 的 字符集: 就是 当 sql语句 连接进来后, 服务器收到 sql语句后, 并不是 马上 就进入 数据库进行存储, 而是要 先 放下来, 经过 connect 连接字符集的处理后, 才能 进入数据库. 这里, connect就相当于 数据库 进门时的 门卫和看守, 而character_set_result就相当于数据库 出库输出 内容的出门 时 的 门卫和看守, 都要 经果他们的 转换的!
每天自动对 mysql数据库的备份 shell脚本
备份命令: mysqldump -u root -p db_test > db_name.sql
还原: 有两种方法, 一是 进入mysql后, 执行 source命令;
二是, 还是在 shell下, 执行 mysql命令:mysql -u root -p db_name < db_name.sql
跟登录数据库的命令类似, 只是后面 要加上 ( 数据库名称< 脚本名称 )
推荐 用 第二种 mysql命令, 因为它可以直接在 shell下执行.一个常识: 在命令行操作 mysql的命令(相关命令)时, 一定要加上操作用户和密码选项. 这样mysql服务器才能 决定是否有权执行... 而且 指定密码的 方式是: -p 不要直接写密码值.
mysqladmin 提供了对mysql数据库 从外部的, 状态上的 一个管理, 主要包括这些命令:
mysqladmin [options] command comand [...]
最常见的选项是 -uroot -p 通常都要把这两个选项带上
- create/drop databsename, 只能创建数据库, 不能创建表, 而且不需要用 database这个关键字
- flush-... 刷新各种权限
- password 和 old-password 设置密码;
- 其他辅助命令, ping, processlist. shutdown, status, version, start/stop-slave 从服务器管理.
学会做人生的减法了.
现在就是只 管php和mysq语言了, 太多的东西, 已经不能兼顾了.
要把mysql当作是一个独立的开发语言, 熟悉并能熟练应用 它里面的函数和各种结构的用法.
mysql中的字符串函数包括:
ascii/char : 将数字和字符进行转换的函数. 比如:ascii('abc') 总是转换第一字符, 配合substr可以 查看任何一个字符, char(89)转换数字到字符
cast(变量/字段 as to_type): mysql的类型转换函数, 强制转换;
concat 字符串连接函数: 可以将最终返回字符串 str_ret跟中间 结果的字符串 相连接, 节省一个中间变 量; 可以将数字和数字字符串相连接, 或将数字和字母字符串相连接;
+: 在mysql中,加号总是用来表示 数字相加, 如果是字符串用加号连接, 总是 尽量 /企图 将"数字字符串" 转换成数字, 所以 如果是字母字符串跟数字相加, 则总是将 字母字符串忽略即为0..mysql> select 2a + 3;
ERROR 1054 (42S22): Unknown column '2a' in 'field list'
mysql> select '2a' + 3;
+----------+
| '2a' + 3 |
+----------+
| 5 |
+----------+
1 row in set, 1 warning (0.00 sec)
mysql>
字符串截取函数: left(str, length), right(str, length), substring(str, start, length),
substring_index(str, delimiter, length).
其中, mid, subst函数 是 substring函数的别名alias.
需要注意的是, 所有的mysql的字符串截取函数, 首字符start都是从1开始的. 而不是从0开始的.
uuid()函数, 生成36位的随机字符串: 8-4-4-4-12(个数) 的 随机字符串. 分成5个部分: 8, 4,4,4 , 12.
但是uuid()不适合用来做主键!
replace(str, from, to): replace("abc-amn-axy", 'a", '#'): 结果是: #bc-#mn-#xy.
instr(haystack, needle): 判断needle在hay中的初始出现的位置,从1开始, 如果没有找到则返回0,hay为 null也返回0.
rand()是生成在0和1之间的 随机数. 可以给rand指定一个参数, 作为种子, 那么 rand(seed)会产生固定的相同的随机数, 改变N种子, 也就能够改变随机数.
rand() 函数也不需要 进行播种..
要生成 x~ y之间的随机数, 可以使用: x+(y-x)*rand(); 这个随机数是小数, 还要用 round或floor, ceil来生成整数. 其中 , floor可以得到下限值, 比如x, ceil可以得到 上限值, 比如 y.
2. 只有 “字符”类型的字段,比如char, varchar, text等才需要指定字符集编码和 collate。其他比如 int, boolean等类型类型则不需要指定 字符集.
使用$where = " where 1 "; 然后后面的所有条件语句的拼接都可以 and 的统一形式进行书写, 而不 用去判断是否是第一个条件字符串...
是否可以用 charset 来代替 character set?
在help create table中, 提示的是 : [default] character set [=] charset_name. 当然你可以用 character set utf8 来指定, 但是 你也可以 [肯定是可以的] 用 charset 来指定. 而且即使你用 character set来指定的字符集, 你用show create table foo;来查看, 显示的结果也是 用的 charset...mysql> create table bar(id int not null) character set utf8;
Query OK, 0 rows affected (0.05 sec)
mysql> show create table bar;
+-------+--------------------------------------------------------
------------+
| Table | Create Table
|
+-------+--------------------------------------------------------
------------+
| bar | CREATE TABLE `bar` (
`id` int(11) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8 | ### 这里的字符集指定都是用的 charset这种简写方式, 和 character set 这种全写方式, 完全是一样的!
+-------+--------------------------------------------------------
------------+
1 row in set (0.00 sec)
select 10 where 1; 为什么报错?
where子句, 只能使用 在 对 "数据表"的 操作中! 也就是里面要有表, 要有字段, 否则就会出错.对于where子句来说, 通常是不区分大小写的, 只有在使用 like 条件运算符的时候, 才区分大小写! 如果要区分大小,可以使用 binary关键字, 就是以字节位单位来比较的.
length是按字节来计算的. 而char_length 是按字符个数来计算长度的.
在mysql中的循环语句, 没有/不支持 for 循环语句! 只有while do end while; repeat util end repeat; lp1: loop ... leave lp1...end loop语句!
对于mysql而言, 根本就不需要适用 图形化的 客户端界面, 因为那种方式 效率太低, 不能理解/记忆很多的mysql操作语句, 不能深入理解了解mysql的内在, 所以 直接使用 mysql的命令行控制台客户端, 这是每个linux程序员最基本的素质.
关于select中的rand() 函数的使用??
- 也就是说, select实际上有两个作用, 有两种使用场景: 一是: 纯粹的输出, print, output, 并不牵涉到 "表的 查询" ! 另一种是: 对表的 操作中, 作为 对表的 查询 动作;
- **select语句中, 如果牵涉到 表的 查询, 最好是 不要使 用 rand() 函数, 因为使用rand随机函数时, 会进行多次计算和查询. 通常 应该将确定性的 函数如 max, avg , count等放在 select 对 表的 查询语句中, 然后, 将 rand()函数 用在 跟 查询结果的 四则运算中. **
- 要注意的是, select about_function(rand())语句中, select只是 起到 "输出 "的作用, 并没有 查询的 意思和操作!
比如:select * from student where id > round(rand()*(select max(id) from student))
如果要抽出 多个随机性的记录行结果?
应该使用的方法是: 第一 ,要 能够正确的 适用 rand()函数, 第二, 要在一次查询操作中, 只输出一个 记录行, 然后使用mysql中的循环结构多次输出...
即:
while i< rec_num do
select * from student where id > round(rand()*(select max(id) from student)) limit 1; # id > round(...)的记录有很多个, 我们每次只选择一个limit 1.
end while
但是 这个有可能会取到跟上一次 一样的记录, (同一条记录) 因此, 要判断一下, 当前取出的这条记录的某个关键字(key, 或 primary key) 跟上一条记录的primary key是否是一样的, 如果不是一样的 , 则接收, 同时 计数器i 加1, ... 如果是一样的 , 则不接收, 放弃后面的操作, 同时 i也不要 增加.
set @pre_id=0;
set @cur_id=0;
while i< rec_num do
select id into @sel_id , other_filed into @other_field from user where id > round(rand()*(select max(id) from use)) limit 1;
if @pre_id <> @sel_id then
set i=i+1;
-- 返回 @sel_id, @other_field
end if;
if @pre_id = @cur_id then
-- 此时 循环变量i 不要加1
end if;
end while
在mysql中, 可以直接使用 变量, 而不必 事先定义该变量. 但是一个变量, 如果事先没有声明 初始化赋值, 那么 它的值就是 NULL, NULL跟任何东西运算,都将得到NULL.
MariaDB [test]> select @pre_name;
+-----------+
| @pre_name |
+-----------+
| NULL |
+-----------+
1 row in set (0.00 sec)
MariaDB [test]>
在 select语句中, 给 变量赋值 有两种方式, 即 select ...into, select a:=b
select name into @name from t where...
第二种方法是: select @name2:=name from t where ...
在这两种方法中, 都不需要 事先 声明/定义/初始化 变量 @name @name2等.
注意的是, select中 不能 直接使用 a=b 的方式 来 赋值.
关于mysql中的特殊 常量?
有三个特殊的常量: TRUE, FALSE, NULL
这三个特殊常量, 是不分大小写的! 比如: true, True, 都是和TRUE一样的, 同样null和 Null 更 NULL也是一样的! 在写法上没有区别!
mysql的特殊类型 boolean和 tinyint?
在mysql中, 是没有boolean 类型的. 而true 和 false 是当做 tinyint(1)来处理的, 注意 这里的1, 表示 的是, 只显示一位数! 并不是说它的取值范围.
mysql中的游标cursor 的使用? http://www.cnblogs.com/Luouy/p/7301360.html
mysql中的 循环有三种, while ,和 loop 和 repeat中的 "break 和 continue?"
- loop和 repeat中 就相当于 c/c++语言中的 do ....while(condition...)
- mysql中, 使用 break和continue的对应 关键字 是: iterate 和 leave
- 但是要配合 标号/标识表示: 比如: loop_name: lp:
彻底理解mysql服务器的字符集转换问题的更多相关文章
- mysql服务器的字符集
文章:http://www.cnblogs.com/fantiantian/p/3468454.html 的评论中有这样的文字: 谢谢沧海一滴的总结 在Linux中一般都是UTF-8字符集.我们在建数 ...
- mysql Emoji表情字符集转换
<pre name="code" class="html">Java代码 java.sql.SQLException: Incorrect stri ...
- MySQL字符集转换引发插入乱码问题
根据http://www.cnblogs.com/cchust/p/4601536.html进行验证测试 问题背景 在mysql上面执行一条普通的insert语句,结果报错: Incorrect st ...
- mysql已有数据字符集转换
下面模拟把latin1字符集的数据转换为utf8字符集 一.创建测试表和测试数据: 1.修改会话级别的连接字符集 mysql > set names latin1; 查看一下: 2.创建测试表: ...
- MySQL(一) -- MySQL学习路线、数据库的基础、关系型数据库、关键字说明、SQL、MySQL数据库、MySQL服务器对象、SQL的基本操作、库操作、表操作、数据操作、中文数据问题、 校对集问题、web乱码问题
1 MySQL学习路线 基础阶段:MySQL数据库的基本操作(增删改查),以及一些高级操作(视图.触发器.函数.存储过程等). 优化阶段:如何提高数据库的效率,如索引,分表等. 部署阶段:如何搭建真实 ...
- MySQL 是怎样运行的:从根儿上理解 MySQL:字符集和比较规则
本文章借鉴自https://juejin.im/book/5bffcbc9f265da614b11b731 字符集和比较规则简介 一些重要的字符集 ASCII字符集 共收录128个字符,包括空格.标点 ...
- Mysql基础之字符集与乱码
原文:Mysql基础之字符集与乱码 Mysql的字符集设置非常灵活 可以设置服务器默认字符集 数据库默认字符集 表默认字符集 列字符集 如果某一个级别没有指定字符集,则继承上一级. 以表声明utf8为 ...
- MySql学习(七) —— 查询性能优化 深入理解MySql如何执行查询
本篇深入了解查询优化和服务器的内部机制,了解MySql如何执行特定查询,从中也可以知道如何更改查询执行计划,当我们深入理解MySql如何真正地执行查询,明白高效和低效的真正含义,在实际应用中就能扬长避 ...
- (转)修改及查看mysql数据库的字符集
原文:http://www.cnblogs.com/donqiang/articles/2057972.html Liunx下修改MySQL字符集:1.查找MySQL的cnf文件的位置find / - ...
随机推荐
- 执行字符串或注释代码段的方法(eval、exec、execfile)
eval:计算字符串中的表达式exec:执行字符串中的语句execfile:用来执行一个文件 需注意的是,exec是一个语句,而eval()和execfile()则是内建built-in函数. 1 2 ...
- sqlserver 用一个表的值 更新另一个表
update cas set cas.DocumentHeaderIdOfTransferredForForm = apply.Id from dbo.CaseTransfer cas join db ...
- 2.sklearn库中的标准数据集与基本功能
sklearn库中的标准数据集与基本功能 下面我们详细介绍几个有代表性的数据集: 当然同学们也可以用sklearn机器学习函数来挖掘这些数据,看看可不可以捕捉到一些有趣的想象或者是发现: 波士顿房价数 ...
- javascript(三):对象
对象(object)是javascript中很重要的数据类型.对象是“键值对”的集合,同时也是无序的.(注意:对象结尾处有分号) var ob1={ a1:'name',//a1可以加引号或者不加 a ...
- 谈谈CSS中一些比较"偏门"的小知识
前面我写了:谈谈html中一些比较"偏门"的知识,现在这篇(主要)想谈谈个人所见的CSS一些小知识点,加深印象:同时也希望有需要的人能有收获! 1.常见的浏览器内核: 以IE为代表 ...
- html5-div布局
<!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8&qu ...
- 20155228 2017-5-10 课堂测试:Arrays和String单元测试
20155228 2017-5-10 课堂测试:Arrays和String单元测试 题目和要求 在IDEA中以TDD的方式对String类和Arrays类进行学习 测试相关方法的正常,错误和边界情况 ...
- Windsor
https://github.com/castleproject/Windsor https://github.com/castleproject/Windsor/blob/master/docs/R ...
- QT 继承QWidget && 继承QDialog
工作项目中,利用到Qt对话框,场景需求: 1. 一部分窗体需要继承自QWidget 2. 一部分窗体需要继承自QDialog 3. 两者均需要去掉标题栏图标,同时能够自由拖动. 如果两者分开继承实现, ...
- c++学习笔记(六)- vector使用和内存分配
-----------------------------2019/01/15------------------------------- 复习了下迭代器,其实c++参考里讲的很清楚,主要需要辨析规 ...