iaw4 has asked for the wisdom of the Perl Monks concerning the following question:

has someone already written a bracketed paren formatter for function calls? I am thinking increasing spaces for outer-more calls. non-function call spacing should be ignored. think
ab + (fun1(fun2( 3 +. fun3( 4+(5+6) )))
would become something linke
`ab + (fun1(..fun2(.3 . + . fun3(4+(5+6)).)..)
where I have replaced spaces with dots for clarity.

Replies are listed 'Best First'.
Re: paren formatter for function calls?
by virtualsue (Vicar) on Apr 24, 2018 at 10:59 UTC
Re: paren formatter for function calls? (updated)
by AnomalousMonk (Archbishop) on Apr 24, 2018 at 15:27 UTC

    If you just gotta do this with a regex, try something like (needs Perl version 5.10+):

    c:\@Work\Perl\monks>perl -wMstrict -le "use 5.010; ;; my $s = 'ab + (fun1( fun2( 3 +fun3 ( 4+(5+6) ))) ) + x + f ( 1 + 2 )' +; print qq{'$s'}; ;; $s =~ s{ ( \( (?: [^()]++ | (?1) )* \) ) } { (my $ns = $1) =~ tr/ \t\n\f//d; $ns; }xmsge; print qq{'$s'}; " 'ab + (fun1( fun2( 3 +fun3 ( 4+(5+6) ))) ) + x + f ( 1 + 2 )' 'ab + (fun1(fun2(3+fun3(4+(5+6))))) + x + f (1+2)'
    This uses Perl version 5.10 Extended Patterns  (?1) (essential; see (?PARNO)) and the  ++ "possessive quantifier" (inessential; could use a  (?>pattern) "atomic" group). If you have Perl version 5.14+, the  tr/// expression in the replacement block can simply be
        { $1 =~ tr/ \t\n\f//dr; }
    (note the  /r switch) with no need for substitute-on-copy.

    I doubt this regex is the most optimal. I'd like to come up with a regex that just matches  \s+ within a nested paren group and replaces with the empty string, but haven't figured this out yet.

    Update: This is a little neater, more elegant, but still not quite what I was hoping for:

    c:\@Work\Perl\monks\iaw4>perl -wMstrict -le "use 5.010; ;; my $s = 'ab + (fun1( fun2( 3 +fun3 ( 4+(5+6) ))) ) + x + f ( 1 + 2 )' +; print qq{'$s'}; ;; $s =~ s{ [(] (?: [^()]++ | (?0) )* [)] } { (my $ns = ${^MATCH}) =~ s/\s+//g; $ns; }xmsgpe; print qq{'$s'}; " 'ab + (fun1( fun2( 3 +fun3 ( 4+(5+6) ))) ) + x + f ( 1 + 2 )' 'ab + (fun1(fun2(3+fun3(4+(5+6))))) + x + f (1+2)'
    Note that the  /p modifier is needed here because  ${^MATCH} is used. And again, the replacement expression becomes a bit simpler with the use of the  /r modifier of Perl 5.14+ on the  s/// operation.


    Give a man a fish:  <%-{-{-{-<

Re: paren formatter for function calls?
by Anonymous Monk on Apr 24, 2018 at 02:30 UTC

    For because?

    Syntax hilighting editors (scite) usually highlight the matching parens, ... programmers usually add newlines ...

    ppi_dumper knows everything, PPI easily gets you a neat tree, and you can easily adjust the whitespace to your liking ( ppix_regexp_strip_comments )

    PPI::Statement PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Word 'ab' PPI::Token::Whitespace ' ' PPI::Token::Operator '+' PPI::Token::Whitespace ' ' PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Word 'fun1' PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Word 'fun2' PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Number '3' PPI::Token::Whitespace ' ' PPI::Token::Operator '+' PPI::Token::Whitespace ' ' PPI::Token::Word 'fun3' PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Number '4' PPI::Token::Whitespace ' ' PPI::Token::Operator '+' PPI::Token::Whitespace ' ' PPI::Structure::List ( ... ) PPI::Statement::Expression PPI::Token::Number '5' PPI::Token::Whitespace ' ' PPI::Token::Operator '+' PPI::Token::Whitespace ' ' PPI::Token::Number '6' PPI::Token::Structure ';'
Re: paren formatter for function calls?
by LanX (Saint) on Apr 24, 2018 at 05:04 UTC
    I use multiple lines if a statement gets to complicated and if I can't use temporary variables.

    Cheers Rolf
    (addicted to the Perl Programming Language and ☆☆☆☆ :)
    Wikisyntax for the Monastery