在给的 http.log 日志文件中,是电信运营商记录用户上网访问某些网站行为的日志记录数据,一条数据中有多个字段用空格分隔。

例如: "18611132889是一条上网行为,第一个字段代表手机号码,第二个字段代表请求网站的 URL ,第三个字段代表请求发送的数据即上行流量( 20字节),第四个字段代表服务器响应给用户的流量即下行流量( 5000 字节)。

数据

 

手机段规则

 

需求:

  1. 计算出用户上网流量总流量(上行 + 下行)最高的的网站 Top3 ,
  2. 根据给的的手机号段归属地规则,计算出总流量最高的省份 Top3
  3. 根据给的的手机号段运营商规则,计算出总流量最高的运营商 Top3

步骤分析:

1 将手机号规则信息放在 Map 集合中,以手机号为 key ,手机数据实体为 value 。

2 加载 http 日志数据,获取 url 和手机号数据( url 需要简单清洗)

3 处理 url 数据,统计流量

4 根据 http 日志文件中的手机号匹配获取对应的区域运营商数据,进行统计

知识点:

集合 list 和 map 存储数据特点

IO 切割

1.1. ** 创建两个实体 bean 来存储手机号规则数据和上网数据 **

HttpBean pojo
** private ** String phone ; // 手机号
** private ** String url ; // 请求的 _ url _
** private ** ** int ** upData ; // 上行流量
** private ** ** int ** lowData ; // 下行流量


TelBean

** private ** String prefix ;
** private ** String phone ;
** private ** String province ;
** private ** String city ;
** private ** String isp ;
** private ** String postCode ;
** private ** String cityCode ;
** private ** String areaCode ;


1.2. ** 读取手机号规则数据 将数据封装到 Map 中 **

/**
• 将 _ Tel _ 放在 map 中 
• ** @return **
*/ 
** public ** ** static ** Map<String, TelBean> getTelMap() {
Map<String, TelBean> map = ** new ** HashMap<>();
** try ** (BufferedReader bfr = ** new ** BufferedReader( ** new **FileReader( "d:/data/ 手机号段规则 .txt" ));) {
String line = ** null ** ;
bfr .readLine();
** while ** (( line = bfr .readLine()) != ** null ** ) {
// System.out.println(line);
String[] split = line .split( "\s" );
String prefix = split [0];
String phone = split [1]; // 七位
String province = split [2];
String city = split [3];
String isp = split [4];
String postCode = split [5];
String cityCode = split [6];
String areaCode = split [7];
TelBean telBean = ** new ** TelBean( prefix , phone , province ,city , isp , postCode , cityCode , areaCode );
map .put( phone , telBean ); // key 七位的手机号
}
} ** catch ** (Exception e ) {
// ** TODO ** Auto-generated catch block
e .printStackTrace();
}
** return ** map ;
}


1.3. ** 将手机号规则数据存储在 list 中 **

/**
• 返回 _ Tel _ 的 list 数据 
• ** @return **
*/ 
** public ** ** static ** List<TelBean> getTelList() {
List<TelBean> list = ** new ** ArrayList<>();
** try ** (BufferedReader bfr = ** new ** BufferedReader( ** new **FileReader( "d:/data/ 手机号段规则 .txt" ));) {
String line = ** null ** ;
bfr .readLine();
** while ** (( line = bfr .readLine()) != ** null ** ) {
// System.out.println(line);
String[] split = line .split( "\s" );
String prefix = split [0];
String phone = split [1];
String province = split [2];
String city = split [3];
String isp = split [4];
String postCode = split [5];
String cityCode = split [6];
String areaCode = split [7];
TelBean telBean = ** new ** TelBean( prefix , phone , province ,city , isp , postCode , cityCode , areaCode );
list .add( telBean );
}
} ** catch ** (Exception e ) {
// ** TODO ** Auto-generated catch block
e .printStackTrace();
}
** return ** list ;
}


由于 List 集合和 Map 集合存储数据的特点不同 , 此案例我们选择使用 map 集合

List 需要根据手机号获取其对应的区域需要遍历并匹配手机字段

Map 存储手机号规则数据 , 可将手机号作为 key , TelBean 为 value 数据 , 直接根据 key来获取其对应的区域信息

