How to generate knock-out vectors in Chapel?

87 Views Asked by At

I have a matrix, yes, A. Operating on her rows, I often need to create "knock-out" vectors. Basically

var v = [5, 4, 3, 2, 1];
v_{-2} = [5, 3, 2, 1]; // e.g. v[2] is removed

I don't want to remove it permanently, just for this calculation, and I want to do it along the rows of A.

var knockouts: [A.dim(1)] int;  // list of knockout dims, as tall as A
for i in A.dim(1) {
  var w = ||v_{-knockouts[i]}|| / ||v||
}

== UPDATE ==

More on A to keep it general. It is very large and (as is my wont) sparse. The elements knocked out are expected to be within the populated subdomain, but may not be in some cases. The entries are often probabilities, as in a stochastic matrix, so a few common row operations are

r = A[i,..]
s = r[3] / sum(r_{-3})
s = sum(r[3] log(r_{-3}))
s = sum(log (r_{-3})) / sum (log (r_{-5}))

With all the logging going on, it may not be safe to set r[3] = 0. But if that is the solution, it would still be nice to have a convenience function to do it under the covers. I don't recall seeing one but, maybe sum(r.except(3)) or another syntax.

1

There are 1 best solutions below

0
On BEST ANSWER

I don't know of a good way to do this "in-place" such that no temporary arrays are created.

For now, here's an approach that knocks out indices by creating a temporary array:

var v = [5, 4, 3, 2, 1];
writeln(exclude(v, 2));     // 5 3 2 1
writeln(exclude(v, 3));     // 5 4 2 1


/* Returns array with element at idx excluded */
proc exclude(A: [], idx) {
  var v1 = A[..idx-1];
  v1.push_back(A[idx+1..]); // See NOTE
  return v1;
}

NOTE: Passing arrays to push_back() is not supported in Chapel 1.15. It has been added in #7180.