2014-11-13 3 views
0

숫자가있는 2D 배열을 임의의 치수로 다시 스케일하는 방법을 찾고 있는데, 재 배열 된 셀의 각 셀에 (부분적으로) 커버하는 모든 셀의 가중 평균이 포함되어 있습니다. .2D 샘플을 임의의 치수로 다시 채우기

새 치수가 원래 치수의 배수 인 경우이를 수행하는 몇 가지 방법을 발견했습니다. 예를 들어, 4x4 배열이 주어지면, 이것은 2x2 배열로 재조정 될 수 있습니다. 첫 번째 셀은 원래의 4 개의 왼쪽 상단 셀의 평균입니다.하지만이 방법 중 어떤 것도 4x4 배열을 3x3 배열로 배열하십시오. 커버 작은 배열에 https://www.dropbox.com/s/iutym4frcphcef2/regrid.png?dl=0

셀 (0,0) :

이 이미지는 내가 3 × 3으로 4 × 4 (검은 색 계통)에서 (빨간색 격자를)가는 경우에 수행하고 싶은 것을 보여 전체 셀 (0,0) 및 셀 (1,0), (0,1) 및 (1,1)의 일부. 나는 새로운 세포가 노란색, 녹색, 파란색 및 주황색 영역의 영역에 의해 가중 된 이들 세포의 평균을 포함하고 싶습니다.

numpy/scipy로이 작업을 수행 할 방법이 있습니까? 이 유형의 재정리를위한 이름이 있습니까 (이는 방법을 검색 할 때 도움이됩니다)? #

그것은 쉽게 다른 그리드의 세포의 중복을 계산하는 Interval 패키지를 사용하기 때문에 당신은 잡아해야합니다 : 여기

+0

당신이 말하는 것은 보간법입니다. numpy/scipy에서 여러 가지 방법이 있습니다. [다음은 그 중 하나입니다] (http://docs.scipy.org/doc/scipy-0.14.0/reference/tutorial/interpolate.html#two-dimensional-spline-representation-procedural-bisplrep) (편집 : 업데이트 됨 더 좋은 예에 대한 링크) – will

+0

나는 여러 가지 보간 방법을 이미 실험 해왔다. 그러나 그 중 아무 것도 나에게 내가 설명한 결과를 제공하지는 못했다. – user3468216

+0

당신이 묘사하는 것은 정확하게 보간법입니다. 선형이든, 스플라인이든, 또는 다른 메트릭이 좋을 지 결정해야합니다. – will

답변

0

는 당신은 간다. 너무 가능하다

2x2 grid mapped to a 5x5 grid

3x2 grid mapped to 5x7

5x5-59x59

샘플링 다운 : 여기

from matplotlib import pyplot 
import numpy 
from interval import Interval, IntervalSet 

def overlap(rect1, rect2): 
    """Calculate the overlap between two rectangles""" 
    xInterval = Interval(rect1[0][0], rect1[1][0]) & Interval(rect2[0][0], rect2[1][0]) 
    yInterval = Interval(rect1[0][1], rect1[1][1]) & Interval(rect2[0][1], rect2[1][1]) 
    area = (xInterval.upper_bound - xInterval.lower_bound) * (yInterval.upper_bound - yInterval.lower_bound) 
    return area 


def meanInterp(data, m, n): 

    newData = numpy.zeros((m,n)) 
    mOrig, nOrig = data.shape 

    hBoundariesOrig, vBoundariesOrig = numpy.linspace(0,1,mOrig+1), numpy.linspace(0,1,nOrig+1) 
    hBoundaries, vBoundaries = numpy.linspace(0,1,m+1), numpy.linspace(0,1,n+1) 

    for iOrig in range(mOrig): 
    for jOrig in range(nOrig): 
     for i in range(m): 
     if hBoundaries[i+1] <= hBoundariesOrig[iOrig]: continue 
     if hBoundaries[i] >= hBoundariesOrig[iOrig+1]: break 
     for j in range(n): 
      if vBoundaries[j+1] <= vBoundariesOrig[jOrig]: continue 
      if vBoundaries[j] >= vBoundariesOrig[jOrig+1]: break 

      boxCoords = ((hBoundaries[i], vBoundaries[j]),(hBoundaries[i+1], vBoundaries[j+1])) 
      origBoxCoords = ((hBoundariesOrig[iOrig], vBoundariesOrig[jOrig]),(hBoundariesOrig[iOrig+1], vBoundariesOrig[jOrig+1])) 

      newData[i][j] += overlap(boxCoords, origBoxCoords) * data[iOrig][jOrig]/(hBoundaries[1] * vBoundaries[1]) 

    return newData 



fig = pyplot.figure() 
ax1 = fig.add_subplot(1,2,1) 
ax2 = fig.add_subplot(1,2,2) 

m1, n1 = 37,59 
m2, n2 = 10,13 

dataGrid1 = numpy.random.rand(m1, n1) 
dataGrid2 = meanInterp(dataGrid1, m2, n2) 

mat1 = ax1.matshow(dataGrid1, cmap="YlOrRd") 
mat2 = ax2.matshow(dataGrid2, cmap="YlOrRd") 

#make both plots square 
ax1.set_aspect(float(n1)/float(m1)) 
ax2.set_aspect(float(n2)/float(m2)) 



pyplot.show() 

는 다른 그리드와 몇 가지 예입니다. 37x69-10x13

이 작업을 수행 한 후, 내가 한 모든 작업은 image sampling의 일부 양식이라고 확신합니다. 큰 목록에서이 작업을 수행하려는 경우 꽤 느려질 수 있으므로 작업을 좀 더 효율적으로 만들어야합니다.

+0

고마워요! 그게 내가 찾고있는 것 같아. 아마 네가 말했듯이, 나는 아마도 이것을 C 나 뭔가 받아 들일만한 성능을 얻기 위해 구현해야 할 것이다. – user3468216

+0

이전에 이미지 샘플링 알고리즘도보고있었습니다. 정확히 이것을 수행하는 알고리즘이있을 수 있지만 찾지 못했습니다. 나는이 유형의 리샘플링을위한 이름이 있는지 여전히 관심이있다. – user3468216

관련 문제