help-gawk
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: How to Generate a Long String of the Same Character


From: Wolfgang Laun
Subject: Re: How to Generate a Long String of the Same Character
Date: Mon, 19 Jul 2021 08:51:24 +0200

Neil R. Ormos suggests the following code, which I put here as a function:
function srep(n, s){
    while( length(s) < n )
        s = s s;
    return substr( s, 1, n );
}
Neil points out that doubling in the while loop may overshoot the desired
length by almost 100%, potentially causing the algorithm to fail. However,
it is quite simple to avoid this:
function srep(n, s){   # *dbl*
    while( length(s)*2 <= n )
        s = s s;
    return s substr( s, 1, n - length(s) );
}

I have tried to keep track of all the solutions to the simple original
problem, extending the functionality to string repetition (because this
makes it more useful), and done some performance testing.

The original question was whether this:
function srep(n, s,  res){  # *rpt*
     for( i = 1; i <= n; ++i )
         res = res s
     return res;
}
could be improved. This was proposed as an improvement over the *rpt*
version:
function srep(n, s,  res){    # *sub*
     res = sprintf("%*s", n, "");
     gsub( / /, s, res );
     return res;
}
and I contributed:
function srep(n, s,   h){  # *rec*
     if( n == 0 ) return "";
     h = srep( int(n/2), s )
     return n % 2 == 1 ? h h s : h h;
}

I have used this code together with /usr/bin/time:
BEGIN {
    for( j = 1; j <= 300000; ++j ){
        srep( j%1000, "a" );
        srep( j%1000, "abcde" );
    }
}
The results for the four versions:
   *rec*  0m1,436s
   *dbl*  0m2.322s
   *rpt*   0m13.543s
   *sub*  0m27.290s

Note 1: It should be noted that version *sub* has a defect: using "&" or
some combination with "\" is not handled correctly. I have read section
9.1.3.1, *More about ‘\’ and ‘&’ with sub(), gsub(), and gensub(), *of the
GUM and, although it didn't cause me a headache, it made me gawk. I did not
try to cook *sub.*

Note 2: I have provoked the aforementioned failure in *dbl*, resulting in
the somewhat laconic error message:
    $ gawk -f srepDoubl.awk
    Killed
See the bug list for my comment on this message.

Cheers
Wolfgang


reply via email to

[Prev in Thread] Current Thread [Next in Thread]