package com.sides.redis;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Callable;
import org.apache.log4j.Logger;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.Pipeline;
import com.sides.file.DataFactory;
public class WriteRedisThread implements Callable<Boolean>{
private static final Logger logger = Logger.getLogger(WriteRedisThread.class);
private List<Map<String,Object>> dataList;
private String tableId;
public WriteRedisThread(List<Map<String,Object>> dataList,String tableId){
this.dataList = dataList;
this.tableId = tableId;
}
@Override
public Boolean call() throws Exception {
Jedis client = null;
JSONArray dataArr = null;
try {
dataArr = JSONArray.fromObject(dataList,DataFactory.jsonConfig);
client = RedisDao.getClient();
Pipeline line = client.pipelined();
Iterator<JSONObject> iter = null;
for(int i=0;i<9;i++){
iter = dataArr.iterator();
while(iter.hasNext()){
line.lpush(tableId, iter.next().toString());
}
}
line.sync();
} catch (Exception e) {
logger.warn("when insert data into "+tableId+" exception .", e);
return false;
}finally{
RedisDao.closeClient(client);
}
return true;
}
}
调用:
redis客户端jedispackage com.sides.redis;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import org.apache.log4j.Logger;
import redis.clients.jedis.Jedis;
import com.sides.file.DataFactory;
public class WriteMain {
private static final Logger logger = Logger.getLogger(WriteMain.class);
public static void main(String[] args) throws InterruptedException, ExecutionException {
List<Map<String,Object>> list = DataFactory.dataList;
ExecutorService service = Executors.newFixedThreadPool(200);
long t0 = System.nanoTime();
List<Future<Boolean>> results = new ArrayList<Future<Boolean>>();
for(int i=0;i<8000;i++){
Future<Boolean> future = service.submit(new WriteRedisThread(list, "V"+i+"TRIP_DTL"));
results.add(future);
}
logger.info("所有线程已启动,开始最后的阻塞同步");
for(Future<Boolean> f:results){
f.get(); //强制同步
}
long t1 = System.nanoTime();
logger.info("耗时:"+(t1-t0)/1000000);
Jedis client = RedisDao.getClient();
Set<String> set = client.keys("*");
for(String s:set){
logger.info(s);
}
logger.info("数据库中KEY数目:"+client.dbSize());
RedisDao.closeClient(client);
RedisDao.destroyPool();
}
}
测试数据生成工厂:package com.sides.redis;
import org.apache.log4j.Logger;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPoolConfig;
public class RedisDao {
private static final Logger logger = Logger.getLogger(RedisDao.class);
public static JedisPool clientPool;
static{
JedisPoolConfig config = new JedisPoolConfig();
// config.setMaxActive(1500);
config.setMaxIdle(3600);
clientPool = new JedisPool(config, "10.10.10.21", 6379);
}
public static synchronized Jedis getClient(){
return clientPool.getResource();
}
public static void closeClient(Jedis client){
if(client!=null){
clientPool.returnResource(client);
}
}
public static void destroyPool(){
clientPool.destroy();
}
}
一个JSON日期处理类:package com.sides.file;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import net.sf.json.JsonConfig;
import org.apache.commons.lang.math.RandomUtils;
/****************************************************************************
* com.sides.file DataFactory.java Created on 2013-12-3
* @Author: linfenliang
* @Description:
* @Version: 1.0
***************************************************************************/
public class DataFactory {
private static final DateFormat dformat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
public static final List<Map<String,Object>> dataList = initData();
public static JsonConfig jsonConfig = initjsonconfig();
private static final List<Map<String,Object>> initData(){
List<Map<String,Object>> dataList = new ArrayList<Map<String,Object>>();
Map<String,Object> map;
String recvDate = dformat.format(new Date().getTime()+1000*10);
for(int i=0;i<10;i++){
map = new HashMap<String, Object>();
map.put("GATHERTIME", dformat.format(new Date().getTime()+i*1000));
map.put("ACCSTATUS", "0");
map.put("OBD_SPEED", RandomUtils.nextInt(255));
map.put("MAF", nextRandomDouble(0, 20, 2));
map.put("BASE_STATION", "1823,4207,460,0,37;18431,4207,460,0,25;1822,4207,460,0,25;");
map.put("BABV", nextRandomDouble(9.6, 13.6, 2));
map.put("MILAGE", nextRandomDouble(0, 20, 2));
map.put("FUEL", nextRandomDouble(10, 20, 2));
map.put("G_FORCE", nextRandomDouble(-1, 1, 2));
map.put("PID_010C", "");
map.put("PID_010B", "");
map.put("PID_010F", "");
map.put("RECEIVED_TIME", recvDate);
map.put("REMARK", nextInt(0, 65535));
dataList.add(map);
}
return dataList;
}
private static final double nextRandomDouble(double startIndex, double endIndex, int scale){
double source = RandomUtils.nextFloat();
double differ = endIndex - startIndex;
double value = source * differ + startIndex;
double factor = Math.pow(10, scale);
return Math.floor(value * factor + 0.5) / factor;
}
private static final int nextInt(int startIndex, int endIndex){
double source = RandomUtils.nextDouble();
int differ = endIndex - startIndex;
return (int) (source * differ + startIndex);
}
private static final JsonConfig initjsonconfig(){
JsonConfig jsonConfig = new JsonConfig();
jsonConfig.registerJsonValueProcessor(java.util.Date.class, new JsonDateValueProcessor());
jsonConfig.registerJsonValueProcessor(java.sql.Date.class, new JsonDateValueProcessor());
return jsonConfig;
}
/**
* @param args
* void
* @date 2013-12-3
* @version V1.0.0
* @author linfenliang
*/
public static void main(String[] args) {
// System.out.println(dataList);
// for(int i=0;i<20;i++){
// System.out.println(nextDouble(100, 110,2));
// }
// for(int i=0;i<20;i++){
// System.out.println(nextInt(100, 110));
// }
}
}
测试结果:package com.sides.file;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import net.sf.json.JsonConfig;
import net.sf.json.processors.JsonValueProcessor;
/****************************************************************************
* com.sides.pub.util JsonDateValueProcessor.java Created on 2013-9-16
* @Author: linfenliang
* @Description: 该类主要将日期类型(java.util.Date与java.sql.Date)格式化为yyyy-MM-dd HH:mm:ss字符串
* @Version: 1.0
***************************************************************************/
public class JsonDateValueProcessor implements JsonValueProcessor {
private static final DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
/**
* 将日期类型(java.util.Date与java.sql.Date)格式化为yyyy-MM-dd HH:mm:ss字符串
* @author linfenliang
*/
public JsonDateValueProcessor() {
super();
}
@Override
public Object processArrayValue(Object arg0, JsonConfig arg1) {
return process(arg0);
}
@Override
public Object processObjectValue(String arg0, Object arg1, JsonConfig arg2) {
return process(arg1);
}
private Object process(Object value) {
try {
if (value instanceof java.util.Date || value instanceof java.sql.Date) {
return dateFormat.format(value);
}
return value == null ? "" : value.toString();
} catch (Exception e) {
return "";
}
}
}
测试次数 | 耗时(s) | 方式 | 单KEY插入记录数 | 单KEY每次插入记录数 | KEY个数 | 线程数 | 内存消耗 | CPU消耗 |
1 | 706.232 | Jedis客户端 | 7200 | 10 | 100 | 200 | 约248MB | <30% |
2 | 231.693 | Jedis客户端管道方式 | 7200 | 10 | 100 | 200 | 约248MB | <30% |
3 | 178.745 | Jedis客户端管道方式 | 7200 | 7200 | 100 | 200 | 约248MB | <30% |
4 | 180.466 | Jedis客户端管道方式 | 72000 | 72000 | 10 | 200 | 约248MB | <30% |
5 | 179.186 | Jedis客户端管道方式 | 720 | 720 | 1000 | 200 | 约248MB | <30% |
6 | 180.310 | Jedis客户端管道方式 | 90 | 90 | 8000 | 200 | 约248MB | <30% |
测试次数 | 耗时(s) | 方式 | 单KEY插入记录数 | 单KEY每次插入记录数 | KEY个数 | 线程数 | 内存消耗 | CPU消耗 |
1 | 122.488 | Jedis客户端 | 7200 | 10 | 100 | 200 | 约248MB | <30% |
2 | 23.306 | Jedis客户端管道方式 | 7200 | 10 | 100 | 200 | 约248MB | <30% |
3 | 22.004 | Jedis客户端管道方式 | 7200 | 7200 | 100 | 200 | 约248MB | <30% |
4 | 21.689 | Jedis客户端管道方式 | 72000 | 72000 | 10 | 200 | 约248MB | <30% |
5 | 22.305 | Jedis客户端管道方式 | 720 | 720 | 1000 | 200 | 约248MB | <30% |
6 | 22.004 | Jedis客户端管道方式 | 90 | 90 | 8000 | 200 | 约248MB | <30% |