|
[ 직접 테스트 해보니.]
memcopy로 120Byte씩 100*4800번 for문 아무리 돌려도 40ms이상 걸리지 않는데요...
코드를 한번 올려봐 주시죠..
[버퍼 선언에 대해.]
그리고 ... buffer를 선언할때
1. char cBuf[120*100][4800];
2 . char cBuf[4800][120*100];
1번과 같이 선언하면 가로 4800 , 세로 12000 개 입니다.
무슨말이냐면 메모리 순서로 볼때 4800개씩 ... 12000 개 있다는 뜻입니다.
즉 이경우 120개 짜리를 가로 100번 세로 4800번 copy한다는게 말이 이상합니다.
그렇게 하려면 2번과 같이 버퍼를 선언해야 아래와 같은 code가 나올수 있습니다.
----------------------------------------
for(int i=0;i<4800;i++)
for(int j=0;j<100;j++)
memcpy( *** , *** , 120);
----------------------------------------
1번과 같이 선언하면 한번데 120개씩 순서대로 copy가 안될것입니다.
3 . char cBuf[100][120][4800];
4 . char cBuf[100][4800][120];
위 3,4번과 같이 버퍼를 선언하면 아래와 같은 구문이 나올수 있구요..
for(int i=0;i<100;i++)
memcpy( *** , *** , 120*4800 );
@ memset , memcpy, memmove 속도...
int tick=GetTickCount();
for(int i=0;i<4800;i++)
{
for(int j=0;j<100;j++)
{
//1. memset(&cBuf[i][ j*120],cBase[i][0], 120);
//2. memcpy(&cBuf[i][ j*120],&cBase[i][0], 120);
//3. memmove(&cBuf[i][ j*120],&cBase[i][0], 120);
}
}
ShowMessage(IntToStr(GetTickCount()-tick));
위 코드에서 1,2,3번 주석된것을 하나씩 풀어서 test해보니..
걸리는 시간이
memcpy < memset < memmove 순으로 나오더군요
[memset보다 memcopy가 ...]
보통 초기화 할때 전체가 같은값으로 셋팅할때 memset을 사용합니다.
그러나 님의 경우 모두가 같은 값이 아니라 일정한 패턴을 지닌 값입니다.
위와 같은 경우 memset보다는
일정한 패턴값을 초기화 해 놓고 그 패턴을 반복해서 복사하는 memcopy가 더 좋을것 같습니다.
그럼...
이용태 님이 쓰신 글 :
: 밑에 글에서 제가 설명을 자세히 하지 못한거 같아서 다시 글 올립니다.
:
: 자세히 설명을 하면요... 일단
:
: 원본 데이터는 다음과 같습니다.
:
: 데이터 셋트가 120개 있습니다. 한 셋트는 다시 데이터 4800개로 이루어집니다.
:
: 그러므로 총 데이터 포인트 수는 120개셋트 = 120*4800개입니다.
:
: a[120] [4800] <-- 원본 데이터
:
: 가로 120개..
: 세로 4800개로 다음과 같이 메모리 구조가 되어 있겠죠..(배열에 들어가 있는 값은 랜덤값으로 가정했습니다...)
: --->가로 120
: ___________________ ___________________
: 0|2|8|9|1|3|4|5|0|1 ---중간생략 --- 1|4|1|2|8|9|6
: 9|2|7|1|3|5|8|0|1|4 ----중간생략 --- 2|3|7|2|7|9|1
: | | |
: 중간생략 중간생략 중간생략
: | | |
: 0|1|5|7|2|5|6|7|9|4 ---중간생략 --- 1|5|7|2|7|8|0
: 8|2|2|2|3|3|7|1|2|4 ----중간생략 --- 1|2|3|2|1|2|4
: ___________________ ___________________
: 세로 4800
:
:
: 여기서 120*4800개의 데이터 한개한개를 가로로 100개씩 뻥튀기를 합니다..
:
: 그러면 총 데이터 개수는 120*100*4800입니다. 데이터 형은 BYTE 입니다.
:
: b[120*100][4800] <--- 가로로 100배 뻥튀기 된 데이터
:
: 메모리 구조는 다음과 같겠죠..
:
:
: 가로 120*100개
: ___________________ ___________________
: 0|0|0|0|0|0|0|0|0|0|2|2|2|2|2|2|2|2|2|2 ---중간생략 --- 9|9|9|9|9|9|9|9|9|6|6|6|6|6|6|6|6|6|6|
: 9|9|9|9|9|9|9|9|9|9|7|7|7|7|7|7|7|7|7|7 ----중간생략 --- 9|9|9|9|9|9|9|9|9|1|1|1|1|1|1|1|1|1|1|
: | | |
: 중간생략 중간생략 중간생략
: | | |
: 0|0|0|0|0|0|0|0|0|0|1|1|1|1|1|1|1|1|1|1| ---중간생략 --- 8|8|8|8|8|8|8|8|8|8|0|0|0|0|0|0|0|0|0|0
: 8|8|8|8|8|8|8|8|8|8|2|2|2|2|2|2|2|2|2|2| ----중간생략 --- 2|2|2|2|2|2|2|2|2|2|4|4|4|4|4|4|4|4|4|4
: ___________________ ___________________
: 세로 4800개
:
:
: 데이터 맵을 위와 같이 만들려고 하려다 보니... for()문을 돌려 원본 데이터(a[])로부터 일일히 해당 가로/인덱스에 해당하는 값을 읽어와 순차적으로 한개씩 값을 대입하는것보단 한꺼번에 범위로 값을 때려박는게 효율적이어서 memset()를 사용했던 것이죠...
:
: 이렇게 하여 데이터 맵을 만들어보니... memset()가 120*4800번 수행을 하게 되어 시간이 대략 0.23초 정도 걸리더군요..
:
: 데이터를 만든 후, 이미지 맵핑을 하고 각종 다른 부가 작업을 하니 시간이 0.32초 정도 걸립니다. 전체 작업에서 데이터 만드는 부분에서 무려 2/3의 시간을 잡아 먹게 되는거죠...
: 그래서 어떻게 해서든지 memset()보다 더 빠른 함수를 사용하던지 아니면 memset()를 적게 사용하는것이 답인거 같아서 여러가지 생각을 해봤습니다.
:
: memset()보다 빠른 함수를 찾지 못해서... memset()를 적게 사용할 수 있는 방법을 강구해봤습니다.
:
: 위의 데이터 그림에서와 같이.. 한셋트 데이터가 세로로 4800개씩.. 가로로 120개씩 늘어져 있는 모습입니다.
:
: 지금 방법은 각 데이터 포인트에 대해 memset()를 적용하여 뻥튀기를 했기 때문에 4800*120번 memset()을 사용하게 됩니다.
: 그런데 이것을 만약에 세로로 데이터 한셋트를 통채로 복사하여 가로로 복사를 하게 된다면 memset()를 120번만 수행하면 되죠...
:
: 그래서 어떻게 할 수 있을까 생각하면서 테스트를 해봤으나 도저히 방법이 떠오르지 않습니다.
:
: 배열에서 인접한 가로의 값을 긁어와 memcpy()로 복사 할 수 는 있지만.. 세로로 인접한 값은 한꺼번에 긁어오지 못하므로 memcpy()를 쓰지 못하더군요...
:
: 어떻게 하면 될까요?
:
: 0.23초는 너무 많이 걸립니다.. 0.1초 이하로 데이터 맵을 만들 수 있게끔 할려고 하는데요... 어떻게 하면 될까요??
|