2012-12-18 8 views
2

지난 달 나는 photomosaic 웹 사이트에서 작업했습니다. PHP로 모든 것을 구축하고 잘 작동합니다. 내가 싫어하는 유일한 것은 실행 시간입니다. 이것은 선형 비교 검색 때문에 너무 오래 생각합니다. 그래서 나는 검색 시간을 향상시키는 방법에 대해 물어 보았고 대부분의 사람들은 k- 이웃을 더 빨리 만드는 KD- 트리의 방향으로 나를 지적했다.사진 모자이크 웹 응용 프로그램입니다. KD 트리

그래서 저는 KD- 트리를 조사해 왔고 수동으로 그러한 트리를 구성하는 방법을 알고 있습니다. 이제이 코드를 작성하고 싶습니다. C++ 및 java 라이브러리 만 찾을 수있었습니다. 필자는 PHP에 대해서만 잘 알고 있기 때문에 직접 만들려고 노력했지만이 방법은 생각만큼 쉽지 않습니다.

• 내가 당면한 문제는 모든 것을 저장하는 방법입니다. 내가 그 안에 모든 포인트를 가진 첫 번째 배열을 얻었을 때 나는 그것을 3 조각에 침을 뱉을 것이다. 왼쪽 분기, 노드 및 오른쪽 분기. 물론 더 이상 나눌 수 없을 때까지 왼쪽 브랜치에서 똑같이 할 것입니다. 물론 축 (XYZ)을 순환합니다. 그러나 내가 어떻게 알맞은 가지를 보관합니까? 또는 그들을 사용할 준비가되면 다시 계산합니까?

• 내가 궁금해했던 또 다른 이유는 PHP가이 작업에 적합한 언어가 아니기 때문에 PHP KD 트리 스크립트가없는 이유입니다.

이것은 내가 지금까지 가지고있는 것입니다.

이 함수는 나머지를 테스트하는 데 사용하는 임의의 색상 (RGB)을 계산합니다.

<?php 
function randomiser($number){ 

    if($number <= 0){ 
     echo 'Error: The input of randomiser() is less than or equal to zero !!'; 
     return FALSE;   
    }else{ 
     $R = array(); 
     $G = array(); 
     $B = array(); 

     for($x = 1; $x <= $number; $x++){ 
      $r = rand(1, 255); 
      $g = rand(1, 255); 
      $b = rand(1, 255); 

      $rgb['pic ' . $x]['R'] = $r; 
      $rgb['pic ' . $x]['G'] = $g; 
      $rgb['pic ' . $x]['B'] = $b;  
     } 
    } 
return $rgb; 
} 
?> 

이 함수 종류의 특정 키에 대한 다차원 배열 (기본값은 R입니다)

<?php 
function sorter(&$array, $key = 'R'){ 

    if(!is_array($array)){ 
     echo 'Error: The input of sorter() is not an array !!<br>'; 
     return FALSE;   
    }else{ 
     uasort($array, function ($a, $b) use ($key){ 
      return strnatcmp($a[$key], $b[$key]); 
     }); 
    } 
} 
?> 

이 클래스는 왼쪽 지점, 노드 및 오른쪽 지점에있는 배열을 분할합니다.

<?php 
class splitting { 

    public $left; 
    public $node; 
    public $right; 

    function __construct($array){ 

     if(!is_array($array)){ 
      echo 'Error: The input of splitter() is not an array !!<br>'; 
      return FALSE;   
     }else{ 
      $number = count($array); 
      $median = round($number/2) - 1; 

      $this->left = array_slice($array, 0, $median); 
      $this->node = array_slice($array, $median, 1); 
      $this->right = array_slice($array, $median+1); 
     } 
    } 
} 
?> 

답변

0
  1. 당신은 왼쪽 $ 및 $ 권리 변수가 아닌 배열 또는 당신이 일을해야하는 변수의 나무에 포인터를 저장해야합니다. kd-tree가 너무 복잡하다면 r-tree도 살펴볼 것입니다. r- 트리는 평면을 4 개의 가장자리, 즉 참 2 차원으로 분할하고, kd- 트리는 단지 이진 트리이다. 그러면 중간 값을 백업하기 위해 $ payload 또는 기타 변수가 필요합니다.
  2. 아니요. 또한 PHP 트리 예제를 찾을 수 있습니다. 다음은 예입니다. http://blog.sandfox.co.uk/2012/09/10/php-kdtree/. 당신은 또한 PHP에서 카트 타 트리 구현을 찾을 수 있습니다. OO 및 노드 및 에지 클래스도 사용합니다. 다음은 lightmap을 http://www.blackpawn.com/texts/lightmaps/default.html에서 kd-tree로 패킹하는 스크립트입니다.

    struct Node 
    { 
        Node* child[2] 
        Rectangle rc 
         int imageID 
    } 
    
    Node* Node::Insert(const Image& img) 
         if we're not a leaf then 
         (try inserting into first child) 
         newNode = child[0]->Insert(img) 
         if newNode != NULL return newNode 
    
    (no room, insert into second) 
         return child[1]->Insert(img) 
        else 
    (if there's already a lightmap here, return) 
    if imageID != NULL return NULL 
    
    (if we're too small, return) 
    if img doesn't fit in pnode->rect 
        return NULL 
    
    (if we're just right, accept) 
    if img fits perfectly in pnode->rect 
        return pnode 
    
    (otherwise, gotta split this node and create some kids) 
    pnode->child[0] = new Node 
    pnode->child[1] = new Node 
    
    (decide which way to split) 
    dw = rc.width - img.width 
    dh = rc.height - img.height 
    
    if dw > dh then 
        child[0]->rect = Rectangle(rc.left, rc.top, 
               rc.left+width-1, rc.bottom) 
        child[1]->rect = Rectangle(rc.left+width, rc.top, 
               rc.right, rc.bottom) 
    else 
        child[0]->rect = Rectangle(rc.left, rc.top, 
               rc.right, rc.top+height-1) 
        child[1]->rect = Rectangle(rc.left, rc.top+height, 
               rc.right, rc.bottom) 
    
    (insert into first child we created) 
    return Insert(img, pnode->child[0])