PHWinfo banniere

Titres
PORTAIL ANNUAIRE ARTICLES COMPARATEUR HÉBERGEURS DEVIS FORUMS RÉDUCTEUR D'URL
Précédent   PHWinfo > Forums Hébergement > Forum Serveur - Sécurité et techniques > comp.unix.shell > double "triangle" loop for $* ?
S'inscrire FAQ Membres Recherche Messages du jour Marquer les forums comme lus
comp.unix.shell Using and programming the Unix shell.

double "triangle" loop for $* ?

Réponse
 
LinkBack Outils de la discussion
Vieux 01/11/2006, 00h11   #1
Yakov
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut double "triangle" loop for $* ?

I'm curious how to write the double "triangle" loop for $* in posix sh
analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
preferably in posix shell. I'm experienced shell scripter but here,
I'm stumped: for x in $*; do for y in ????; do body; done; done;
(???? must become the slice of $* list from $1 to one before
the element represented by $x)

Is it possible at all ? bash-specific solutions are welcome, too,
but posix sh are preferred.

Yakov

  Réponse avec citation
Vieux 01/11/2006, 01h23   #2
Chris F.A. Johnson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 2006-11-01, Yakov wrote:
> I'm curious how to write the double "triangle" loop for $* in posix sh
> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
> preferably in posix shell.


Straightforward POSIX:

