Re: Proposal for a (small) enhancement to the value() function.
- Posted by CChris <christian.cuvier at agriculture.gouv.fr> Jun 27, 2007
- 719 views
Pete Lomax wrote: > > > I've really only been skimming this thread, but a suggestion which just might > possibly make everyone happy is instead of: > }}} <eucode> > return {s,v,c,l} > </eucode> {{{ > where c, l are local vars to count chars read, leading spaces, do this: > }}} <eucode> > return {s,v} > ... > global function Get_extra_info() > -- retrieve extra info about the immediately preceding get()/value() call > -- (if unsuccessful, it should indicate the exact point of error) > return {c,l} --{chars read, leading spaces} > end function > </eucode> {{{ > Instead of c, I would re-use string_next (NB with changes below, now 0..len, > was 1..len+1), and use leading_chars instead of l. In both value() and get(), > initialise string_next to 0 and leading_chars to -1, and: > }}} <eucode> > procedure get_ch() > if sequence(input_string) then > if string_next < length(input_string) then -- (was <=) > string_next += 1 -- (was after next) > ch = input_string[string_next] > else > ch = GET_EOF > end if > else > string_next += 1 -- (new) > ch = getc(input_file) > end if > end procedure > > procedure skip_blanks() > -- skip white space > -- ch is "live" at entry and exit > > while find(ch, " \t\n\r") do > get_ch() > end while > if leading_chars=-1 then -- (new) > leading_chars=string_next-1 -- (new) > end if -- (new) > end procedure > </eucode> {{{ > At least I think that would do everything asked for. I don't think you need > to modify/duplicate Get() at all. The above is just a suggestion, completely > untested of course. > The problem with this approach is that Get() calls both itself and skip_blanks(). skip_blanks() should record stuff only on its very first invocation. Total character count can be read right before the outermost instance of Get() returns, so it is not affected. Use "{ 2}" as a test case: leading spaces should be 0, not 3. To avoid the penalty of endlessly testing whether the current instance of Get() is the outermost one, which is often false in the case of strings representing sequences, I defined a modified Get2(), which value() calls and then calls the regular Get() for any inner subobjects. If you prefer doing that in skip_blanks() instead, no problem. leading_whitespace will become local instead of private to Get2(). As for defining an extra get_read_characters(), which would return the extra info, well I'd go with it, the job will get done. Could you explain, however, why this alternative scheme is preferable? It makes one extra public function to document, instead of extra returned values. Otherwise, it is completely equivalent. Oh right, you must be careful to call get_read_characters(), if you wish, before calling value() or get() again - I assume this is a minor issue. And not to accidentally call get_read_characters() before value(). My proposal avoided all these small issues. > Someone needs to conjure up a decent test script for the changes though, one > that ensures no existing functionality is damaged in any way whatsoever, bar > an inevitable, tiny and utterly insignificant performance hit. Rob, don't you have a test suite available for Euphoria? It would be a good addition to the SVN repository. This solution would ensure a uniform level of quality control. Tests could be freely added, but none modified or removed from such a suite. > > Now, does anyone have any objections to that? > > Regards, > Pete > PS I have no quibble with adding Derek's routine at the same time. CChris