- remove '>' in "(customers.item>) "

- corrected link to LINEAR_ITERATOR
- replace code for 'An example iterator routine'
- added link to 'target' to point to the correct place in LINEAR_ITERATOR chart
- Modified "An example use of iteration" to conform to current implementation using agents.
-- TODO --
 Continue work from
 =Using the Iteration Library=
Updated wikipage EiffelBase, Iteration.
	(Signed-off-by:WilliamsLima).

git-svn-id: https://svn.eiffel.com/eiffel-org/trunk@2074 abb3cda0-5349-4a8f-a601-0c33ac3a8c38
This commit is contained in:
eiffel-org
2018-09-12 13:40:39 +00:00
parent 5c31df2449
commit 2a3b1e09c1

View File

@@ -1,3 +1,5 @@
[[Property:modification_date|Wed, 12 Sep 2018 13:40:39 GMT]]
[[Property:publication_date|Wed, 12 Sep 2018 13:40:39 GMT]]
[[Property:title|EiffelBase, Iteration]]
[[Property:weight|6]]
[[Property:uuid|9c0313bf-571d-0c8d-5c49-8bd99f86bed5]]
@@ -38,8 +40,8 @@ then a class <eiffel>SPECIAL_PROMOTION</eiffel> of a text processing system may
until
customers.exhausted
loop
if recent_purchases.has (customers.item>) then
target_list.put (customers.item>)
if recent_purchases.has (customers.item) then
target_list.put (customers.item)
end
customers.forth
end</code>
@@ -55,49 +57,54 @@ To get a first grasp of how one can work with the Iteration library, let us look
==An example iterator routine==
Here, given with its full implementation, is a typical Iteration library routine: the procedure until_do from [[ref:libraries/base/reference/linear_iterator_chart]] , the class defining iteration mechanisms on linear (sequential) structures.
Here, given with its full implementation, is a typical Iteration library routine: the procedure until_do from [[ref:libraries/base/reference/linear_iterator_chart|LINEAR_ITERATOR]] , the class defining iteration mechanisms on linear (sequential) structures.
<code>
until_do
-- Apply action to every item of target,
-- up to but excluding first one satisfying test.
-- (Apply to full list if no item satisfies test.)
require
traversable_exists: target /= Void
do
from
target.start
invariant
''invariant_value''
until
target.exhausted or else test
loop
action
target.forth
end
ensure
achieved: target.exhausted or else test
invariant_satisfied: ''invariant_value''
end</code>
until_do (action: PROCEDURE [G]; test: FUNCTION [G, BOOLEAN])
-- Apply `action' to every item of `target' up to
-- but excluding first one satisfying `test'.
-- (Apply to full list if no item satisfies `test'.)
do
start
until_continue (action, test)
ensure then
achieved: not exhausted implies test.item ([target.item])
end
The precise form of the procedure in the class relies on a call to another procedure, until_continue, and on inherited assertions. Here everything has been unfolded for illustration purposes. <br/>
This procedure will traverse the linear structure identified by target and apply the procedure calledaction on every item up to but excluding the first one satisfying test. <br/>
until_continue (action: PROCEDURE [G]; test: FUNCTION [G, BOOLEAN])
-- Apply `action' to every item of `target' from current
-- position, up to but excluding first one satisfying `test'.
require
invariant_satisfied: invariant_value
do
from
invariant
invariant_value
until
exhausted or else test.item ([target.item])
loop
action.call ([item])
forth
end
ensure
achieved: exhausted or else test.item ([target.item])
invariant_satisfied: invariant_value
end
</code>
The precise form of the procedure in the class relies on a call to another procedure, until_continue, and on inherited assertions. Here the routines are shown as they are found in the current implementation of the class [[ref:libraries/base/reference/linear_iterator_chart|LINEAR_ITERATOR]]. <br/>
This procedure will traverse the linear structure identified by [[ref:libraries/base/linear_iterator_flatshort.html#f_target|target]] and apply the procedure called action on every item up to but excluding the first one satisfying test. <br/>
The class similarly offers <eiffel>do_all</eiffel>, <eiffel>do_while</eiffel>, <eiffel>do_for</eiffel>, <eiffel>do_if</eiffel> and other procedures representing the common control structures. It also includes functions such as <eiffel>exists</eiffel> and <eiffel>forall</eiffel>, corresponding to the usual quantifiers. <br/>
These iteration schemes depend on the procedure <eiffel>action</eiffel>, defining the action to be applied to successive elements, and on the function <eiffel>test</eiffel>, defining the boolean query to be applied to these elements. These features are declared in class [[ref:libraries/base/reference/iterator_chart|ITERATOR]] (the highest-level deferred class of the Iteration library); here is <eiffel>test</eiffel>:
<code>
test: BOOLEAN
-- Test to be applied to item at current position in
-- target (default: value of item_test on item)
require
traversable_exists: target /= Void
not_off: not target.off
These iteration schemes depend on the procedure <eiffel>action</eiffel>, defining the action to be applied to successive elements, and on the function <eiffel>test</eiffel>, defining the boolean query to be applied to these elements. Both routines are used trough the Eiffel's agent mechanism; here is an example of a <eiffel>test</eiffel>
function intended to be used with iteration over a data structure whose elements are <code>STRING</code>s.
<code>
test (a_item: STRING): BOOLEAN
-- Test to be applied to a_item
do
Result := item_test (target.item>)
ensure
not_off: not target.off
end</code>
Result := a_item.count > 0
end
</code>
This indicates that the value of the boolean function <eiffel>test</eiffel> will be obtained by applying <eiffel>item_test</eiffel> to the item at the current position in the target structure. In [[ref:libraries/base/reference/iterator_chart|ITERATOR]] , function <eiffel>item_test</eiffel> always return ; descendant classes will redefine it so as to describe the desired test. Similarly, <eiffel>action</eiffel> is declared in class [[ref:libraries/base/reference/iterator_chart|ITERATOR]] as a call to <eiffel>item_action</eiffel>. Descendants will redefine <eiffel>item_action</eiffel>, which as initially declared in [[ref:libraries/base/reference/iterator_chart|ITERATOR]] is a procedure with a null body. <br/>
Going through <eiffel>item_action</eiffel> and <eiffel>item_test</eiffel> provides an extra degree of flexibility. Normally the action and test performed at each step apply to <eiffel>target</eiffel> <code> . </code><eiffel>item></eiffel>, so that it suffices to redefine the <eiffel>item_features</eiffel>. This is the case with all examples studied in this chapter. In a more general setting, however, you might need to redefine <eiffel>action</eiffel> and <eiffel>test</eiffel> themselves.
This indicates that the value of the boolean function <eiffel>test</eiffel> will be obtained by verifying that <eiffel>a_item</eiffel> is an empty string or not.
==An example use of iteration==
@@ -119,10 +126,7 @@ class
TEXT_PROCESSOR
inherit
LINEAR_ITERATOR [PARAGRAPH]
redefine
item_action, item_test
end
LINEAR_ITERATOR [PARAGRAPH]
feature
@@ -131,12 +135,12 @@ feature
-- the first one that has been modified.
do
set (t)
until_do
until_do (agent item_action, agent item_test)
end
feature {NONE}
item_test (p PARAGRAPH): BOOLEAN
item_test (p: PARAGRAPH): BOOLEAN
-- Has p been modified?
do
Result := p.modified
@@ -154,9 +158,9 @@ Thanks to the iteration mechanism, the procedure <eiffel>resize_paragraphs</eiff
* To set its argument <code>t</code> as the iteration target, it uses procedure <eiffel>set</eiffel>. (This procedure is from class [[ref:libraries/base/reference/iterator_chart|ITERATOR]] which passes it on to all iterator classes.)
* Then it simply calls <eiffel>until_do</eiffel> as defined above.
Procedure <eiffel>item_action</eiffel> is redefined to describe the operation to be performed on each successive element. Function <eiffel>item_test</eiffel> is redefined to describe the exit test. <br/>
Procedure <eiffel>item_action</eiffel> is defined to describe the operation to be performed on each successive element. Function <eiffel>item_test</eiffel> is defined to describe the exit test. <br/>
As presented so far, the mechanism seems to limit every descendant of an iteration class to just one form of iteration. As shown later in this chapter, it is in fact easy to generalize the technique to allow a class to use an arbitrary number of iteration schemes. <br/>
What is interesting here is that the redefinitions of <eiffel>item_test</eiffel> and <eiffel>item_action</eiffel> take care of all the details. There is no need to write any loop or other control structure. We are at the very heart of the object-oriented method, enjoying the ability to encapsulate useful and common software schemes so that client developers will only need to fill in what is specific to their application.
What is interesting here is that the definitions of <eiffel>item_test</eiffel> and <eiffel>item_action</eiffel> take care of all the details. There is no need to write any loop or other control structure. We are at the very heart of the object-oriented method, enjoying the ability to encapsulate useful and common software schemes so that client developers will only need to fill in what is specific to their application.
=Using the Iteration Library=