用開關處理檔案合併
用開關處理檔案合併
最近合併一個增量和全量檔案的時候用到了開關,很好用的一種處理邏輯。
應用場景:有一個增量檔案,一個全量檔案,按照規則將增量檔案和全量檔案進行對比後,寫入新的全量檔案。
在增量檔案中有三種資料標識,0表示此增量資料不用新增到新的全量檔案中,要在全量檔案中刪除此標識對新增到新的全量檔案中。1表示2表示此條增量資料要插入新的全量檔案中,2表示此條增量資料對應的手機號需要更新到新的全量檔案,原全量檔案的有相同手機號的不用新增新的全量檔案中。
增量資料如下:
1,13188739756,00020220,00030220,2018-09-18 00:00:00 直接加入到新的全量檔案中
2,13188739754,00020220,00030220,2018-09-18 00:00:00 刪除原全量檔案同樣手機號的資料,將此條資料擷取2,後的資料新增到新的全量檔案中
0,13188739755,00020220,00030220,2018-09-18 00:00:00 此條資料不新增到到新的全量資料檔案
全量資料:
13288739764,00030220,00020220,2017-09-18 00:00:00
13188739754,00030220,00020220,2018-09-18 00:00:00
13188739755,00020220,00030220,2018-09-18 00:00:00
最終要生成的新的全量檔案:
13288739764,00030220,00020220,2017-09-18 00:00:00
13188739754,00020220,00030220,2018-09-18 00:00:00
13188739756,00020220,00030220,2018-09-18 00:00:00
真實的全量資料有將近40萬,增量資料有5000多條,0,1,2標識的資料增量資料數量不等,可能沒有0,或沒有2,或沒有1,或者都沒有,或者都有,或者只有1條,或者有很多條。
全量和增量檔案第一行是此檔案含有的記錄數。
public static void dataReadWrite(File itffullFile ,File increfile){ int start=increfile.getAbsolutePath().indexOf("\\0000"); String filename=(increfile.getAbsolutePath()).substring(start+1); //將合併好的集合資料寫到當日的全量檔案中 String writeITFFilePath="D:\\QQ\\file\\center\\adcnp_dispose\\adcfull_incre_wetcode_data_new\\ITF_XHZW_000087102018080206";//2號開始的增量檔案 String increstr=null,itffullstr=null; BufferedReader increbr =null; BufferedReader fullbr=null; BufferedReader itffullbr=null; PrintWriter pw=null; try { //D:\QQ\file\center\adcnp_dispose\adcfull_incre_wetcode_data_new fullbr = new BufferedReader(new FileReader(itffullFile)); increbr = new BufferedReader(new FileReader(increfile)); pw=new PrintWriter(new OutputStreamWriter(new FileOutputStream(new File(writeITFFilePath))),true); List<String> increlist0=new ArrayList<String>(); List<String> increlist1=new ArrayList<String>(); List<String> increlist2=new ArrayList<String>(); int readline=0; while ((increstr = increbr.readLine())!= null) { if(increstr.indexOf(",")==-1){/ /沒有逗號\ System.out.println("increFile "+filename+" has "+increstr+" records"); if(increstr=="0"){ while ((itffullstr = fullbr.readLine())!= null) { pw.println(itffullstr); readline++; } pw.println(readline); } }else{ if(increstr.startsWith("0,")){ increlist0.add(increstr.substring(2)); }else if(increstr.startsWith("1,")){ increlist1.add(increstr.substring(2)); }else if(increstr.startsWith("2,")){ increlist2.add(increstr.substring(2)); } } } while ((itffullstr = fullbr.readLine())!= null) { if(itffullstr.indexOf(",")==-1){ System.out.println("fullFile "+filename+" has "+itffullstr+" records"); }else{//有逗號 System.out.println("增量資料是:"+itffullstr); try { boolean flag=false; String flag0 = null; String strinsert=null; /** * 組合如下: * 登出: flag0=remove0 , flag=false * 更新: flag0=add , flag=true * 原始: flag0=add , flag=false * 只有更新的資料 flag0=nothandle ,flag=false */ if(increlist0.size()!=0){ if(increlist1.size()==0){//有登出,無更新 System.out.println("---------------只有登出資料,沒有更新資料"); for (String increstr0 : increlist0) { if(itffullstr.equals(increstr0)) {//如果這條全量資料 is 登出的這條的增量, flag0="remove0"; flag=false; break; } } }else{ //有登出,有更新 System.out.println("-----------------有登出和更新的資料"); for (String increstr0 : increlist0) { if(itffullstr.equals(increstr0)) {//如果這條全量資料 is 登出的這條的增量, flag0="remove0"; break; }else{ flag0="add"; //此條增量資料is not登出資料,是更新的資料,或者原始資料 } } for (String increstr2 : increlist2) { System.out.println("****************更新的資料:"+increstr2); //說明此條全量資料 is 更新資料2 if(!flag0.equals("remove0") && itffullstr.indexOf(increstr2.substring(2,13))!=-1){ flag=true; strinsert=increstr2; break; //說明此條全量資料 is 是原始資料 }else if(flag0.equals("add") && itffullstr.indexOf(increstr2.substring(2,13))==-1){ flag=false; strinsert=itffullstr; } } } }else if(increlist0.size()==0){ flag0="add";//預設為add,原始資料或者更新資料 System.out.println("------------沒有登出只有更新"); if(increlist2.size()!=0){//無登出,有更新 for (String increstr2 : increlist2) { System.out.println("沒有登出的資料,只有更新的資料:"+increstr2); //說明此條全量資料 is 更新資料2 if(!flag0.equals("remove0") && itffullstr.indexOf(increstr2.substring(2,13))!=-1){ flag=true; strinsert=increstr2; break; //說明此條全量資料 is 是原始資料 }else if(flag0.equals("add") && itffullstr.indexOf(increstr2.substring(2,13))==-1){ flag=false; strinsert=itffullstr; } } }else{//無登出,無更新 flag0="nothandle"; flag=false; } } if(flag){//是更新的 if(flag0.equals("add")){ if(itffullstr.indexOf(strinsert.substring(2,13))!=-1){ pw.println(strinsert); readline++; } } }else{//是登出的資料 if(flag0.equals("remove0")){ System.out.println("此全量資料是登出資料,不用新增到新的全量資料中"); } if(flag0.equals("add")){ System.out.println("此條資料是原始資料 ,直接新增到新的全量資料中"); pw.println(itffullstr); readline++; } if(flag0.equals("nothandle")){ System.out.println("此增量資料只有更新的資料,此條資料是原始資料 ,直接新增到新的全量資料中"); pw.println(itffullstr); readline++; } } } catch (Exception e) { e.printStackTrace(); } } } if(increlist1.size()!=0){ for (String increstr1 : increlist1) { pw.println(increstr1); readline++; } } pw.println(readline); } catch (IOException e) { e.printStackTrace(); }finally { try { if (increbr != null) { increbr.close(); } if (fullbr != null) { fullbr.close(); } if (itffullbr != null) { itffullbr.close(); } } catch (Exception e) { e.printStackTrace(); } } }
可能會有很好的辦法,但是這是我能想到最好的辦法,如果你有好的辦法可以給我留言哦!