Tips for SQL and Bash

本文详细介绍了Oracle数据库的基本概念、SQL语法特点、数据管理与查询技巧,对比了MySQL的安装配置与管理方式,并深入探讨了Shell脚本语言的基础用法与实践案例。
Database and Linux shell:
#Oracle#
Oracle服务器: Oracle数据库(磁盘)和 Oracle实例(内存)
Oracle集群(cluster): 一个数据库映射多个实例副本(负载均衡,失败迁移)
oracle的方案:基于用户的管理方案
ordinary user login: sqlplus scott/11
super user login: sqlplus /nolog ;      connect /as sysdba
look up what tables under user: select * from tab
null value problem: 
1 the result of operation between any number and null is null
2 null value is not null: null!= null
filter null function: nvl(a,b),when a is null,return b,ps: this b can be number or string,the following is a sql example: select ename,empno,job,sal,nvl(sal*12+comm,0) from emp;
伪表: select sysdate from dual;    || 连接符       distinct 去重,可修饰多个字段
modify format of Date: alter session set NLS_DATE_FORMAT=‘yyyy-mm-dd’;
where 子句中单引号里边的字符串区分大小写;
转义字符使用: select * from emp where ename like ‘%\_%’ escape ‘\’;
order by 后面+列名  表达式  别名  序号
当order by 遇上空值: 把空的记录最后显示
 select empno,ename,comm from order by 3 desc nulls last
遭遇多列时,select * from emp order by deptno desc,sal desc;先按deptno排,当deptno相等时,再按照sal排序
oracle 支持隐藏类型转换
单行函数(一条输入记录,一条输出):listed following
字符函数 example: select insti(‘winbox’,’box’) 求子串位置 from dual;   
数字函数 example: select round(88.868,2) 四舍五入,trunc(66.316,2) 截断,mod(1600,300) 求余 from dual;
日期函数 example: select ename,MONTHS_BETWEEN(sysdate,hiredate) 精确算月数 from emp
通用函数
条件表达式(做报表)example: 
给员工涨工资,总裁1000    经理800    其他涨500  列出前后工资  
select ename,job,sal 涨前工资,( case job when ‘PRESIDENT’ then sal+1000
   when ‘MANAGER’ then sal+800
   else sal+500
)涨后工资  from emp;
oracle 独有方法: 将括号中case ..when..then..结构 替换成
decode(job,’PRESIDENT’,sal+10000,’MANAGER’,sal+800,Sal+500)
多行函数 (多条输入记录,一条输出):
分组函数:select .. from .. where col in ..    col >    col between a and b  
    group by .. having.. order by ..
组函数能自动过滤空值:select count(comm),count(*) from emp;
难点:分组检索  :  select a,b,c from t group by a,b,c,d
注意事项: 1  除了组函数外,select检索的列必须要位于group by 后面的集合列中
            2  组函数设计的本意就是必须要在分组数据之上进行结果集的检索
求各个部门每个工种的平均工资:
select deptno,job,avg(sal),count(deptno) from emp group by deptno,job order by 1
having 和 where子句区别(sql优化问题)
求10号部门的平均工资:
先分组再过滤:select deptno,avg(sal) from emp group by deptno having deptno=10
先过滤再分组(效率高):select deptno,avg(sal) from emp where deptno=10 group by deptno 
尽量不要用*,以减少列名翻译开销;
oracle解析逻辑表达式的方向是从右往左,where子句中过滤记录最多的条件应放在最右边;
多表查询:(笛卡尔乘积:行数相乘,列数相加)
不等值连接: select e.empno,e.ename,e.sal,s.grade from emp e,salgrade s where e.sal>=s.losal and e.sal<=s.hisal;
外连接(处理等值条件不成立情况): eg: 统计各部门的员工人数
(注意有些部门新成立没有人的情况)
select d.deptno,d.dname,count(e.empno) from dept d,emp e where d.deptno=e.deptno(+) group by d.deptno,d.dname;   note:当+号出现在=式右边,为左外连接,反之右外连接
自连接: eg: 显示各员工的上级信息,老板显示其自己
select e.ename || ‘的老板:’ || nvl(b.ename,’他自己’) from emp e,emp b where e.mgr=b.empno(+);
子查询(涉及两次以上的查询,效率比多表查询低): eg: 查询部门是sales的员工信息
方法一: select * from emp where DEPTNO = (select deptno from dept where dname=‘sales’);
方法二: select e.* from emp e,dept d where e.deptno = d.deptno and d.name=‘SALES’;
group by 和order by子句中不能出现子查询,select 子句只能出现单行子查询
查询最低工资大于50号部门的部门编号,并显示其最低工资
select department_id,min(salary) from employees group by department_id having min(salary)>(select MIN(salary) from employees where department_id =50);
多行操作符(返回多行,用于多行比较操作): IN      ANY      ALL
eg: 查询比30号部门所有人薪资都高的员工信息
select * from emp where sal > all(select sal from emp where deptno =30);
当子查询遇上null: eg: 查询不是经理的员工信息: 
select * from emp where empno not in (select mgr from emp where mgr is not null);
任何参数与null进行逻辑运算都是假;eg: column !=null
rownum: 结果集的行号,从第一行动态逐行生成;只能用<=或者<,不能用>或者>=;
oracle分页规律: 三层嵌套查询 :内层排序外层选,中层前n改别名
example: 查询薪资排在5到8名的员工信息:   select r,empno,ename,sal from 
                              (select rownum r,empno,ename,sal from 
(select empno,ename,sal from emp order by sal desc) where rownum <=8) where r>=5;
查询薪资大于本部门平均工资的员工:
select e.empno,e.ename,e.sal,d.avgsal from emp e,(select deptno,avg(sal) avgsal from emp group by deptno) d where e.deptno = d.deptno and e.sal>d.avgsal;
相关子查询(多值子查询):执行依赖于外部查询的数据,外部查询一次,子查询一次。
DML: 批量插入数据  eg: 把10号部门的员工拷贝到另外一个表中
create table emp10 as select * from emp where 1=2;
insert into emp10 select * from emp where deptno =10;
savepoint a;设置保存点,方便回滚;
Oracle默认事务隔离级别:read committed,同时支持serializable,并自创read-only隔离级别
Mysql默认事务隔离级别: repeatable read;
DDL: 管理数据库的对象: 表 视图 索引 序列 同义词 约束(…)
创建一个表的两个条件: 权限和表空间

