changeset 32382:48599bdcc9ca stable

intersect.m: Correct third output with "stable" flag (bug #60347). * scripts/set/intersect.m: Return indices in third output in correct order when using "stable" flag.
author Johannes Pfeifer
date Thu, 05 Oct 2023 20:41:02 +0200
parents 903c9100178b
children a476cdefdafc 9afc383bb60a
files scripts/set/intersect.m
diffstat 1 files changed, 16 insertions(+), 4 deletions(-) [+]
line wrap: on
line diff
--- a/scripts/set/intersect.m	Tue Oct 03 10:48:06 2023 +0200
+++ b/scripts/set/intersect.m	Thu Oct 05 20:41:02 2023 +0200
@@ -111,7 +111,8 @@
     else
       c = [a; b];
       ## FIXME: Is there a way to avoid a call to sort?
-      c = c(sort (ic(match)), :);
+      [c_ind, sort_ind] = sort (ic(match));
+      c = c(c_ind, :);
     endif
     len_a = rows (a);
   else
@@ -132,7 +133,8 @@
     else
       c = [a(:); b(:)];
       ## FIXME: Is there a way to avoid a call to sort?
-      c = c(sort (ic(match)));
+      [c_ind, sort_ind] = sort (ic(match));
+      c = c(c_ind);
     endif
 
     ## Adjust output orientation for Matlab compatibility
@@ -147,8 +149,9 @@
     if (! optsorted)
       ## FIXME: Is there a way to avoid a call to sort?
       ia = sort (ia);
-      [~, idx] = min (ib);
-      ib = [ib(idx:end); ib(1:idx-1)];
+      ib_ind(sort_ind) = 1:numel(sort_ind);
+      ## Change ordering to conform to unsorted c
+      ib(ib_ind) = ib;
     endif
     if (optlegacy && isrowvec && ! by_rows)
       ia = ia.';
@@ -212,6 +215,15 @@
 %! c = intersect (a, b, "stable");
 %! assert (c, [2,1]);
 
+## Test "stable" argument
+%!test <*60347>
+%! a = [8 4 2 6]';
+%! b = [1 7 2 8]';
+%! [c, ia, ib] = intersect (a, b, "stable");
+%! assert (c, [8;2]);
+%! assert (ia, [1;3]);
+%! assert (ib, [4;3]);
+
 %!test
 %! a = [3 2 4 5 7 6 5 1 0 13 13];
 %! b = [3 5 12 1 1 7];