comparison liboctave/array/Array.cc @ 17642:7ed397c8ca68

improve compatibility of null assignment (bug #31287) * Array.cc (Array<T>::delete_elements (const Array<idx_vector>&)): Improve compatibility when indices references an empty slice. * Sparse.cc (Sparse<T>::delete_elements (const idx_vector&, const idx_vector&)): Likewise. (Sparse<T>::delete_elements (const idx_vector&)): Likewise. * index.tst: New tests.
author John W. Eaton <jwe@octave.org>
date Fri, 11 Oct 2013 23:39:54 -0400
parents 648dabbb4c6b
children d63878346099
comparison
equal deleted inserted replaced
17641:cd5a6008ae72 17642:7ed397c8ca68
1458 1458
1459 template <class T> 1459 template <class T>
1460 void 1460 void
1461 Array<T>::delete_elements (const Array<idx_vector>& ia) 1461 Array<T>::delete_elements (const Array<idx_vector>& ia)
1462 { 1462 {
1463 if (ia.length () == 1) 1463 int ial = ia.length ();
1464
1465 if (ial == 1)
1464 delete_elements (ia(0)); 1466 delete_elements (ia(0));
1465 else 1467 else
1466 { 1468 {
1467 int len = ia.length (), k, dim = -1; 1469 int k, dim = -1;
1468 for (k = 0; k < len; k++) 1470 for (k = 0; k < ial; k++)
1469 { 1471 {
1470 if (! ia(k).is_colon ()) 1472 if (! ia(k).is_colon ())
1471 { 1473 {
1472 if (dim < 0) 1474 if (dim < 0)
1473 dim = k; 1475 dim = k;
1479 { 1481 {
1480 dim_vector dv = dimensions; 1482 dim_vector dv = dimensions;
1481 dv(0) = 0; 1483 dv(0) = 0;
1482 *this = Array<T> (dv); 1484 *this = Array<T> (dv);
1483 } 1485 }
1484 else if (k == len) 1486 else if (k == ial)
1485 { 1487 {
1486 delete_elements (dim, ia(dim)); 1488 delete_elements (dim, ia(dim));
1487 } 1489 }
1488 else 1490 else
1489 { 1491 {
1490 (*current_liboctave_error_handler) 1492 // Allow the null assignment to succeed if it won't change
1491 ("a null assignment can only have one non-colon index"); 1493 // anything because the indices reference an empty slice,
1494 // provided that there is at most one non-colon (or
1495 // equivalent) index. So, we still have the requirement of
1496 // deleting a slice, but it is OK if the slice is empty.
1497
1498 // For compatibility with Matlab, stop checking once we see
1499 // more than one non-colon index or an empty index. Matlab
1500 // considers "[]" to be an empty index but not "false". We
1501 // accept both.
1502
1503 bool empty_assignment = false;
1504
1505 int num_non_colon_indices = 0;
1506
1507 int nd = ndims ();
1508
1509 for (int i = 0; i < ial; i++)
1510 {
1511 octave_idx_type dim_len = i >= nd ? 1 : dimensions(i);
1512
1513 if (ia(i).length (dim_len) == 0)
1514 {
1515 empty_assignment = true;
1516 break;
1517 }
1518
1519 if (! ia(i).is_colon_equiv (dim_len))
1520 {
1521 num_non_colon_indices++;
1522
1523 if (num_non_colon_indices == 2)
1524 break;
1525 }
1526 }
1527
1528 if (! empty_assignment)
1529 (*current_liboctave_error_handler)
1530 ("a null assignment can only have one non-colon index");
1492 } 1531 }
1493 } 1532 }
1494 1533
1495 } 1534 }
1496 1535