1.4. ** 统计 url 的访问流量 **

/**
• 统计 URl 结果 
• ** @return **
*/ 
** public ** ** static ** Map<String,Integer> getUrlResult() {
// 统计各个 _ url _ 的访问量数据
Map<String,Integer> urlMap = ** new ** HashMap<>();
** try ** (BufferedReader bfr = ** new ** BufferedReader( ** new **FileReader( "d:/data/http.log" ));){
String line = ** null ** ;
** while ** (( line = bfr .readLine())!= ** null ** ){
//System.out.println(line);
String[] split = line .split( "\s" );
String _ phone _ = split [0];
String urlStr = split [1];
String upDateStr = split [2];
String lowDataStr = split [3];
// 处理 _ url _ 数据 清洗掉数据格式不正确的数据
String[] split2 = urlStr .split( "\." );
** if ** ( split2 . length >=3){ // 如果 _ url _ 包含两个 点
String url = split2 [1];
Integer sum = ** urlMap .getOrDefault( url , 0); **
sum += Integer. _ parseInt _ ( upDateStr )+Integer. _ parseInt _ (lowDataStr );
urlMap .put( url , sum ); // 结果数据
}
}
} ** catch ** (Exception e ) {
// ** TODO ** Auto-generated catch block
e .printStackTrace();
}
** return ** urlMap ;
}

1.5. 统计省份和运营商的访问流量统计

** static ** Map<String, TelBean> _ telMap _ ;
** static ** {
_ telMap _ = TelAdmin. _ getTelMap _ ();
}
** public ** ** static ** ** void ** main(String[] args ) {
// 存储省份结果
Map<String,Integer> pMap = ** new ** HashMap<>();
// 存储运营商结果
Map<String,Integer> ispMap = ** new ** HashMap<>();
// 存储统计 _ url _ 结果
Map<String,Integer> urlMap = ** new ** HashMap<>();
** try ** (BufferedReader bfr = ** new ** BufferedReader( ** new **FileReader( "d:/data/http.log" ));){
String line = ** null ** ;
** while ** (( line = bfr .readLine())!= ** null ** ){
//System.out.println(line);
String[] split = line .split( "\s" );
String phone = split [0];
String urlStr = split [1];
String upDateStr = split [2];
String lowDataStr = split [3];
String tel = phone .substring(0, 7);
TelBean telBean = _ telMap _ .get( tel );
String province = telBean .getProvince(); // 省份
Integer tatol1 = pMap .getOrDefault( province , 0);
tatol1 +=Integer. _ parseInt _ ( upDateStr )+Integer. _ parseInt _ (lowDataStr );
pMap .put( province , tatol1 );
String isp = telBean .getIsp(); // 运营商
Integer tatol2 = ispMap .getOrDefault( isp , 0);
tatol2 +=Integer. _ parseInt _ ( upDateStr )+Integer. _ parseInt _ (lowDataStr );
ispMap .put( isp , tatol2 );
String[] split2 = urlStr .split( "\." );
** if ** ( split2 . length >=3){
String url = split2 [1];
//System.out.println( _ url _ );
Integer tatol = urlMap .getOrDefault( url , 0);
tatol += Integer. _ parseInt _ ( upDateStr )+Integer. _ parseInt _ (lowDataStr );
urlMap .put( url , tatol );
}
}
// 对结果集 map 排序 获取想要的结果
ispMap .entrySet();
pMap .entrySet();
urlMap .entrySet();
} ** catch ** (Exception e ) {
// ** TODO ** Auto-generated catch block
e .printStackTrace();
}


1.6. map 排序工具类

** public ** ** static ** ArrayList<Entry<String, Integer>>sort(Map<String,Integer> map ){
Set<Entry<String, Integer>> entrySet = map .entrySet();
ArrayList<Entry<String, Integer>> list = ** new ** ArrayList<>( entrySet);
Collections. _ sort _ ( list , ** new ** Comparator<Entry<String,Integer>>() {
@Override
** public ** ** int ** compare(Entry<String, Integer> o1 , Entry<String,Integer> o2 ) {
** return ** o2 .getValue().compareTo( o1 .getValue());
}
});
** return ** list ;
}