Re: alternation option end of string

Ray Andrews <[email protected]>
Newsgroups gmane.comp.shells.zsh.devel,gmane.comp.shells.zsh.user
Message-ID <[email protected]>
On 2026-05-03 17:01, Mark J. Reed wrote:
> What you really want is to _remove_ whatever comes after either "cats" 
> or, if the thing after "cat" is not an s, "cat".
>
> But if you're reading comma-separated fields, you can just use `read`:
>
>     IFS=, read base idx comment <<<"$INPUT"
>
>
>    INPUT: file,8a
>     base: file
>      idx: 8a        FAIL
>  comment:
>
>    INPUT: file,a8
>     base: file
>      idx: a8        FAIL
>  comment:
>
>    INPUT: file,a8,comment
>     base: file
>      idx: a8                FAIL
>  comment: comment
>
>    INPUT: file,8a,comment
>     base: file
>      idx: 8a                FAIL
>  comment: comment
>
>    INPUT: file,8a,com,ment
>     base: file
>      idx: 8a                FAIL
>  comment: com,ment

... between commas must be only a number. But I still like the idea, 
because the primary breakdown is indeed by commas (but a comma can occur 
in a comment, which muddies the water somewhat).  Still, I think that 
Roman's method does the job perfectly as it is.  Only a bit more work to 
be sure of the comment.  Here's the whole thing, I wonder if the logic 
can be tightened up even further:

# Tests of s() filename parsing:

function s_split ()
{
     [[ ! "$@" ]] && return # Otherwise it tries to 'run empty' twice.

     # Global so can access at CL:
     s_base=
     s_idx=
     s_comment=
     local remainder=
     local flag_verbose=

[[ "$1" == ',v' ]] && { flag_verbose=1; shift }

     # Strip off the longest match of 'a comma followed by anything' 
from the rear, leaving the basename:
     s_base="${@%%,*}"
     # Mirror image of the above: save whatever was stripped off, this 
will be any combination of idx and comment:
     remainder="${(M)@%%,*}"

     # Roman's power code with back references:
     [[ $remainder == (#b)(,(<->)|,(<->),*) ]] && s_idx=$match[2]$match[3]

     # We found an idx.  Comment will be anything following:
     # If no idx then entire remainder is a commment (strip the comma).
     [[ $s_idx ]] && s_comment="${(S)remainder##,<->,}"\
                  || s_comment="${remainder#,}"

     # Exception! Test: >file,8< : comment leaks thru so kill it:
     [[ ",$s_idx" == "$s_comment" ]] && s_comment=

[[ "$flag_verbose" ]] &&
{
     grnline "\nINPUT: $@"
     echo "base:       $s_base"
     echo "idx:        $s_idx"
     echo "comment:    $s_comment"
}
} # END: s_split()
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.