Re: Goto (Was Re: Open Source)

new topic     » goto parent     » topic index » view thread      » older message » newer message

Juergen Luethje wrote:
> > If I didn't make a mistake, this translates to the following Eu program:
<snip>
> I actually would prefer to write the code this way:
<snip>
> Now this is short and pretty clear. Without using GOTO, the structure of
> the program (2 nested loops) is directly visible. So the "nature" of the
> program can be understood immediately and intuitively.
No arguments here, but you did need two attempts even on such a trivial piece of
code smile

> Sorry, I do not know anything about COBOL.
Try this then:
-- optimised best-fit algorithm
include sort.e

integer required
	required = 2482
-- expected results with first sizes set:
--Exact 2482:  12 505, 10 425, 7 396, 6 391, 5 388, 1 377
-- expected results with second sizes set:
--Lower 2324: 6 798, 5 734, 3 410, 2 382
--Higher 2520: 5 734, 4 650, 3 410, 2 382, 1 344
	required = 1659
-- expected results with first sizes set:
--Exact 1659: 11 488, 7 396, 6 391, 3 384
-- expected results with second sizes set:
--Lower 1590: 6 798, 3 410, 2 382
--Higher 1728: 5 734, 4 650, 1 344

sequence sizes
--	 sizes = {377,378,384,387,388,391,396,422,424,425,488,505}
	 sizes = {798,344,650,410,382,734}

sequence incset

integer lowbest, lowlevel, highbest, highlevel, worktot, level, item
sequence lowset, highset

procedure display(integer tot, integer level, sequence incset)
integer item
    printf(1,"%d ",tot)
    for i = 1 to level do
	item = incset[i]
	printf(1,"%d %d ",{item,sizes[item]})
    end for
    puts(1,"       key <cr>")
    if getc(0) then end if
    puts(1,"\n")
end procedure
 
function find_combination(integer jumpToDa200)
--
-- this section tries to find a set of sizes which add up to the
-- required amount exactly.
--
    if jumpToDa200 then goto da200 end if
    level = 1
    lowbest = 0
    highbest = 999999999
    item = length(sizes)
    incset=repeat(0,item)
    worktot=0
da100::
    incset[level] = item
    worktot += sizes[item]
    if worktot = required then return 0 end if	      -- found exact fit
    if worktot > required then goto da200 end if	    -- too big
--
-- this set is smaller than required - save it if it is best so far
--
    if worktot > lowbest then
	lowbest = worktot
	lowlevel = level
	lowset = incset
    end if
    if item > 1 then	    -- more to be tested
	item -= 1
	level += 1	    -- leave item in table;
	goto da100
    end if
    goto da300
da200::
--
-- this set is larger than required - save it if it is best so far
--
    if worktot < highbest then
	highbest = worktot
	highlevel = level
	highset = incset
    end if
da300::
--
-- now we need to backtrack;  remove item from running total and look
-- at the next instead.
--
    worktot -= sizes[item]
    if item > 1 then	-- more to be tested
	item -= 1	-- look at next (overwrite item in table)
	goto da100
    end if
--
-- we have exhausted all possibilities at this level; backtrack to
-- a previous level.
--
    incset[level] = 0
    level -= 1
    if level = 0 then return 1 end if		-- all done
    item = incset[level]
    goto da300
 
end function

procedure main()
    sizes=sort(sizes)
    if not find_combination(0) then
	while 1 do
	    display(worktot,level,incset)
--	    if da200() then exit end if
	    if find_combination(1) then exit end if
	end while
    end if
    puts(1,"lower figure ")
    display(lowbest,lowlevel,lowset)
    puts(1,"higher figure ")
    display(highbest,highlevel,highset)
end procedure
main()


I wasn't really keeping track but I think it just took me a shade under an hour
to hack that into something working, then again I know how it works and I've
managed that trick once before, and that I tried and failed many moons ago when I
was still an Eu novice. While messing about I trigered two fatal crashes in Edita
(in re-indent and CtrlBracket) which I fixed (as part of that hour), so at least
it was not a complete and utter waste of time smile

One thing I would like to say is that the original of that code was used as part
of the compilation process in a team of ten programmers for many years, so any
restructuring or rewrite would, I felt, carry a strong chance of (re-)introducing
bugs that had been ironed out long ago. OTOH if you translate some code from
language A to language B then a) that is a big enough upheaval anyway, and b) if
you don't test it thoroughly then you know what to expect.

The point that this is the only real nasty I have encountered in 5+ years with
Eu is not a small point either.

Regards,
Pete

new topic     » goto parent     » topic index » view thread      » older message » newer message

Search



Quick Links

User menu

Not signed in.

Misc Menu