1

This question is for the Halide language.

Say for a particular (x, y), I want to operate on a KxK patch around (x, y). E.g. sum them, square them, etc., to get the obtain the new value for (x, y).

Most of the Halide examples I've found "hard-code" selecting the neighboring coordinates. Like in this example, and also the blur algorithm example on the home page:

Func blur_x, blur_y; Var x, y;

// hard codes selecting x-1:x+1 and y-1:y+1
blur_x(x, y) = (input(x-1, y) + input(x, y) + input(x+1, y))/3;
blur_y(x, y) = (blur_x(x, y-1) + blur_x(x, y) + blur_x(x, y+1))/3;

But let's say I want to paramertize the size of my KxK patch. How would I select and then operate on a neighborhood of arbitrary size around (x, y)?

  • I think I found the answer. The answer is to use RDoms e.g. for a 3x3 patch `RDom r(-1, 1, -1, 1); Func sum_patch; Var x, y; sum_patch(x, y) = sum(input(x + r.x, y + r.y);` – Andrew Jong Jan 15 '20 at 22:16
  • But now my question is, what if I don't want to reduce the patch into a single value yet, but instead keep them stored as a group to operate on individually later? E.g. I want to square them individually. – Andrew Jong Jan 15 '20 at 22:20
  • Or another example: how would I calculate the element-wise (Hadamard) product between two patches? – Andrew Jong Jan 15 '20 at 23:00

2 Answers2

0

Maybe this is an answer.

// First add the boundary condition.
Func clamped = BoundaryConditions::repeat_edge(input);

// Define a 5x5 box that starts at (-2, -2)
RDom r(-2, 5, -2, 5);

// Compute the 5x5 sum around each pixel.
Func local_sum;
local_sum(x, y) = 0;  // Compute the sum as a 32-bit integer
local_sum(x, y) += clamped(x + r.x, y + r.y);
  • I'm still confused about this though; when I test this, I don't get a group of pixels I can operate on. It reduces to a single value. I guess that's why it's called a "Reduction Domain", but that doesn't do what I want. – Andrew Jong Jan 16 '20 at 00:54
0

Regarding your questions in the comments, I think what you need is a Func with 4 Vars: output(x, y, xi, yi)

x, y is the coordinate of the pixel in the center of each patch, which is effectively the ordinary coordinate of the pixel in an image. And xi, yi is the inner coordinate of the pixels within each patch.

output(x, y, xi, yi) = input(x + xi, y + yi)

In this way, you get a group of pixels that you can operate on.

Jiang
  • 149
  • 6