Spring MVC 知识点整理

 

extend:http://www.jianshu.com/p/bef0e52067d2

1. Redis 存储方式

Redis存储机制分成两种Snapshot 和 AOF。无论是那种机制,Redis都是将数据存储在内存中。

Snapshot工作原理: 是将数据先存储在内存,然后当数据累计达到某些设定的伐值的时候,就会触发一次DUMP操作,将变化的数据一次性写入数据文件(RDB文件)。

AOF 工作原理 : 是将数据也是先存在内存,但是在存储的时候会使用调用fsync来完成对本次写操作的日志记录,这个日志揭露文件其实是一个基于Redis网络交互协议的文本文件。AOF调用fsync也不是说全部都是无阻塞的,在某些系统上可能出现fsync阻塞进程的情况,对于这种情况可以通过配置修改,但默认情况不要修改。AOF最关键的配置就是关于调用fsync追加日志文件的平率,有两种预设频率,always每次记录进来都添加,everysecond 每秒添加一次。两个配置各有所长后面分析。由于是采用日志追加的方式来持久话数据,所以引出了第二个日志的概念:rewrite. 后面介绍它的由来。

存储模式性能和安全比较:

1.性能:Snapshot方式的性能是要明显高于AOF方式的,原因有两点:

Snapshot采用2进制方式存储数据,数据文件比较小,加载快速.
存储的时候是按照配置中的save策略来存储,每次都是聚合很多数据批量存储,写入的效率很好

而AOF则一般都是工作在实时存储或者准实时模式下。相对来说存储的频率高,效率却偏低。

2.数据安全:AOL数据安全性高于Snapshot存储,原因:

Snapshot存储是基于累计批量的思想,也就是说在允许的情况下,累计的数据越多那么写入效率也就越高,但数据的累计是靠时间的积累完成的,那么如果在长时间数据不写入RDB,但Redis又遇到了崩溃,那么没有写入的数据就无法恢复了,但是AOF方式偏偏相反,根据AOF配置的存储频率的策略可以做到最少的数据丢失和较高的数据恢复能力。
说完了性能和安全,这里不得不提的就是在Redis中的Rewrite的功能,AOF的存储是按照记录日志的方式去工作的,那么成千上万的数据插入必然导致日志文件的扩大,Redis这个时候会根据配置合理触发Rewrite操作,所谓Rewrite就是将日志文件中的所有数据都重新写到另外一个新的日志文件中,但是不同的是,对于老日志文件中对于Key的多次操作,只保留最终的值的那次操作记录到日志文件中,从而缩小日志文件的大小。这里有两个配置需要注意:

auto-aof-rewrite-percentage 100 (当前写入日志文件的大小占到初始日志文件大小的某个百分比时触发Rewrite)
auto-aof-rewrite-min-size 64mb (本次Rewrite最小的写入数据良)

两个条件需要同时满足。

2.Redis 对于HashMap的存储方式

Redis不支持Java的HashMap,Redis有自己的数据结构
但可以使用Jedis (Jedis是redis的java版本的客户端实现) 来处理HashMap

 /**
  * redis操作Map
  */
 @Test
 public void testMap() {
     //-----添加数据----------  
     Map<String, String> map = new HashMap<String, String>();
     map.put("name", "xinxin");
     map.put("age", "22");
     map.put("qq", "123456");
     jedis.hmset("user",map);
     //取出user中的name,执行结果:[minxr]-->注意结果是一个泛型的List  
     //第一个参数是存入redis中map对象的key,后面跟的是放入map中的对象的key,后面的key可以跟多个,是可变参数  
     List<String> rsmap = jedis.hmget("user", "name", "age", "qq");
     System.out.println(rsmap);  
     //删除map中的某个键值  
     jedis.hdel("user","age");
     System.out.println(jedis.hmget("user", "age")); //因为删除了,所以返回的是null  
     System.out.println(jedis.hlen("user")); //返回key为user的键中存放的值的个数2 
     System.out.println(jedis.exists("user"));//是否存在key为user的记录 返回true  
     System.out.println(jedis.hkeys("user"));//返回map对象中的所有key  
     System.out.println(jedis.hvals("user"));//返回map对象中的所有value 
     Iterator<String> iter=jedis.hkeys("user").iterator();  
     while (iter.hasNext()){  
         String key = iter.next();  
         System.out.println(key+":"+jedis.hmget("user",key));  
     }  
 }
 

 

3.Redis和Memcached的区别 - extend

  • Redis不仅仅支持简单的k/v类型的数据,同时还提供list,set,hash等数据结构的存储;

  • Redis支持数据的备份,即master-slave模式的数据备份。

  • Redis支持数据的持久化。

  • Redis在很多方面支持数据库的特性,可以这样说他就是一个数据库系统,而memcached只是简单地K/V缓存。

  • 它们在性能方面差别不是很大,读取方面尤其是针对批量读取性能方面memcached占据优势。当然redis也有他的优点,如持久性、支持更多的数据结构。

  • Redis和Memcache都是将数据存放在内存中,都是内存数据库。不过memcache还可用于缓存其他东西,例如图片、视频等等;

  • 虚拟内存--Redis当物理内存用完时,可以将一些很久没用到的value 交换到磁盘;

  • 过期策略--memcache在set时就指定,例如set key1 0 0 8,即永不过期。Redis可以通过例如expire 设定,例如expire name 10;

  • 分布式--设定memcache集群,利用magent做一主多从; redis可以做一主多从。都可以一主一从;

  • 存储数据安全--memcache挂掉后,数据不可恢复;redis可以定期保存到磁盘(持久化),数据丢失后可以通过aof恢复;

  • Redis支持数据的备份,即master-slave模式的数据备份;

  • 应用场景不一样:Redis出来作为NoSQL数据库使用外,还能用做消息队列、数据堆栈和数据缓存等;Memcached适合于缓存SQL语句、数据集、用户临时性数据、延迟查询数据和session等。

所以在选择方面如果有持久方面的需求或对数据类型和处理有要求的应该选择redis。如果简单的key/value 存储应该选择memcached。

3.mysql中order by与group by的顺序

MySQL 中order by 与group by的顺序 是:
select -> from -> where -> group by -> order by

注意:group by 比order by先执行,order by不会对group by 内部进行排序,如果group by后只有一条记录,那么order by 将无效。要查出group by中最大的或最小的某一字段使用 max或min函数。
例:

select
sum(click_num) as totalnum,
max(update_time) as update_time,
count(*) as totalarticle
from
article_detail
where
userid =1
group by
userid
order by
update_time
desc

 

4.MyBatis和Hibernate相比,优势在哪里?

  • 开发对比
    开发速度Hibernate的真正掌握要比Mybatis来得难些。
    Mybatis框架相对简单很容易上手,但也相对简陋些。
    个人觉得要用好Mybatis还是首先要先理解好Hibernate。

  • 开发社区
    Hibernate 与Mybatis都是流行的持久层开发框架,但Hibernate开发社区相对多热闹些,支持的工具也多,更新也快,当前最高版本4.1.8。
    而Mybatis相对平静,工具较少,当前最高版本3.2。
    开发工作量Hibernate和MyBatis都有相应的代码生成工具。可以生成简单基本的DAO层方法。
    针对高级查询,Mybatis需要手动编写SQL语句,以及ResultMap。而Hibernate有良好的映射机制,开发者无需关心SQL的生成与结果映射,可以更专注于业务流程。

  • Mybatis优势MyBatis可以进行更为细致的SQL优化,可以减少查询字段。-
    MyBatis容易掌握,而Hibernate门槛较高。

  • Hibernate优势Hibernate的DAO层开发比MyBatis简单,Mybatis需要维护SQL和结果映射。

  • Hibernate对对象的维护和缓存要比MyBatis好,对增删改查的对象的维护要方便。

  • Hibernate数据库移植性很好,MyBatis的数据库移植性不好,不同的数据库需要写不同SQL。

  • Hibernate有更好的二级缓存机制,可以使用第三方缓存。MyBatis本身提供的缓存机制不佳。

  • hibernate是在jdbc上进行了一次封装,而mybatis基于原生的jdbc,因此mybatis天生就有运行速度上的优势。

  • mybatis开放了插件接口,把很多功能接口都开放了,网上大神写的插件多得很;按注解生成自动生成sql的插件早就有了;还有缓存的插件等等。可以说,只要肯在mybatis上花时间,你会发现orm这一块的所有问题它都有解决方案。这方面不是说hibernate不好,但是我还真没听说过hibernate有插件了

MyBatis+MySQL 返回插入对象的主键ID

需求:使用MyBatis往MySQL数据库中插入一条记录后,需要返回该条记录的自增主键值。

  • 方法1:在mapper中指定keyProperty属性,示例如下:

useGeneratedKeys="true":设置是否使用JDBC的getGenereatedKeys方法获取主键并赋值到keyProperty设置的领域模型属性中。(适用于MySQL、sqlserver数据库,Oracle不能使用,使用selectkey子节点做)

keyProperty="userId":赋值的对象的属性名称。
添加完成后,直接根据对象属性取值

<insert id="insertAndGetId" useGeneratedKeys="true" keyProperty="userId"
parameterType="com.chenzhou.mybatis.User">  
    insert into user(userName,password,comment)  
    values(#{userName},#{password},#{comment})  
</insert>  

 

如上所示,我们在insert中指定了keyProperty="userId",其中userId代表插入的User对象的主键属性。

User.java

public class User {  
    private int userId;  
    private String userName;  
    private String password;  
    private String comment;  
      
    //setter and getter  
}  

 

UserDao.java
public interface UserDao {  
  
    public int insertAndGetId(User user);  
  
}  

 

测试:

User user = new User();  
user.setUserName("chenzhou");  
user.setPassword("xxxx");  
user.setComment("测试插入数据返回主键功能");  
  
System.out.println("插入前主键为:"+user.getUserId());  
userDao.insertAndGetId(user);//插入操作  
System.out.println("插入后主键为:"+user.getUserId());  

 

输出:

插入前主键为:0  
插入后主键为:15  

查询数据库:

 

如上所示,刚刚插入的记录主键id为15

 <insert 
    id="insertUser"  parameterType="com.entity.user">
     insert into test (name) values (#{name})
<selectKey keyProperty="id" resultType="java.lang.Integer">      
   select LAST_INSERT_ID() as id      
</selectKey>    
</insert>

 

后台代码不变。
各个数据库获取方式不一样,本例根据mysql为例。其他请各自根据需要查询。

posted @ 2017-08-29 14:29  n1rAy  阅读(267)  评论(0编辑  收藏  举报