#Mysql#
mysql的安装:
--这里要注意一个问题,就是设置MySQL的自启动。 如果使用native package来安装,会自动设置为自启动,如果使用其他的方式,如source,binary和RPM,就需要单独的来设置自启动。
1 查询服务器上已经安装的mysql
rpm -aq | grep mysql
2 卸载旧的版本
rpm -e mysql --nodeps --allmatches (不理会依赖关系,删除所有上一步查出来的相同的mysql)
[root@localhost home]#  rpm -e mysql-connector-odbc-3.51.26r1127-1.el5 --nodeps --allmatches
[root@localhost home]#  rpm -e libdbi-dbd-mysql-0.8.1a-1.2.2 --nodeps --allmatches
[root@localhost home]#  rpm -e mysql-server-5.0.77-3.el5 --nodeps --allmatches
[root@localhost home]# rpm -aq | grep mysql
[root@localhost home]# 
3 将老版本的几个文件手工删除
#rm -f /etc/my.cnf
#rm -rf /var/lib/mysql
#rm -rf/var/share/mysql
# rm -rf/usr/bin/mysql*
4 上传mysql的安装包
MySQL-client-advanced-5.6.20-1.el6.x86_64.rpm
MySQL-devel-advanced-5.6.20-1.el6.x86_64.rpm
MySQL-server-advanced-5.6.20-1.el6.x86_64.rpm
5 安装服务器和客户端
#rpm -ivh MySQL-server-advanced-5.6.****-1.el6.x86_64.rpm
#rpm -ivh MySQL-client-advanced-5.6.****-1.el6.x86_64.rpm
说明:不安装mysql-client是不能使用mysql工具登陆到mysql数据库
6 oracle收购Mysql后,新版的mysql刚安装完mysql后不能直接输入mysql登录数据库,
而是设置了默认free password密码,默认密码放在了/root/.mysql_secret文件中,登陆后需要修改密码
7 修改密码
(1)查看文件寻找密码
vi /root/.mysql_secret
(2)登陆Mysql
linux mysql 服务启动和关闭
service mysql start service mysql stop
登陆服务器
mysql -u root -p
mysql -uroot -p123456
(3)修改密码
mysql> set password=password('123456') ; 
也可以使用脚本 /usr/bin/mysql_secure_installation进行交互式的修改mysql的root密码。
mysql基于数据库的管理,一般开发人员针对每一个应用创建一个数据库;
show databases;显示所有数据库
创建一个使用utf-8字符集并带校对规则的mydb3数据库:
create database mydb3 character set utf8 collate utf8_general_ci;
将1到5条记录划分到班级一:update student set classid = 1 where id>=1 and id<=5; 
左外连接: eg(标准写法): select d.deptno,d.dname,count(e.empno) from dept d left outer join emp e on d.deptno group by d.deptno,d.dname;
连接符||在mysql不能用,concat函数替代,nvl也不支持,ifnull替代;
mysql乱码问题: mysql有六处使用了字符集,分别是client,connection,database,results,server,system;
显示当前字符集: show variables like ‘character%’;
解决方法:保持客户端,服务器,连接的编码一致;
事务控制:mysql默认自动提交事务(每执行一次sql语句自动提交事务)。