k=0
N=666
while [ "$k" -lt "$N" ]
do
j=0
while [ "$j" -lt $k" ]
do
: whatever
j=$(( $j + 1 ))
done
k=$(( $k + 1 ))
done


> I'm experienced shell scripter but here,
> I'm stumped: for x in $*; do for y in ????; do body; done; done;
> (???? must become the slice of $* list from $1 to one before
> the element represented by $x)


Since you are using $* (instead of "$@", which is probably what you
really want) that is straightforward:

z=
for x in $*
do
z="$z $x"
for y in $z
do
: body
done
done


To use "$@" is more complicated in a POSIX shell, but
straightforward in bash:

unset z
for x in $*
do
z[${#z[@]}]=$x
for y in "${z[@]}"
do
: body
done
done

> Is it possible at all ? bash-specific solutions are welcome, too,
> but posix sh are preferred.


--
Chris F.A. Johnson, author <http://cfaj.freeshell.org/shell>
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
===== My code in this post, if any, assumes the POSIX locale
===== and is released under the GNU General Public Licence
  Réponse avec citation
Vieux 01/11/2006, 05h22   #3
Bill Marcum
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 31 Oct 2006 16:11:39 -0800, Yakov
<iler.ml@gmail.com> wrote:
> I'm curious how to write the double "triangle" loop for $* in posix sh
> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
> preferably in posix shell. I'm experienced shell scripter but here,
> I'm stumped: for x in $*; do for y in ????; do body; done; done;
> (???? must become the slice of $* list from $1 to one before
> the element represented by $x)
>
> Is it possible at all ? bash-specific solutions are welcome, too,
> but posix sh are preferred.
>

Bash version 2 or later, zsh, and I think ksh93 have the syntax
for (( k=0; k<N; k++ ))

Some systems have the "seq" command:
for x in `seq 1 10`


--
Baker's First Law of Federal Geometry:
A block grant is a solid mass of money surrounded on all sides by
governors.
  Réponse avec citation
Vieux 01/11/2006, 07h04   #4
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-10-31, 16:11(-08), Yakov:
> I'm curious how to write the double "triangle" loop for $* in posix sh
> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
> preferably in posix shell. I'm experienced shell scripter but here,
> I'm stumped: for x in $*; do for y in ????; do body; done; done;
> (???? must become the slice of $* list from $1 to one before
> the element represented by $x)
>
> Is it possible at all ? bash-specific solutions are welcome, too,
> but posix sh are preferred.

[...]

for x in $*

is not correct. the "*" variable contains the concatenation of
the positional parameters with spaces. As you left it unquoted
it is split against spaces (the ones used for concatenation and
the one in the positional parameters themselves)tabs and newline
characters, and filename generation is performed (? is expanded
to the list of single character files in the current directory
for instance).

The syntax is

for i do ...; done
or
for i in "$@"; do ...; done

You can do:

k=1
while [ "$k" -le "$#" ]; do
eval "arg_k=\${$k}"
j=1
while [ "$j" -lt "$k" ]; do
eval "arg_j=\${$j}"
# body
j=$(($j + 1))
done
k=$(($k + 1))
done

Or:

k=0
for arg_k do
j=0
for arg_j do
[ "$j" -ge "$k" ] && break
# body
j=$(($j + 1))
done
k=$(($k + 1))
done

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 07h46   #5
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-1, 00:22(-05), Bill Marcum:
> On 31 Oct 2006 16:11:39 -0800, Yakov
> <iler.ml@gmail.com> wrote:
>> I'm curious how to write the double "triangle" loop for $* in posix sh
>> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
>> preferably in posix shell. I'm experienced shell scripter but here,
>> I'm stumped: for x in $*; do for y in ????; do body; done; done;
>> (???? must become the slice of $* list from $1 to one before
>> the element represented by $x)
>>
>> Is it possible at all ? bash-specific solutions are welcome, too,
>> but posix sh are preferred.
>>

> Bash version 2 or later, zsh, and I think ksh93 have the syntax
> for (( k=0; k<N; k++ ))


I think that syntax appeared in 2.04, it's not in 2.03 which I
beleive is still the version shipped with Solaris up to 9.

> Some systems have the "seq" command:
> for x in `seq 1 10`


GNU systems, seq is a GNU only command. And that assumes the
newline character is in IFS and that no digits are in IFS.

x=1
while [ "$x" -le 10 ]; do
...
x=$(($x + 1))
done

is POSIX.

zsh and bash3 (and possibly the latest version of ksh93) have:

for x in {1..10}; do ...; done

zsh has

x=1; repeat 10 { ((x++)); ... }

for x ({1..10}) {...}

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 07h56   #6
Chris F.A. Johnson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 2006-11-01, Stephane CHAZELAS wrote:
> 2006-10-31, 16:11(-08), Yakov:
>> I'm curious how to write the double "triangle" loop for $* in posix sh
>> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
>> preferably in posix shell. I'm experienced shell scripter but here,
>> I'm stumped: for x in $*; do for y in ????; do body; done; done;
>> (???? must become the slice of $* list from $1 to one before
>> the element represented by $x)
>>
>> Is it possible at all ? bash-specific solutions are welcome, too,
>> but posix sh are preferred.

> [...]
>
> for x in $*
>
> is not correct.


It may be correct. The OP may want it ...

> split against spaces (the ones used for concatenation and
> the one in the positional parameters themselves)tabs and newline
> characters, and filename generation is performed (? is expanded
> to the list of single character files in the current directory
> for instance).

....

--
Chris F.A. Johnson, author <http://cfaj.freeshell.org/shell>
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
===== My code in this post, if any, assumes the POSIX locale
===== and is released under the GNU General Public Licence
  Réponse avec citation
Vieux 01/11/2006, 08h11   #7
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-1, 02:56(-05), Chris F.A. Johnson:
> On 2006-11-01, Stephane CHAZELAS wrote:
>> 2006-10-31, 16:11(-08), Yakov:
>>> I'm curious how to write the double "triangle" loop for $* in posix sh
>>> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
>>> preferably in posix shell. I'm experienced shell scripter but here,
>>> I'm stumped: for x in $*; do for y in ????; do body; done; done;
>>> (???? must become the slice of $* list from $1 to one before
>>> the element represented by $x)
>>>
>>> Is it possible at all ? bash-specific solutions are welcome, too,
>>> but posix sh are preferred.

>> [...]
>>
>> for x in $*
>>
>> is not correct.

>
> It may be correct. The OP may want it ...

[...]

It is syntactically correct but does not make any sense. It only
makes sense (with the default value of IFS and setting of -f) if
the positional parameters are to be taken as blank separated
lists of file patterns, as in $1 == "*.txt foo*", $2 = "*.bar",
and even then it's quite dangerous given the way the shells
treat patterns that don't have any match.

With some other values of IFS, the behavior varies from shell to
shell.

With zsh (when not in sh or ksh mode),

for x in $*

loops over the non-empty positional parameters, a bit like in

IFS=; set -f; for x in $*

in some other shells.

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 08h19   #8
Chris F.A. Johnson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 2006-11-01, Stephane CHAZELAS wrote:
> 2006-11-1, 02:56(-05), Chris F.A. Johnson:
>> On 2006-11-01, Stephane CHAZELAS wrote:
>>> 2006-10-31, 16:11(-08), Yakov:
>>>> I'm curious how to write the double "triangle" loop for $* in posix sh
>>>> analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
>>>> preferably in posix shell. I'm experienced shell scripter but here,
>>>> I'm stumped: for x in $*; do for y in ????; do body; done; done;
>>>> (???? must become the slice of $* list from $1 to one before
>>>> the element represented by $x)
>>>>
>>>> Is it possible at all ? bash-specific solutions are welcome, too,
>>>> but posix sh are preferred.
>>> [...]
>>>
>>> for x in $*
>>>
>>> is not correct.

>>
>> It may be correct. The OP may want it ...

> [...]
>
> It is syntactically correct but does not make any sense.


Of course it mase sense. It may not give the desired behaviour in
most cases, but it may well be what is wanted.

> It only makes sense (with the default value of IFS and setting of
> -f) if the positional parameters are to be taken as blank separated
> lists of file patterns, as in $1 == "*.txt foo*", $2 = "*.bar", and
> even then it's quite dangerous given the way the shells treat
> patterns that don't have any match.


The may be what is wanted, with or without set -f.

> With some other values of IFS, the behavior varies from shell to
> shell.
>
> With zsh (when not in sh or ksh mode),
>
> for x in $*
>
> loops over the non-empty positional parameters, a bit like in
>
> IFS=; set -f; for x in $*
>
> in some other shells.
>



--
Chris F.A. Johnson, author <http://cfaj.freeshell.org/shell>
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
===== My code in this post, if any, assumes the POSIX locale
===== and is released under the GNU General Public Licence
  Réponse avec citation
Vieux 01/11/2006, 09h00   #9
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-10-31, 20:23(-05), Chris F.A. Johnson:
[...]
> To use "$@" is more complicated in a POSIX shell, but
> straightforward in bash:
>
> unset z
> for x in $*


ITYM

for x in "$@"

> do
> z[${#z[@]}]=$x
> for y in "${z[@]}"
> do
> : body
> done


In the OP's requirement z[...] should be after the for y loop.

> done

[...]

It may reveal more legible in zsh:

z=()
for x do
for y in "$z[@]"; do
: body
done
z+=$x
done

Also:

awk '
BEGIN {
for (i = 1; i < ARGC; i++) {
for (j = 1; j < i; j++) {
# body ARGV[i] ARGV[j]
}
}
exit
}' "$@"

may reveal more appropriate if the purpose is to do arithmetic
or text manipulation operations over the elements.

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 09h24   #10
Yakov
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

Chris F.A. Johnson wrote:
> On 2006-11-01, Yakov wrote:
> > I'm curious how to write the double "triangle" loop for $* in posix sh
> > analogous to this loop: for(k=0; k<N;k++) for(j=0; j<k; j++) body;
> > preferably in posix shell.
> > I'm experienced shell scripter but here,
> > I'm stumped: for x in $*; do for y in ????; do body; done; done;
> > (???? must become the slice of $* list from $1 to one before
> > the element represented by $x)

>
> Since you are using $* (instead of "$@", which is probably what you
> really want) that is straightforward:
>
> z=
> for x in $*
> do
> z="$z $x"
> for y in $z
> do
> : body
> done
> done


This is nice, thanx, just what I was looking for.


> To use "$@" is more complicated in a POSIX shell, but
> straightforward in bash:
>
> unset z
> for x in $*
> do
> z[${#z[@]}]=$x
> for y in "${z[@]}"
> do
> : body
> done
> done


Nice, too.

Yakov

  Réponse avec citation
Vieux 01/11/2006, 15h27   #11
Janis Papanagnou
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

Stephane CHAZELAS wrote:
> 2006-11-1, 00:22(-05), Bill Marcum:
>
>>Some systems have the "seq" command:
>>for x in `seq 1 10`

>
> GNU systems, seq is a GNU only command. And that assumes the
> newline character is in IFS and that no digits are in IFS.


If one fiddles with IFS he should take care that any changed
IFS has just some well defined preferable local scope, take
some precautions to save/restore it, or define it for a single
command only.

Janis
  Réponse avec citation
Vieux 01/11/2006, 15h58   #12
Casper H.S. Dik
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:

>Stephane CHAZELAS wrote:
>> 2006-11-1, 00:22(-05), Bill Marcum:
>>
>>>Some systems have the "seq" command:
>>>for x in `seq 1 10`

>>
>> GNU systems, seq is a GNU only command. And that assumes the
>> newline character is in IFS and that no digits are in IFS.


>If one fiddles with IFS he should take care that any changed
>IFS has just some well defined preferable local scope, take
>some precautions to save/restore it, or define it for a single
>command only.



And who needs seq (for most purposes) when you have:

`yes "" | cat -n | head -10`


for 10 fill in any number.

Casper
  Réponse avec citation
Vieux 01/11/2006, 16h54   #13
Chris F.A. Johnson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 2006-11-01, Casper H.S Dik wrote:
> Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:
>
>>Stephane CHAZELAS wrote:
>>> 2006-11-1, 00:22(-05), Bill Marcum:
>>>
>>>>Some systems have the "seq" command:
>>>>for x in `seq 1 10`
>>>
>>> GNU systems, seq is a GNU only command. And that assumes the
>>> newline character is in IFS and that no digits are in IFS.

>
>>If one fiddles with IFS he should take care that any changed
>>IFS has just some well defined preferable local scope, take
>>some precautions to save/restore it, or define it for a single
>>command only.

>
>
> And who needs seq (for most purposes) when you have:
>
> `yes "" | cat -n | head -10`
>
>
> for 10 fill in any number.


But who says you have it?

$ yes "" | cat -n | head -10
cat: cannot open -n: No such file or directory

It works with most versions of cat, but it is not part of the
standard.

--
Chris F.A. Johnson, author <http://cfaj.freeshell.org/shell>
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
===== My code in this post, if any, assumes the POSIX locale
===== and is released under the GNU General Public Licence
  Réponse avec citation
Vieux 01/11/2006, 16h58   #14
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-01, 16:27(+01), Janis Papanagnou:
> Stephane CHAZELAS wrote:
>> 2006-11-1, 00:22(-05), Bill Marcum:
>>
>>>Some systems have the "seq" command:
>>>for x in `seq 1 10`

>>
>> GNU systems, seq is a GNU only command. And that assumes the
>> newline character is in IFS and that no digits are in IFS.

>
> If one fiddles with IFS he should take care that any changed
> IFS has just some well defined preferable local scope, take
> some precautions to save/restore it, or define it for a single
> command only.

[...]

That's one approach.

An approach that makes more sense to me (in scripts) is to
define IFS each time you ask the shell to split something for
you. That's what you do in other languages.

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 17h05   #15
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-01, 15:58(+00), Casper H.S Dik:
> Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:
>
>>Stephane CHAZELAS wrote:
>>> 2006-11-1, 00:22(-05), Bill Marcum:
>>>
>>>>Some systems have the "seq" command:
>>>>for x in `seq 1 10`
>>>
>>> GNU systems, seq is a GNU only command. And that assumes the
>>> newline character is in IFS and that no digits are in IFS.

>
>>If one fiddles with IFS he should take care that any changed
>>IFS has just some well defined preferable local scope, take
>>some precautions to save/restore it, or define it for a single
>>command only.

>
>
> And who needs seq (for most purposes) when you have:
>
> `yes "" | cat -n | head -10`
>
>
> for 10 fill in any number.

[...]

Note that neither yes nor cat -n nor head -10 are SUSv3 though
they are supported by most systems

You can do:

NL='
'

yes() {
(
IFS=" "
printf '%s\n' "$*" |
sed -e :1 -e p -e b1
)
}

cat_n() {
nl -ba -d "$NL"
}

and do:

yes "" | cat_n | head -n 10

or:

for x in 1 2 3 4 5 6 7 8 9 10

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 17h41   #16
Loki Harfagr
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

Le Wed, 01 Nov 2006 17:05:15 +0000, Stephane CHAZELAS a écrit:

> 2006-11-01, 15:58(+00), Casper H.S Dik:
>> Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:
>>
>>>Stephane CHAZELAS wrote:
>>>> 2006-11-1, 00:22(-05), Bill Marcum:
>>>>
>>>>>Some systems have the "seq" command:
>>>>>for x in `seq 1 10`
>>>>
>>>> GNU systems, seq is a GNU only command. And that assumes the
>>>> newline character is in IFS and that no digits are in IFS.

>>
>>>If one fiddles with IFS he should take care that any changed
>>>IFS has just some well defined preferable local scope, take
>>>some precautions to save/restore it, or define it for a single
>>>command only.

>>
>>
>> And who needs seq (for most purposes) when you have:
>>
>> `yes "" | cat -n | head -10`
>>
>>
>> for 10 fill in any number.

> [...]
>
> Note that neither yes nor cat -n nor head -10 are SUSv3 though
> they are supported by most systems
>
> You can do:
>
> NL='
> '
>
> yes() {
> (
> IFS=" "
> printf '%s\n' "$*" |
> sed -e :1 -e p -e b1
> )
> }
>
> cat_n() {
> nl -ba -d "$NL"
> }
>
> and do:
>
> yes "" | cat_n | head -n 10
>
> or:
>
> for x in 1 2 3 4 5 6 7 8 9 10


Then, while at replacing 'yes' and 'act -n' to simulate 'seq'
why not directly simulate 'seq' ?
here follows a possible form, I guess Chris F.A. Johnson and/or
youreslf will correct the possible holes in it :-)

$ cat seq_in_shell.sh
#!/bin/bash
###
###
### In the "horrible tools without tools" collection.
###
###
### Admitting you miss the 'seq' utility and you don't
### have access to the source and/or a C compiler.
### Well, also admitting you have some spare time
### and you are kin to the March Hare here's a
### horrible still effective bash way to fill your dreams.
###
###
###
_min=1
_max=$1
(( $# > 1 )) && _max=$2 && _min=$1
_count=$_min
(( _max=${_max} + 1 ))
(( _max - $_min )) || exit
while true
do
printf ${_count}"\n"
(( _count=${_count} + 1 ))
(( ${_max} - ${_count} )) || exit
done
  Réponse avec citation
Vieux 01/11/2006, 18h45   #17
Janis Papanagnou
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

Chris F.A. Johnson wrote:
> On 2006-11-01, Casper H.S Dik wrote:
>>Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:
>>>Stephane CHAZELAS wrote:
>>>>2006-11-1, 00:22(-05), Bill Marcum:
>>>>
>>>>>Some systems have the "seq" command:
>>>>>for x in `seq 1 10`
>>>>
>>>>GNU systems, seq is a GNU only command. And that assumes the
>>>>newline character is in IFS and that no digits are in IFS.

>>
>>>If one fiddles with IFS he should take care that any changed
>>>IFS has just some well defined preferable local scope, take
>>>some precautions to save/restore it, or define it for a single
>>>command only.

>>
>>And who needs seq (for most purposes) when you have:
>>
>> `yes "" | cat -n | head -10`
>>
>>for 10 fill in any number.

>
> But who says you have it?
>
> $ yes "" | cat -n | head -10
> cat: cannot open -n: No such file or directory
>
> It works with most versions of cat, but it is not part of the
> standard.


$ yes "" | head -10 | awk '{print NR}'


Janis
  Réponse avec citation
Vieux 01/11/2006, 18h49   #18
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-01, 18:41(+01), Loki Harfagr:
> Le Wed, 01 Nov 2006 17:05:15 +0000, Stephane CHAZELAS a écrit:
>
>> 2006-11-01, 15:58(+00), Casper H.S Dik:
>>> Janis Papanagnou <Janis_Papanagnou@hotmail.com> writes:
>>>
>>>>Stephane CHAZELAS wrote:
>>>>> 2006-11-1, 00:22(-05), Bill Marcum:
>>>>>
>>>>>>Some systems have the "seq" command:
>>>>>>for x in `seq 1 10`
>>>>>
>>>>> GNU systems, seq is a GNU only command. And that assumes the
>>>>> newline character is in IFS and that no digits are in IFS.
>>>
>>>>If one fiddles with IFS he should take care that any changed
>>>>IFS has just some well defined preferable local scope, take
>>>>some precautions to save/restore it, or define it for a single
>>>>command only.
>>>
>>>
>>> And who needs seq (for most purposes) when you have:
>>>
>>> `yes "" | cat -n | head -10`
>>>
>>>
>>> for 10 fill in any number.

>> [...]
>>
>> Note that neither yes nor cat -n nor head -10 are SUSv3 though
>> they are supported by most systems
>>
>> You can do:
>>
>> NL='
>> '
>>
>> yes() {
>> (
>> IFS=" "
>> printf '%s\n' "$*" |
>> sed -e :1 -e p -e b1
>> )
>> }
>>
>> cat_n() {
>> nl -ba -d "$NL"
>> }
>>
>> and do:
>>
>> yes "" | cat_n | head -n 10
>>
>> or:
>>
>> for x in 1 2 3 4 5 6 7 8 9 10

>
> Then, while at replacing 'yes' and 'act -n' to simulate 'seq'
> why not directly simulate 'seq' ?
> here follows a possible form, I guess Chris F.A. Johnson and/or
> youreslf will correct the possible holes in it :-)

[...]

#! /usr/bin/awk -f
BEGIN {
min=1
step = 1
max = ARGV[1]
if (ARGC > 2) {
min = max
max = ARGV[2]
}
if (ARGC > 3) step = ARGV[3]
if ((max - min) * step < 0) exit(1)
for (i = min; i*step <= max*step; i+=step)
printf "%.17g\n", i
exit(0)
}

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 18h50   #19
Stephane CHAZELAS
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

2006-11-01, 19:45(+01), Janis Papanagnou:
[...]
> $ yes "" | head -10 | awk '{print NR}'


yes "" | sed -n '=;10q'

--
Stéphane
  Réponse avec citation
Vieux 01/11/2006, 20h26   #20
Chris F.A. Johnson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ?

On 2006-11-01, Loki Harfagr wrote:
....
> Then, while at replacing 'yes' and 'act -n' to simulate 'seq'
> why not directly simulate 'seq' ?
> here follows a possible form, I guess Chris F.A. Johnson and/or
> youreslf will correct the possible holes in it :-)
>
> $ cat seq_in_shell.sh
> #!/bin/bash
> ###
> ###
> ### In the "horrible tools without tools" collection.
> ###
> ###
> ### Admitting you miss the 'seq' utility and you don't
> ### have access to the source and/or a C compiler.
> ### Well, also admitting you have some spare time
> ### and you are kin to the March Hare here's a
> ### horrible still effective bash way to fill your dreams.
> ###
> ###
> ###
> _min=1
> _max=$1
> (( $# > 1 )) && _max=$2 && _min=$1


Why use non-standard syntax?

> _count=$_min
> (( _max=${_max} + 1 ))
> (( _max - $_min )) || exit
> while true
> do
> printf ${_count}"\n"
> (( _count=${_count} + 1 ))
> (( ${_max} - ${_count} )) || exit
> done


seq()
{
inc=1
min=1
case $# in
1) max=$1 ;;
2) min=$1; max=$2; ;;
3) min=$1; inc=$2; max=$3 ;;
*) echo "Too few arguments" >&2; return 1 ;;
esac

[ $inc -eq 0 ] && return 1

while :
do
[ $inc -gt 0 ] && [ $min -gt $max ] && break
[ $inc -lt 0 ] && [ $min -lt $max ] && break
printf "%d\n" "$min"
min=$(( $min + $inc ))
done
}

--
Chris F.A. Johnson, author <http://cfaj.freeshell.org/shell>
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
===== My code in this post, if any, assumes the POSIX locale
===== and is released under the GNU General Public Licence
  Réponse avec citation
Vieux 02/11/2006, 08h53   #21
Loki Harfagr
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: double "triangle" loop for $* ? [OT]

Le Wed, 01 Nov 2006 15:26:17 -0500, Chris F.A. Johnson a écrit:

....
>> (( $# > 1 )) && _max=$2 && _min=$1

>
> Why use non-standard syntax?


Well, I reckon it was to entice you to offer your fully standard version
I'm enjoying your book (recipes) but haven't read it all over again ;-)

(note that I was honest and "she-banged" '#!/bin/bash')
  Réponse avec citation
Réponse


Outils de la discussion

Règles de messages
Vous ne pouvez pas créer de nouvelles discussions
Vous ne pouvez pas envoyer des réponses
Vous ne pouvez pas envoyer des pièces jointes
Vous ne pouvez pas modifier vos messages

Les balises BB sont activées : oui
Les smileys sont activés : oui
La balise [IMG] est activée : oui
Le code HTML peut être employé : non
Trackbacks are oui
Pingbacks are oui
Refbacks are oui


Fuseau horaire GMT +1. Il est actuellement 17h57.


Édité par : vBulletin® version 3.7.3
Copyright ©2000 - 2008, Jelsoft Enterprises Ltd.
Search Engine Friendly URLs by vBSEO 3.2.0 RC5 Tous droits réservés.
Version française #16 par l'association vBulletin francophone
PHWinfo est un site Éducation Sans Frontières ©2000-2008
Ad Management by RedTyger
©Tous droits réservés par les parties respectives
Page generated in 0,33636 seconds with 29 queries