昨天的程序有点错误,重新粘一个, for循环终结括号括错了。
另外新加了个destroy()方法
下篇重写了个单线程版本的
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.zip.CRC32;
public class MobileUtil {
private static final ScheduledExecutorService timer = Executors
.newScheduledThreadPool(Runtime.getRuntime().availableProcessors());
private static final String fileName = "d:\\mobilelocation";
private static long crc32;// 字符串进行crc32数据校验
private static String content = null;// 获取的内容字符串
private static HashMap<String, Location> locationMap = new HashMap<String, Location>();
private static volatile boolean started = false;
final MobileUtil mobileUtil = null;
private MobileUtil() {
}
private void initial() {
timer.scheduleWithFixedDelay(new Runnable() {
public void run() {
long start = System.nanoTime();
try {
//crc32校验
long crc = crc32(fileName);
if(crc32 == crc){
return;
}
crc32 = crc;
System.out.println("开始加载手机号归属地信息...");
FileInputStream fi = new FileInputStream(fileName);
InputStreamReader inreader = new InputStreamReader(fi,
"GBK");
BufferedReader reader = new BufferedReader(inreader);
String line = null;
StringBuilder sb = new StringBuilder();
int strCount = 0;
while ((line = reader.readLine()) != null) {
strCount++;
sb.append(line + "\r\n");
}
content = sb.toString();
String contentCopy = content;
int total = contentCopy.length();
System.out.println(total);
// 使用的线程数量
int threadCounts = Runtime.getRuntime()
.availableProcessors();
ExecutorService exec = Executors
.newFixedThreadPool(threadCounts);
List<Callable<HashMap<String, Location>>> callList = new ArrayList<Callable<HashMap<String, Location>>>();
int len = strCount / threadCounts;// 平均分割strCount
// strCount小于线程数
if (len == 0) {
threadCounts = strCount;// 采用一个线程处理List中的一个元素
len = strCount / threadCounts;// 重新平均分割List
}
for (int i = 0; i < threadCounts; i++) {
// 根据线程数量切割字符串为线程数量个子字符串
final String subContent;
if (0 == threadCounts - 1) {
subContent = contentCopy;
} else {
int startPos = i * total / threadCounts;
int endPos = (i + 1) * total / threadCounts;
if (i != 0)
while (!contentCopy.substring(startPos - 2,
startPos).endsWith("\r\n")) {
startPos++;
}
if (i != threadCounts - 1)
while (!contentCopy.substring(endPos - 2,
endPos).endsWith("\r\n")) {
endPos++;
}
subContent = contentCopy
.substring(startPos, endPos);
}
callList.add(new Callable<HashMap<String, Location>>() {
public HashMap<String, Location> call()
throws Exception {
String contentCopy = subContent;
HashMap<String, Location> map = new HashMap<String, Location>();
while (true) {
String splitStr = null;
int j = contentCopy.indexOf("\r\n");
if (j < 0) {
break;
}
splitStr = contentCopy.substring(0, j);
Location lc = new Location();
String num = splitStr.substring(0,
splitStr.indexOf("\t")).trim();
lc.setNum(num);
splitStr = splitStr.substring(splitStr
.indexOf("\t") + 1);
lc.setProvince(splitStr.substring(0,
splitStr.indexOf("\t")).trim());
splitStr = splitStr.substring(splitStr
.indexOf("\t") + 1);
lc.setCity(splitStr.substring(0,
splitStr.indexOf("\t")).trim());
splitStr = splitStr.substring(splitStr
.indexOf("\t") + 1);
lc.setOperator(splitStr.trim());
map.put(num, lc);
contentCopy = contentCopy.substring(j + 1);
}
return map;
}
});
}
List<Future<HashMap<String, Location>>> futureList = exec
.invokeAll(callList);
HashMap<String, Location> result = new HashMap<String, Location>();
for (Future<HashMap<String, Location>> future : futureList) {
result.putAll(future.get());
}
locationMap = result;
started = true;
System.out.println("手机号归属地信息加载完毕...用时:"+(System.nanoTime() - start)/1e9+"秒,"+"加载数量:"+strCount);
exec.shutdown();
} catch (FileNotFoundException e) {
e.printStackTrace();
System.out.println("找不到文件" + fileName + "...");
} catch (IOException e) {
e.printStackTrace();
System.out.println("与文件" + fileName + "通信异常...");
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
}, 0, 30, TimeUnit.MINUTES);
}
public static void init() {
final MobileUtil mobileUtil = new MobileUtil();
mobileUtil.initial();
}
public static void destroy(){
timer.shutdown();
content = null;
locationMap = null;
started = false;
}
public static MobileUtil create(){
final MobileUtil mobileUtil = new MobileUtil();
while(!started){
if(started)break;
}
return mobileUtil;
}
public static void main(String args[]) throws IOException {
System.out.println(getCity("13811014978"));
System.out.println(getOperator("13811014978"));
}
static class Location {
private String num;
private String province;
private String city;
private String operator;
public Location() {
}
public String getNum() {
return num;
}
public void setNum(String num) {
this.num = num;
}
public String getProvince() {
return province;
}
public void setProvince(String province) {
this.province = province;
}
public String getCity() {
return city;
}
public void setCity(String city) {
this.city = city;
}
public String getOperator() {
return operator;
}
public void setOperator(String operator) {
this.operator = operator;
}
}
public static Location getLocation(String mobile) {
mobile = getNum7(mobile);
while(!started){
if(started)break;
}
return locationMap.get(mobile);
}
public static String getCity(String mobile) {
while(!started){
if(started)break;
}
mobile = getNum7(mobile);
System.out.println("mobile:"+mobile);
if (locationMap.get(mobile) == null)
return null;
return locationMap.get(mobile).getCity();
}
public static String getProvince(String mobile) {
mobile = getNum7(mobile);
while(!started){
if(started)break;
}
if (locationMap.get(mobile) == null)
return null;
return locationMap.get(mobile).getProvince();
}
public static String getOperator(String mobile) {
mobile = getNum7(mobile);
while(!started){
if(started)break;
}
if (locationMap.get(mobile) == null)
return null;
return locationMap.get(mobile).getOperator();
}
private static String getNum7(String mobile) {
mobile = mobile.trim();
if (mobile.length() != 11 || !mobile.startsWith("1")
|| !mobile.matches("\\d+"))
throw new IllegalArgumentException("传入的手机号码" + mobile
+ "不正确,请使用正确的11位数字号码");
return mobile.substring(0, 7);
}
private static long crc32(String str){
CRC32 crc32 = new CRC32();
byte[] data = str.getBytes();
for(byte i=0;i<data.length;i++) {
data[i] = i;
}
crc32.update(data);
return crc32.getValue();
}
}