From: Niklas Holsti <niklas.holsti@tidorum.invalid>
Subject: Re: Deleting elements from a Vector
Date: Mon, 20 Apr 2015 00:12:28 +0300
Date: 2015-04-20T00:12:28+03:00 [thread overview]
Message-ID: <cpik1tF25ipU1@mid.individual.net> (raw)
In-Reply-To: <lywq173ltl.fsf@pushface.org>
On 15-04-19 23:27 , Simon Wright wrote:
> I need to remove some of the elements from a vector, depending on the
> element. I have the code below, which works for GNAT, but which seems
> distinctly dodgy; in particular, it fails if the last Element is
> negative and therefore gets deleted.
Out of curiosity, how does it fail? Exception?
> The Booch Components have
>
> procedure Delete_Item_At (It : in out Iterator) is abstract;
>
> (an Iterator is very similar to a Cursor) which is defined to leave the
> Iterator designating the 'next' Element (i.e., the one, is any, you
> would have reached by applying Next to the original Iterator). But I
> don't see any such promise for the Containers.
I could not find such promises. There is a promise that the cursor used
to delete the element becomes No_Element, as the comment in your code
(quoted below) says.
It seems that what you are doing is at least unspecified and may be
erroneous:
- RM A.18.2(251/3) says that any other cursor that designates (or
designated) the deleted element becomes invalid through the deletion.
- RM A.18.2(2522/2) says that any use of an invalid cursor in "=" or
Has_Element has unspecified result, and using the cursor with any other
subprogram from Containers.Vectors is erroneous execution.
So, after the V.Delete (D) in the code below, the cursor C is invalid,
and on the next loop iteration the condition C /= Vectors.No_Element has
unspecified result, and the possibly executed Vectors.Element (C) is
erroneous execution. So don't do that :-)
> Is there a proper idiom for doing this job? Should I maybe go over the
> Vector in reverse order and use the version of Delete that uses the
> index?
Indeed that seems safer. Note also RM A.18.2(240/2..243/2) for the
definition and properties of an "ambiguous" cursor. This also suggests
traversing the vector in reverse index order.
> with Ada.Containers.Vectors;
> with Ada.Text_IO; use Ada.Text_IO;
> procedure Deleting_From_Queue is
> package Vectors is new Ada.Containers.Vectors (Positive, Integer);
> V : Vectors.Vector;
> begin
> V.Append (1);
> V.Append (-1);
> V.Append (2);
> V.Append (-2);
> V.Append (3);
> declare
> C : Vectors.Cursor := V.First;
> D : Vectors.Cursor;
> use type Vectors.Cursor;
> begin
> while C /= Vectors.No_Element loop
> if Vectors.Element (C) < 0 then
> Put_Line ("deleting element " & Vectors.Element (C)'Img);
> D := C;
> V.Delete (D); -- D -> No_Element
> else
> Put_Line ("skipping element " & Vectors.Element (C)'Img);
> Vectors.Next (C);
> end if;
> end loop;
> end;
> Put_Line ("length now " & V.Length'Img);
> end Deleting_From_Queue;
>
--
Niklas Holsti
Tidorum Ltd
niklas holsti tidorum fi
. @ .
next prev parent reply other threads:[~2015-04-19 21:12 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-04-19 20:27 Deleting elements from a Vector Simon Wright
2015-04-19 21:07 ` Jeffrey Carter
2015-04-19 21:12 ` Niklas Holsti [this message]
2015-04-20 7:56 ` Simon Wright
2015-04-20 8:39 ` Georg Bauhaus
2015-04-20 11:13 ` Simon Wright
2015-04-20 7:36 ` Dmitry A. Kazakov
replies disabled
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox