Как учитывать соседние ячейки в 2D-массиве в Python

вы можете использовать запрос из фляжки

class UploadImage(Resource):
    def post(self, fname):
        file = request.files['file']
        if file and allowed_file(file.filename):
            # From flask uploading tutorial
            filename = secure_filename(file.filename)
            file.save(os.path.join(app.config['UPLOAD_FOLDER'], filename))
            return redirect(url_for('uploaded_file', filename=filename))
        else:
            # return error
            return {'False'}

http://flask.pocoo.org/docs/0.12/patterns/fileuploads/

0
задан handavidbang 13 July 2018 в 18:01
поделиться

1 ответ

Проблема с вашим кодом заключается в том, что вы изменяете grid по мере продвижения. Таким образом, для каждой ячейки вы используете входные значения для соседних с нисходящими / правыми соседями, но выходные значения для соседних со старшим / левым.

Итак, для данного примера, когда вы вычисляете соседи grid[1][0], вы уже заменили двух соседей, grid[0][0] и grid[0][1], поэтому они теперь 4, 4 вместо 2, 3. Это означает, что вы усредняете 4, 4, 5, 6, 8, 9 вместо 2, 3, 5, 6, 8, 9. Итак, вместо того, чтобы получить 5.5, что вы округлите до 5, вы получите 6.0, который округляется до 6.


Самое простое решение - просто создать новую выходную сетку по мере того, как вы идете а затем верните это:

    rows, cols = len(grid), len(grid[0])
    outgrid = []
    #Go through each cell 
    for r in range(rows):
        outrow = []
        for c in range(cols):
            # … same code as before, but instead of the grid[r][c] =
            outrow.append(int(total/n))
        outgrid.append(outrow)
    return outgrid

Если вам нужно изменить сетку на месте, вы можете вместо этого скопировать исходную сетку и выполнить итерацию по этой копии:

    rows, cols = len(grid), len(grid[0])
    ingrid = [list(row) for row in grid]
    #Go through each cell 
    for r in range(rows):
        for c in range(cols):
            # … same code as before, but instead of total += grid[r+ri][c+ci]
            total += ingrid[r+ri][c+ci]

Если вы использовали массив 2D NumPy вместо списка списков, вы могли бы решить это на более высоком уровне.

NumPy позволяет добавлять все массивы все сразу разделите их на скаляры и т. д., чтобы вы могли избавиться от этих циклов над r и c и просто выполнять всю работу в массиве. Но вы все равно должны думать о своих границах. Вы не можете просто добавить arr и arr[:-1] и arr[1:] и т. Д., Вам нужно выставить их на один размер. И если вы просто набрали 0 с, вы закончите усреднение 0, 4, 4, 0, 5, 6, 0, 8, 9, что не хорошо. Но если вы набиваете их значениями NaN, вы усредняете NaN, 4, 4, NaN, 5, 6, NaN, 8, 9, тогда вы можете использовать функцию nanmean , которая игнорирует значения NaN и усредняет 6 действительных значений .

Итак, это все еще несколько строк кода для итерации по 9 направлениям, поместите 9 массивов и nanmean результаты. (Или вы могли бы втиснуть его в гигантское выражение с помощью product, как и ответ на ярлык, но это не совсем читаемо или легче понять.)

Но если вы можете перетащить SciPy , набор алгоритмов почти для всего, что вы хотели бы построить поверх NumPy, имеет функцию в своей библиотеке ndimage под названием generic_filter , которые могут делать все возможные вариации «собрать N соседей, заполнить, как X, и запустить функцию Y на результирующих массивах».

В нашем случае мы хотим собрать 3- соседей по оси, площадку с постоянным значением NaN и запустить функцию nanmean, поэтому этот однострочный файл сделает все, что вам нужно :

scipy.ndimage.generic_filter(grid, function=np.nanmean, size=3, mode='constant', cval=np.NaN)
2
ответ дан abarnert 17 August 2018 в 12:18
поделиться
Другие вопросы по тегам:

Похожие вопросы: