2

Is this Bash variable declaration statement:

foo='b'` `'ar' 

less efficient than this:

foo='bar' 

Does this way of formatting "hanging" or "aligned" indents (line continuations):

a_long_variable_name='a seemingly infinitely long '` `'string requiring continuatio'` `'n on the next line...' 

spawn sub-shells, waste resources, or affect performance in any way, apart from annoying those who dislike its form for (anti?)readability?

Efficiency as in: computer efficiency, not "humans typing many characters and creating space-based, gratuitous maintenance debt".

Can impact (or lack thereof) on performance be easily demonstrated?

5
  • 3
    I can't help but think that if you're concerned about performance and using a bash script, you're doing something wrong. Commented Mar 21, 2013 at 1:25
  • 1
    Ï wanted to argue against or in favour of a coding convention that, if it results in useless inefficiencies which can be demonstrated, has no reason for being. Do you actually know if the backticks "cost" cycles? That's a simple, straightforward question which I am not able to demonstrate one way or the other.. Commented Mar 21, 2013 at 1:29
  • According to this, backticks are evaluated in a subshell, which is almost certainly going to cost you (in terms of computational cycles). Commented Mar 21, 2013 at 1:43
  • 1
    A certain type of parser could look inside the backticks, realise there are no tokens and could collapse the whole thing to a no-op, couldn't it? I think it was reasonable to wonder.. Commented Mar 21, 2013 at 1:45
  • See also Bash variable concatenation. Commented Mar 21, 2013 at 14:10

2 Answers 2

5
tester1() { for i in {1..1000}; do a_long_variable_name='a seemingly infinitely long '` `'string requiring continuation'` `'on the next line...' echo $a_long_variable_name > tmp done } tester2() { for i in {1..1000}; do a_long_variable_name="a seemingly infinitely long\ string requiring continuation\ on the next line..." echo $a_long_variable_name > tmp done } echo tester1 time tester1 echo tester2 time tester2 

Results

tester1 real 0m1.878s user 0m0.209s sys 0m0.566s tester2 real 0m0.335s user 0m0.026s sys 0m0.078s 

These all have similar timings to case 2:

read -r -d '' a_long_variable_name <<EOF a seemingly infinitely long string requiring continuation on the next line... EOF a_long_variable_name="a seemingly infinitely long\ string requiring continuation\ on the next line..." 
Sign up to request clarification or add additional context in comments.

10 Comments

Perfect answer! :) So, I guess the backtick escaping is costly indeed.. (a smart look-ahead tokenizer could have nulled that out, am I mistaken?) How would you achieve the same without the backticks? With plain backslash, as in tester2? (indenting would be nice..)
It might be that bash is optimizing this somehow. What do you mean the same?
A) If Bash spawned the subshell (that's what it does, right?) upon encountering the backtick, it would mean wasted cycles no matter what; if it looked inside the backticks and realised there were no tokens it could "swallow and discard" the whole thing as a no-op. 2) With the same I meant: Python-like column-aligned indents after line continuations. It's a code formatting convention debate for long strings.. What would you do in that case?
updated the answer, I mostly use heredocs myself. I agree, the backtick overhead makes no sense, should be optimized away.
@Robottinosino, this is a very good question. I think your backtick thing is a very good solution. I will def look into this and will update if I can find a better way. I tried all sorts of things (sed, echo, heredocs) but can't find a fast way to handle word splits.
|
0

If I needed it, I'd probably build up the string thus:

x='a seemingly infinitely long ' x="$x"'string requiring continuatio' x="$x"'n on the next line...' a_long_variable_name="$x" 

Or minor variations on that theme. Or I'd repeat the long variable name on each line. Here's a real script I use — it lists relevant environment variables for me:

informix1="DB[^=]|DELIMIDENT=|SQL|ONCONFIG|TBCONFIG|INFOR" informix2="CLIENT_LOCALE=|GL_|GLS8BITSYS|CC8BITLEVEL|ESQL|FET_BUF_SIZE=" informix3="INF_ROLE_SEP=|NODEFDAC=|ONCONFIG|OPTCOMPIND|PDQ|PSORT" informix4="PLCONFIG|SERVER_LOCALE|FGL|C4GL|NE_" informix5="TCL_LIBRARY|TK_LIBRARY|TERM=|TERMCAP=|TERMINFO=" informix="$informix1|$informix2|$informix3|$informix4|$informix5" system1="COLLCHAR=|LANG=|LC_" system2="(DY)?LD_LIBRARY_PATH(_[63][42])?=|PATH=|SHLIB_PATH=|LIBPATH=" system="$system1|$system2" jlss="IX([A-Z]|D(32|64)?)=" env | ${EGREP:-egrep} "^($informix|$system|$jlss)" | sort 

(And the ability to switch which egrep program to use became necessary when Mac OS X 10.7.x egrep stopped working on the expression because it was 'too big'.)

1 Comment

Dear Jonathan, I personally find it easier, in Bash, to read constant values within single quotes. The double quotes already tell me "watch out for expansions in here". My "brain parser" can relax when I see a single quote. Other, of course, will disagree.. actually preferring the consistency of always using double quotes..

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.