2014-05-24 3 views
3

일부 바이너리 데이터의 헥사 문자열 표현 (예 : x00)을 데이터 자체로 변환하는 함수를 작성했습니다.QByteArray 변환의 Qt 최적화

이 코드를 향상시키는 방법?

QByteArray restoreData(const QByteArray &data, const QString prepender = "x") 
{ 
    QByteArray restoredData = data; 

    return QByteArray::fromHex(restoredData.replace(prepender, "")); 
} 

답변

1

이 코드를 향상시키는 방법?

최적화하기 전에 벤치 마크하십시오. 조숙 한 최적화를하지 마십시오.

주요 요점을 넘어서 : 왜 최적화하고 싶습니까?

1) 퍼포먼스 관점에서 볼 때이 무시할 수있는 코드가 중요한 성능에 대해 정말로 염려한다면 Qt가 잘 최적화 된 프레임 워크에 비해 본질적으로 느리기 때문에 처음부터 Qt를 사용하지 않을 것입니다.

2) 성능에 관심이 없다면 가독성 및 유지 관리를 염두에 두어야합니다.이 경우 코드가 문제가되지 않습니다.

정확히 원하는 이유를 실제 사례로 제시하지 않았습니다. 이것은 나에게 많은 소박한 사용없이 학문적 인 질문처럼 느껴진다. 동기 부여에 대해 더 많이 아는 것은 흥미로울 것입니다.

최적화라고도하는 몇 가지 개선 항목이 코드에서 수행 될 수 있지만 다시 말하면 최적화를 위해 수행되지는 않지만 논리적 인 이유와 비슷합니다.

1) 프리 펜더는 나쁜 이름입니다. 일반적으로 영어로 "접두어"라고 불립니다.

2) 캐릭터의 QString이 아닌 QChar를 사용하고 싶습니다.

3) 마찬가지로 대체 할 경우 string'ish "공식 대신" '을 사용하고 싶습니다.

4) CoW (암시 적으로 공유 됨) 인 경우에도 값 의미에 반하는 참조 클래스를 전달할 것입니다.

5) 접두사는 항상 동일하므로 변수의 정의에 실제로 맞지 않으므로 인수를 사용하지 않습니다.

6) 명시 적으로 임시 변수를 만들 필요는 없습니다.

7) 함수를 인라인으로 만듭니다.

따라서이 같은 것을 쓰는 것 :

QByteArray restoreData(QByteArray data) 
{ 
    return QByteArray::fromHex(data.replace('x', '')); 
} 
+0

또한 QString처럼 편의를 위해'제거 (QChar)'방법을 묻는 선택할 수 있습니다. 그러면 코드를 대체하지 않고 논리적으로 제거 할 수 있습니다. – lpapp

1

코드에 replace() (으)로 인해 성능 문제가 있습니다. 교체 자체가 매우 빠르지 않으며 중간에 QByteArray 객체를 만들면 코드가 더 느려집니다. 성능에 대해 정말로 염려하는 경우 Qt 소스에서 QByteArray::fromHex 구현을 복사하고 필요에 맞게 수정할 수 있습니다. 운좋게도 그 구현은 꽤 독립적입니다. / 2/ 3으로 변경하고 --i 줄을 추가하여 "x"문자를 건너 뛰었습니다.

QByteArray myFromHex(const QByteArray &hexEncoded) 
{ 
    QByteArray res((hexEncoded.size() + 1)/ 3, Qt::Uninitialized); 
    uchar *result = (uchar *)res.data() + res.size(); 

    bool odd_digit = true; 
    for (int i = hexEncoded.size() - 1; i >= 0; --i) { 
     int ch = hexEncoded.at(i); 
     int tmp; 
     if (ch >= '0' && ch <= '9') 
      tmp = ch - '0'; 
     else if (ch >= 'a' && ch <= 'f') 
      tmp = ch - 'a' + 10; 
     else if (ch >= 'A' && ch <= 'F') 
      tmp = ch - 'A' + 10; 
     else 
      continue; 
     if (odd_digit) { 
      --result; 
      *result = tmp; 
      odd_digit = false; 
     } else { 
      *result |= tmp << 4; 
      odd_digit = true; 
      --i; 
     } 
    } 

    res.remove(0, result - (const uchar *)res.constData()); 
    return res; 
} 

테스트 : hexEncoded이 잘못된 경우이 코드는 예기치 않게 행동 할 수

qDebug() << QByteArray::fromHex("54455354"); // => "TEST" 
qDebug() << myFromHex("x54x45x53x54"); // => "TEST" 

가 (. .e.g "x54x45x5" "TU"로 변환됩니다). 문제가 발생하면 문제를 해결할 수 있습니다.