#Shell#
Shell 是一种基于函数的服务器脚本语言;
帮助命令:   man   命令
外壳程序(解析器),bash是sh的升级版;
权限:-rwxrw-r- - 给当前用户加可执行权限: chmod u+x t.c 
权限实现原理:umask(掩码过滤);
shell文件头:#!/bin/bash
脚本调用机制:shell进程启动bash进程,bash加载你编写的shell进程,一共三个进程;
shell特性: 别名,管道,命令替换,重定向,后台处理,模式匹配,变量,特殊字符
别名(命令替换):alias
管道(前边命令的输出作为后边命令的输入):|  eg: ps -aux | grep httpd
后台命令:nohup   eg:nohup tar -cvf 111.tar.gz &  同时可以运行多个后台命令
jobs -l   可以查看正在运行的命令
模式匹配: eg: ls *.out
重定向(输入输出到文件): eg: ls -l ant.txt
特殊字符:
双引号(“”):使shell无法认出空格,制表符和其他大多数特殊字符,比如:创建一个带空格的文件: touch “winber empire”
单引号(’):使shell无法认出所有特殊字符 eg: echo ‘$VAR'
反引号(`):用来替换命令,表示引号内当命令处理 eg: echo `ls -l`
分号(;): 允许一行上出现多个命令
变量: 声明变量不加$,使用变量加$;
linux命令区分大小写;
给PATH环境变量追加内容: 格式 export PATH=$PATH:(增加的内容);
.   当前目录 ..   上一级牡蛎
env   查看新增加的环境变量;
本地变量会随着当前终端的关闭而消失;
环境变量如果被修改,只在当前终端有效,重启另一个终端,恢复默认值;
环境变量在shell嵌套调用中值发生改变,只在其本身和子shell生效,父shell恢复默认值;
使用变量的方法:两种,最好用${VAR}的形式;
set 用于查看当前环境下的变量名和值;
变量替换(分情况显示值):${…:…}
unset取消变量,防止函数内外变量同名冲突;
位置变量(给文件传参数):$0到$9,$0的值是脚本的名字;$$是当前shell进程id号; eg:    ./hello.sh   aa bb cc 注意:$0不计入参数个数 $* 以字符串形式显示所有传入的参数,且不受参数个数限制 $# 显示传入参数总个数
标准变量(系统内置变量):LOGNAME,MAIL,TZ时区,PATH,PWD(当前路径)...
$?得到最后一个命令,脚本或者函数执行的返回值;
Shell变量的最基本规则:变量只有字符串和整数两种类型,在Shell运算中都是整数运算或字符串运算; 取值则变量前加$,赋值不加$;
三种引号之间的区别(重要);
表达式运算,格式:$[表达式],也可以用 $((表达式));
输出命令:echo -e 解析转义字符,-n  回车不换行;
输入命令:read 参数的使用规则(常用);
输出命令:tee   常用在管道调试情况;
文件重定向:>  覆盖;  >> 追加;
流程控制:
test命令  test[条件] 条件测试,成功是0,失败是1;   有两种使用形式,使用中括号形式表示时,注意空格规则;    
逻辑测试:    -a 逻辑与, -o 逻辑货, ! 逻辑否;
文件状态测试:   -d 目录 , -s 文件非空, -f 正规文件 , -w 可写 ,-L 符号链接 , -u  文件有 suid 位设置,  -r 可读 , -x  可执行;
eg: [ -w xab -a -w xac ]     echo  $?
字符串测试: =  ,  !=  只针对字符串是否相等,不能用于数值  -z 空串     -n     非空串
测试数值:  -eq  ,   -ne   数值不相等,  -gt  ,  -lt  ,  -le 小于等于,  -ge  ;
算术运算(expr): +    -     \*      /   注意运算符两边空格
eg:     MY_VAR!=21
         MY_VAR2=34
 MY_VAR3=`expr $MY_VAR1 + $MY_VAR2`
 echo $MY_VAR3
 echo $?
条件分支:  格式  :  if  [  ]    then  <cmd>   elif [   ]  then    <cmd >  fi
eg:   if   test   -z   $My_VAR1
then   echo   “3”
else    echo   “4”
fi
case多选择语句:要点: 1,条件处理的是字符串,   2,每一个分支以“;;”作为结束, 3, 条件分支以esac结束,  4, 通配符*,?,[]
正则表达式和文本处理:eg  :     ls   -l   |    grep   ^.r.xr.x
Grep(基于行的匹配) 常用参数(重要)
find 命令 : 用于查找,注意,如果处理大量文件的话应该将命令切换到后台处理,find 基本命令格式: find  路径  选项     注意一个细节,find命令查找的输出中,路径是怎样显示的?      注意    -print 选项存在的意义,强制输出到标准输出;
atime(访问时间)、ctime(状态修改,如权限、用户名等)、mtime(内容修改);
常用的find选项: -name    -type      -depth
find和xargs配合使用;
awk (基于列的匹配):每一列叫“域”,列之间作区分的符号叫分隔符,列控制变量:$0~$n,注意:第一列是$1,而$0代表所有的列,注意awk命令脚本引号的用法,引号就近匹配,注意使用转义,awk命令支持对数字的运算,注意多个脚本表达式之间用分号“;”进行分割;    eg  :  awk ‘{$6>0;print $1 “=>” $6 }’ stock.txt
sed 命令:按照行或者处理文本,  sed   -n  ‘1p’ -n 按照行定为打印  sed -n ‘1,3p’ 范围 sed -n ‘$p’ 代表最后一行 sed  文本替换 sed ’s/old/new/g'
wc   统计行数;
脚本对程序员的意义:1,解决重复性工作,2,控制linux服务,3,对重要文本信息进行处理(日志等);
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值