2012-02-13 1 views
1

Im '입력 이미지의 모든 픽셀을 가장 근접한 RGB로 대체하려고합니다. 색상 및 입력 이미지가 포함 된 배열이 있습니다. 여기 내 코드입니다, 그것은 내게 예상대로 출력 이미지를 제공하지만 한 이미지를 처리하는 데 오랜 시간 (약 분)이 걸립니다. 아무도 내가 코드를 개선하는 데 도움을 줄 수 있습니까? 또는 다른 제안이 있으면 도움을주십시오.이 이미지 처리를 최적화하는 방법 가장 가까운 사용 가능한 RGB로 이미지의 모든 픽셀을 대체 하시겠습니까?

UIGraphicsBeginImageContextWithOptions(CGSizeMake(CGImageGetWidth(sourceImage),CGImageGetHeight(sourceImage)), NO, 0.0f); 
//Context size I keep as same as original input image size 

//Otherwise, the output will be only a partial image 
CGContextRef context; 
context = UIGraphicsGetCurrentContext(); 

//This is for flipping up sidedown 
CGContextTranslateCTM(context, 0, self.imageViewArea.image.size.height); 
CGContextScaleCTM(context, 1.0, -1.0); 



     // init vars 
     float d = 0;       // squared error 
     int idx = 0;        // index of palette color 
     int min = 1000000;      // min difference 
     UIColor *oneRGB;       // color at a pixel 
     UIColor *paletteRGB;      // palette color 



     // visit each output color and determine closest color from palette 
     for(int y=0; y<sizeY; y++) { 
      for(int x=0; x<sizeX; x++) { 
       // desired (avg) color is one pixel of scaled image 
       oneRGB = [inputImgAvg colorAtPixel:CGPointMake(x,y)]; 


       // find closest color match in palette: init idx with index 
       // of closest match; keep track of min to find idx 
       min = 1000000; 
       idx = 0; 

       CGContextDrawImage(context,CGRectMake(xx, yy, 1, 1),img); 
      } 
     } 

     UIImage *output = UIGraphicsGetImageFromCurrentImageContext(); 
     UIGraphicsEndImageContext(); 
     self.imageViewArea.image = output; 
+1

코드 중 가장 오래 걸리는 부분 (루프,'UIGraphics' 또는'CGContext' 함수 등)은 무엇입니까? 코드 프로파일. – Jacob

+0

'ColorDiff'의 코드는 무엇입니까? 또한, 컨벤션은 초기 소문자로 메소드를 명명하는 것입니다. 예 :'[self colorDiffWithPalette : paletteRGB forRGB : oneRGB]' – zaph

+0

@Jacob : 루프가 대부분의 시간을 소비한다고 말합니다. – user1139699

답변

1

이것은 비슷한 질문입니다 (확실한 답변 없음). 그러나 거기에 대한 대답은 이미지의 픽셀에 직접 액세스하기위한 코드입니다.

Quantize Image, Save List of Remaining Colors

각 get 및 set 픽셀의 사용 CG 기능보다는 그렇게해야한다. 이미지의 1 픽셀을 다른 이미지로 드로잉하는 것은 배열에서 3 바이트를 변경하는 것보다 훨씬 느립니다.

또한 ColorDiff에는 무엇이 있습니까? 가장 가까운 픽셀이 가장 작은 diff 일 경우 완벽하게 diffing 할 필요가 없습니다. 이 목록을 사전 처리 할 여지가 있으므로 각 팔레트 항목에 대해 가장 가까운 다른 팔레트 항목과의 차이가 가장 작습니다. 그런 다음 픽셀을 반복하면서 다음 픽셀이 발견 된 색상의 절반 이내에 있는지 신속하게 확인할 수 있습니다 (사진은 서로 가깝게 공통 색상을 갖는 경향이 있으므로).

일치하지 않는 경우 팔레트를 반복하면서이 항목까지의 거리가 반이라면 더 확인하지 않아도됩니다.

기본적으로 각 팔레트 엔트리 주변에이 영역이 가장 가까운 지 확인하는 영역이 있습니다.

+0

특히 이전에 발견 된 팔레트 항목에 대해 사용했을 때 조기 종료를위한 최적의 최적화. 선형 검색의 경우 검색 시간을 평균적으로 절반으로 줄이기 때문에 가능한 솔루션 자체가 될 수는 없습니다. 거리의 제곱을 비교할 때 1/4을 값의 1/4로 사용하고 싶으면 반값이 아니라. –

+0

실제 이미지에서 거의 동일한 색상의 색상이 자주 발생하므로 절반 이상을 얻는다고 생각합니다. 나는 진짜 해결책이 픽셀에 대한 직접적인 메모리 접근을 사용하는 것이라고 생각한다 - 다른 아이디어는 아마 그 효과에 근접하지 않을 것이다. –

+0

방금 ​​RGB 배열로 작동하는지 테스트하기 시작했습니다. 그러면 내 목표는 입력 이미지의 픽셀을 통해 읽혀지고 바꿀 모든 가장 가까운 타일 이미지를 찾습니다. 즉, RGB 만 변경할 수는 없습니다. – user1139699

1

일반적으로 대답은 k-d tree 또는 다른 Octree 구조를 사용하여 각 픽셀에서 수행해야하는 계산 및 비교 횟수를 줄이는 것입니다.

나는 또한 색 공간을 일반 그리드로 분할하고 그리드의 각 부분에 가능한 가장 가까운 일치 목록을 유지하는 데 성공했습니다. 예를 들어, R, G, B의 (0-255) 값을 16으로 나눌 수 있고 (16,16,16) 또는 4096 요소의 격자로 끝날 수 있습니다. 가장 좋은 경우는 특정 그리드 요소에 대해 목록의 단 하나의 구성원 만 있고 목록을 전혀 탐색 할 필요가 없다는 것입니다.

+0

나는 무엇을 말하는지 이해합니다. 이것이 저해상도로 내 처리 이미지를 축소 한 다음 처리를 수행하는 이유입니다. – user1139699

관련 문제