面向性能的编程参考资料
1 Kiss原则
懒人原则,保持简单、愚蠢。以最简洁的方式做好某件事。
Kiss原则使代码简单、清晰、易于理解。编程语言是为人类所理解的,所以保持编码的简单和直接、让人类理解。保证你的方法尽量很小每个方法应该只解决一个小问题,而不是实现很复杂的功能。如果你在方法中有很多条件,把它们分解成更小的单独的方法。它不仅更易于阅读和维护,而且可以更快的发现bug。
excel导入的例子。
相关原则:dry原则,不做重复的事(don't repeat yourself);yagni原则,你不会需要的(You ain't gonna neet it)
2 软件三层架构
高内聚低耦合
分层架构是最常见,也是最重要的一种结构,职位分工
前端 –> 应用层 –> 数据库层xh
3 前端编程
- 减少请求数
- 合并js,css文件
- 合并图片文件css sprites(css图片精灵技术),把一些小图片合并在一张大图上,使用的时候通过背景图片定位,定位在具体的某一张小图上
- 避免循环请求
- 减少数据量
- 使用缓存,cdn,设置过期时间,时间戳
- 压缩js/css文件(webpack、gzip)
- 压缩数据
- 加快页面展示
- css文件放在页面的最前面
- js文件放在页面的后面
- 懒加载技术(图片,数据等),虚拟dom,随着滚动进行加载
- 后台渲染(首屏)
- 使用分页展示技术
- 使用异步编程
4 应用层编程
- 缓存数据
- 进程内缓存
- 进程外缓存
- 常碰到的问题:过期策略(惰性)、缓存更新(独立)、多级缓存、分布式缓存(分片)、高可用(单点)、高并发(雪崩)、命中率(穿透)、缓存淘汰(LRU)等
- 其多级缓存方案的层级关系大都是由浏览器->cdn->反向代理缓存->线程级->内存级->文件(静态资源)->分布式(redis) ->Db结果。
- 返回需要的数据
- 行/列
- 减少数据的往返
- 避免循环取数
- 关闭可关闭的资源
- Using(C#)
- 连接池连接,及时申请和释放
- Open/Close
5 数据库层编程
5.1 事务尽量的短
5.1.1 错误的写法
conn.begintran() … 数据检测 … 调用第三方逻辑 表1.update() 表2.update() Conn.commit();
5.1.2 正确的写法
… 数据检测 … 调用第三方逻辑 conn.begintran() 表1.update() 表2.update() Conn.commit();
5.1.3 ACID特性
并非任意的对数据库的操作序列都是数据库事务。数据库事务拥有以下四个特性,习惯上被称为ACID特性。
- 原子性(Atomicity):事务作为一个整体被执行,包含在其中的对数据库的操作要么全部被执行,要么都不执行。
- 一致性(c、Consistency):事务应确保数据库的状态从一个一致状态转变为另一个一致状态。一致状态的含义是数据库中的数据应满足完整性约束。
- 隔离性(Isolation):多个事务并发执行时,一个事务的执行不应影响其他事务的执行。
- 脏读
- 不可重复读(和脏读区别是,脏读是某一事务读取了另一个事务未提交的脏数据,而不可重复读则是读取了前一事务提交的数据)
- 幻读(幻读和不可重复读都是读取了另一条已经提交的事务(这点就脏读不同),所不同的是不可重复读查询的都是同一个数据项,而幻读针对的是一批数据整体(比如数据的个数))
- Mysql数据库提供的四种隔离级别:
- Serializable(串行化):可避免脏读、不可重复读、幻读的发生
- Repeatable(可重复读)[默认]:可避免脏读、不可重复读的发生
- Read committed(读已提交):可避免脏读的发生
- Read uncommitted(读未提交):最低级别,任何情况都无法保证
- Oracle数据库提供两种事务隔离级别:
- Serializable
- Read committed(默认)
- Sql server事务隔离级别分为以下两大类:
- 基于悲观并发控制的四个隔离级别(Serializable、Repeatable、 Read committed[默认]、 Read uncommitted)
- 基于乐观并发控制的两个隔离级别(Read committed[默认]、Snapshot)
- 持久性(Durability):已被提交的事务对数据库的修改应该永久保存在数据库中。
5.2 不要在循环中启事务与提交事务
错误的写法
List data = new AarrayLis() Conn.setAutoCommit(false) For(int i;=0;i<data.Length;i++){ stmt.update(“”); conn.commit(); }
正确的写法
List data = new AarrayLis() Conn.setAutoCommit(false) For(int i;=0;i<data.Length;i++){ stmt.update(“”); } conn.commit();
批处理的写法
List data = new AarrayLis() Conn.setAutoCommit(false) con.setAutoCommit(false); PreparedStatement ps=con.prepareStatement(sql); for(Integerin:){ ps.setInt(1,in); ps.addBatch(); } int[] result=ps.executeBatch(); conn.commit();
5.3 SQL语句绑定变量
参数化防sql注入
不恰当的写法
String value= “ng”; String sql = “update a set col1=‘”+value+”’”; Stmt.executeupdate(sql);
正确的写法
PreparedStatement updateSales = con.prepareStatement("UPDATE COFFEES SETSALES = ? WHERE COF_NAME LIKE ? "); updateSales.setInt(1, 75); updateSales.setString(2, "Colombian"); updateSales.executeUpdate();
5.4 使用存储过程
5.5 优化数据库索引