2013-11-22 5 views
1

내가 정의 20 만 행과 MAC 주소의 3 종류 CSV 파일이 있습니다방법에 MAC 문자열을 변환하는 콜론으로 구분 된 문자열

  • ECE1A9312000
  • E8 : 6D : 52 : 75 : 2D를 : 16
  • 24 C9-A1-15-89-B0

콜론으로 구분 된 양식에만 머물 내 목표.

mac = mac.replace("-", ":"); 

을하지만 어떻게 EC:E1:A9:31:20:00ECE1A9312000 변환 :

그래서 :--은 큰 문제가되지 않습니다 변환합니다.

너무 많은 데이터 (~ 80k)에 그룹을 사용하기에는 너무 비싸다고 생각합니다.

for(int i=0; i<mac.length(); i++){ 
    ch = mac.charAt(i); 

    if(i % 2 == 0 && i != 0){ 
     tmp += ':'; 
    } 
    tmp += ch; 
} 

또는 더 효율적인 방법이 :

내가 같은 :

char 통해 실행하고 추가해야합니까? 발견 된 문자 인 경우

은 문자로 그것을 통해, 매 2 단계를 문자를

+0

80k는 아주 작은 데이터입니다. . 정규 표현식 코드와 특정 타이밍 결과를 게시해야합니다. –

답변

2

. 650ms (워밍업시 250ms) 동안 완료되었습니다. 가장 느린 부분은 정규식을 포함하지 않지만 String.format입니다. 곧바로 StringBuilder 접근 방식으로 바꾸면 시간이 40ms로 떨어집니다. 당신이 정말로 빠른 솔루션을 찾고 있다면

public class Test { 
    static Pattern regex = Pattern.compile("(..)(..)(..)(..)(..)(..)"); 
    public static void main(String[] args) { 
    final List<String> inMacs = new ArrayList<>(), outMacs = new ArrayList<>(); 
    for (int i = 0; i < 80_000; i++) inMacs.add(mac()); 
    final long start = System.nanoTime(); 
    for (String mac : inMacs) { 
     final Matcher m = regex.matcher(mac); 
     m.matches(); 
     outMacs.add(String.format("%s:%s:%s:%s:%s:%s", 
      m.group(1), m.group(2), m.group(3), m.group(4), m.group(5), m.group(6))); 
    } 
    System.out.println("Took " + (System.nanoTime() - start)/1_000_000 + " milliseconds"); 
    final Iterator<String> it = outMacs.iterator(); 
    for (int i = 0; i < 100; i++) System.out.println(it.next()); 
    } 

    static Random rnd = new Random(); 
    static String mac() { 
    final long mac = (long) (rnd.nextDouble()*(1L<<48)); 
    return String.format("%012x", mac).toUpperCase(); 
    } 
} 

, 다음 정규식을 방지하고 MAC 포맷 감지하는 간단한 테스트를 사용 : 나는 당신의 80,000 만 8 밀리 측정이 방법

static List<String> fixMacs(List<String> inMacs) { 
    final List<String> outMacs = new ArrayList<>(inMacs.size()); 
    for (String mac : inMacs) outMacs.add(
      mac.charAt(2) == '-'? mac.replace("-", ":") 
     : mac.charAt(2) != ':'? fixMac(mac) 
     : mac); 
    return outMacs; 
    } 

    static String fixMac(String inMac) { 
    final StringBuilder b = new StringBuilder(18); 
    for (int i = 0; i < inMac.length(); i++) { 
     b.append(inMac.charAt(i)); 
     if (i%2 == 1 && i != inMac.length()-1) b.append(':'); 
    } 
    return b.toString(); 
    } 

을 맥.

+0

@ MarcoTopolnik, upvote 수 없습니다, 단지 3 pres있다 – snaggs

1

으로 반복을 주셔서 감사합니다 '-'로 교체 ':',이 편지는 나 숫자 다음에 삽입 할 경우 ':'문자를 . E1 : A9 :

+0

내가 물었던 것이 아니기 때문에 나는 'ECE1A9312000 -> EC : E1 : A9 : 31 : 20 : 00'이 필요하다. – snaggs

+0

@ fessy 내 대답을 확인하고이 방법을 원한다면 알려줘 – SpringLearner

1

String x="ECE1A9312000"; 
String finals=""; 
for(int i=0;i<x.length();i=i+2) 
{ 
    if((i+2)<x.length()) 
finals+=x.substring(i, i+2)+":"; 
    if((i+2)==x.length()) 
    { 
     finals+=x.substring(i, i+2); 

    } 

} 
System.out.println(finals); 

출력 EC 시도 31 : 20 : 00 I 함께하여 폐기 정규식 방식에 기초하여 완전히 최적화되지 않은 프로그램을 던지고을 초과

+0

나는 위에 게시했다? 'substring', hmm – snaggs

+0

당신의 방식대로 @fessy for 루프는 12 회 실행될 것입니다. 왜냐하면 당신은 i ++을하고 있기 때문에 i = 2를하고 있지만 이것은 중요하지 않을 것입니다. 그러나 문자로 문자를 읽는 대신 왜 그것도 부분 문자열이 아닌 다른 검색어가 있으면 알려주세요. – SpringLearner

+0

이 질문에 대한 가장 간단하고 최상의 대답입니다. –

0
String mac[] = {"ECE1A9312000", "24-C9-A1-15-89-B0", "E8:6D:52:75:2D:16"}; 

    for (int i = 0; i< mac.length; i++) 
    { 
     if (mac[i].charAt(2) == '-') 
      mac[i] = mac[i].replace("-", ":"); 
     else if (mac[i].charAt(2) != ':') 
      mac[i] = new StringBuilder(mac[i].substring(0,2)).append(":").append(mac[i].substring(2,4)) 
        .append(":").append(mac[i].substring(4,6)).append(":").append(mac[i].substring(6,8)) 
        .append(":").append(mac[i].substring(8,10)).append(":").append(mac[i].substring(10)).toString();   
    } 
    for (int i = 0; i< mac.length; i++) 
     System.out.println(mac[i]); 

출력 : String.join를 사용

EC:E1:A9:31:20:00 
24:C9:A1:15:89:B0 
E8:6D:52:75:2D:16 
+0

@ MarkoTopolnik 예! 고맙습니다! 나는 그것을 제거했습니다. – neutrino

+0

나는이 시간을 잰 적이 있고 그것은 정규식에 대한 나의 접근 방식과 마찬가지로 빠르거나 느리다. 나는 성능에 대한 OP의 불평이 중요하다고 생각하지 않습니다. –

+0

입력이 3 가지 형식으로 제한되어 있기 때문에 형식을 감지하는 가장 효율적인 방법은'mac [2]'를 확인하는 것입니다. –

0

분할 매 2 개 문자 정규 표현식와 구분하여 가입 :

public static String convertToColonSeparatedMac(String mac) { 

    if (mac.contains(":")) 
     return mac; 

    if (mac.contains("-")) 
     return mac.replaceAll("-", ":"); 

    return String.join(":", mac.split("(?<=\\G.{2})")); 
} 

그리고 당신은 변환하기 전에 유효성을 검증 할 수 있습니다

private static final Pattern MAC_PATTERN = Pattern.compile("(^([0-9A-Fa-f]{2}[:-]){5}([0-9A-Fa-f]{2})$)|([0-9A-Fa-f]{12})"); 

public static boolean isValidMac(String mac) { 
    return MAC_PATTERN.matcher(mac).matches(); 
}