> 백엔드 개발 > PHP 튜토리얼 > 인터넷 기록을 위해 PHP로 백만 개의 이미지 그리드 채우기

인터넷 기록을 위해 PHP로 백만 개의 이미지 그리드 채우기

Susan Sarandon
풀어 주다: 2025-01-16 12:04:19
원래의
292명이 탐색했습니다.

10MPage.com: 2025년 인터넷 아카이브 – 천만 개의 이미지에 대한 타일 배치 최적화

저는 2025년 인터넷 상태를 포착하는 것을 목표로 하는 야심찬 프로젝트인 10MPage.com을 구축하고 있습니다. 각 사용자는 이 대규모 온라인 아카이브에 64x64 픽셀 이미지를 제공할 수 있습니다. 이미지 추가에는 다단계 프로세스가 포함됩니다. 업로드하면 대기 중인 타일이 생성되며 그리드에 배치하기 전에 승인이 필요합니다.

그리드 자체는 각 행이 X 및 Y 좌표가 있는 1x1 타일을 나타내는 데이터베이스 테이블(tiles이라고 함)입니다. 보류 중인 더 큰 타일은 여러 개의 1x1 타일로 나뉩니다. 과제: 1,000만 개의 항목을 수용할 수 있도록 이러한 타일을 확장 그리드에 효율적으로 배치하는 것입니다.

빈 공간을 검색하는 간단한 루프인 나의 초기 접근 방식은 비참한 것으로 판명되었습니다. 수천 개의 타일을 추가하는 데 몇 초가 걸렸습니다. 1,000만 개로 추정하면 완료 시간이 몇 년이 걸릴 것으로 예상됩니다!

초기 접근 방식(비효율적):

첫 번째 시도에서는 사용 가능한 공간을 찾기 위해 전체 그리드를 반복했습니다. 그리드는 대략 정사각형 모양을 유지하도록 동적으로 확장되었습니다. 핵심 find() 방법은 다음과 같습니다.

<code class="language-php">public function find(int $blockWidth, int $blockHeight): array
{
    // ... (code to determine grid dimensions) ...

    // Look for a fitting spot
    for ($y = 0; $y < $newHeight; $y++) {
        for ($x = 0; $x < $newWidth; $x++) {
            if ($this->canPlaceBlock($x, $y, $blockWidth, $blockHeight)) {
                return ['x' => $x, 'y' => $y];
            }
        }
    }
    return [0, 0];
}

// ... (canPlaceBlock method) ...</code>
로그인 후 복사

항상 (0,0)부터 검색을 시작했기 때문에 속도가 느렸습니다. 최적화에는 단일 데이터베이스 쿼리를 사용하는 보다 효율적인 canPlaceBlock 방법이 포함되었습니다.

<code class="language-php">public function canPlaceBlock(int $startX, int $startY, int $blockWidth, int $blockHeight): bool
{
    $ys = range($startY, $startY + $blockHeight - 1);
    $xs = range($startX, $startX + $blockWidth - 1);
    return !Tile::whereIn('x', $xs)->whereIn('y', $ys)->exists();
}</code>
로그인 후 복사

최소 기존 X 및 Y 좌표에서 검색을 시작하여 find()을 최적화하려는 추가 시도도 성능을 크게 향상시키지 못했습니다. 더 빠른 검사를 위해 전체 그리드를 메모리에 로드하는 것은 메모리를 너무 많이 사용하는 것으로 나타났습니다.

해결책: 배치 블록

확장성의 핵심은 블록 기반 접근 방식을 채택하는 것이었습니다. 새로운 placement_blocks 데이터베이스 테이블로 관리되는 100x100 타일 단위인 "배치 블록"을 소개했습니다. 각 블록은 최소/최대 X 및 Y 좌표와 "전체" 부울 플래그를 추적합니다.

이 접근 방식은 두 가지 주요 이점을 제공합니다.

  1. 검색 공간 감소: 이제 빈 공간 검색이 100x100 영역으로 제한됩니다.
  2. 동시성: 여러 프로세스가 동시에 타일을 다른 블록에 배치할 수 있습니다.

Filling a Million Image Grid with PHP for Internet History

배치 블록 찾기 및 사용:

재귀 함수는 사용 가능한 배치 블록을 효율적으로 찾거나 필요에 따라 새 블록을 생성합니다.

<code class="language-php">public function find(array $excludeBlocks = []): PlacementBlock
{
    // ... (code to find or create placement blocks) ...
}</code>
로그인 후 복사

place() 메서드는 이 기능을 활용하며 전역 잠금을 사용하여 블록 선택을 조정하고 블록별 잠금을 사용하여 경쟁 조건을 방지합니다.

<code class="language-php">public function place(PendingTile $pendingTile): void
{
    // ... (code to acquire locks and place tiles) ...
}</code>
로그인 후 복사

타일은 최적화된 canPlaceBlock 방법을 사용하여 배치 블록 내에 추가됩니다. 현재 단일 배치 블록보다 큰 타일은 지원되지 않습니다.

동시성 및 확장성:

Laravel 작업과 Horizon은 동시 타일 배치를 관리합니다. 작업자 수는 사용 가능한 배치 블록 수와 일치하거나 작아야 합니다. 이를 통해 쉽게 수평 확장이 가능합니다.

이러한 개선된 접근 방식은 타일 배치 프로세스의 속도와 확장성을 극적으로 향상시켜 10MPage.com의 야심 찬 목표를 달성할 수 있게 해줍니다. 오늘 프로젝트에 참여하고 기여도를 추가하세요!

위 내용은 인터넷 기록을 위해 PHP로 백만 개의 이미지 그리드 채우기의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
저자별 최신 기사
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