{"id":3918,"date":"2018-11-20T20:56:57","date_gmt":"2018-11-20T20:56:57","guid":{"rendered":"https:\/\/www.appservgrid.com\/paw92\/?p=3918"},"modified":"2018-12-07T02:47:03","modified_gmt":"2018-12-07T02:47:03","slug":"whats-new-in-bash-parameter-expansion","status":"publish","type":"post","link":"https:\/\/www.appservgrid.com\/paw92\/index.php\/2018\/11\/20\/whats-new-in-bash-parameter-expansion\/","title":{"rendered":"What&#8217;s New in Bash Parameter Expansion"},"content":{"rendered":"<p>The bash man page is close to 40K words. It&#8217;s not<br \/>\nquite War and Peace, but it could hold its<br \/>\nown in a rack of cheap novels.<br \/>\nGiven the size of bash&#8217;s documentation, missing a useful feature<br \/>\nis easy to do when looking through the man page.<br \/>\nFor that reason, as well as to look for new features,<br \/>\nrevisiting the man page occasionally can be a useful<br \/>\nthing to do.<\/p>\n<p>The sub-section of interest today is Parameter Expansion\u2014that is, $var in its many forms.<br \/>\nDon&#8217;t be confused by the name though, it&#8217;s really about parameter<br \/>\nand variable expansion.<\/p>\n<p>I&#8217;m not going to cover all the different forms of parameter<br \/>\nexpansion here, just some that I think may not be as<br \/>\nwidely known as others.<br \/>\nIf you&#8217;re completely new to parameter expansion,<br \/>\ncheck out my ancient <a href=\"https:\/\/www.linuxjournal.com\/content\/bash-parameter-expansion\">post<\/a> or one of the<br \/>\nmany articles elsewhere on the internet.<\/p>\n<h3>Case Conversion<\/h3>\n<p>Gone are the days of using tr &#8216;[[:lower:]]&#8217; &#8216;[[:upper:]]&#8217;<br \/>\nto convert strings to uppercase:<\/p>\n<p>$ a=hello<br \/>\n$ echo $ # First character only<br \/>\nHello<br \/>\n$ echo $ # All characters<br \/>\nHELLO<\/p>\n<p>And for going to lowercase:<\/p>\n<p>$ a=HELLO<br \/>\n$ echo $ # First character only<br \/>\nhELLO<br \/>\n$ echo $ # All characters<br \/>\nhello<\/p>\n<p>You also can specify a character after the operator and change<br \/>\nthe case only of characters that match:<\/p>\n<p>$ a=hello<br \/>\n$ echo $ # First character if it is an &#8216;l&#8217;<br \/>\nhello<br \/>\n$ echo $ # All characters that are &#8216;l&#8217;s<br \/>\nheLLo<\/p>\n<h3>Names Starting with Some Prefix<\/h3>\n<p>Need a list of all the variables whose names match a certain prefix? Do this:<\/p>\n<p>$ mya=1<br \/>\n$ myb=2<br \/>\n$ yourc=3<br \/>\n$ echo ${!my*}<br \/>\nmya myb<\/p>\n<h3>Indirection<\/h3>\n<p>Bash even can give you a taste of the good-old days of programming<br \/>\nC and Assembler and using indirect addressing\u2014well sort of:<\/p>\n<p>$ var=somevalue<br \/>\n$ var_name=var<br \/>\n$ echo ${!var_name}<br \/>\nsomevalue<\/p>\n<p>What&#8217;s happening here is that the value of var_name gives you<br \/>\nthe name of the actual variable to be expanded.<br \/>\nThat variable then is expanded and becomes the result of the<br \/>\nexpansion.<br \/>\nIn this case, &#8220;var_name&#8221; has the value &#8220;var&#8221;,<br \/>\nso the variable &#8220;var&#8221; is expanded to yield the ultimate<br \/>\nvalue of &#8220;somevalue&#8221;.<\/p>\n<h3>Short Detour into Namerefs<\/h3>\n<p>As a bit of an aside, because it&#8217;s not really about &#8220;parameter<br \/>\nexpansion&#8221;, let&#8217;s take a quick look at namerefs in bash.<br \/>\nA nameref variable is a variable that references another variable:<\/p>\n<p>$ var=no<br \/>\n$ declare -n ref=var # -n == nameref<br \/>\n$ ref=yes<br \/>\n$ echo $ref<br \/>\nyes<\/p>\n<p>The variable &#8220;ref&#8221; is a reference to the variable &#8220;var&#8221;.<br \/>\nWhen you assign to &#8220;ref&#8221;, you actually change the value of &#8220;var&#8221;.<br \/>\nThis can be particularly handy in getting values out of a<br \/>\nfunction by passing the name of a variable to the function:<\/p>\n<p><b>$ cat nref.sh<\/b><br \/>\nfunction func()<br \/>\n{<br \/>\nlocal -n up_value=$1 # -n == nameref<br \/>\nup_value=new_value<br \/>\necho &#8220;Changing &#8216;${!up_value}&#8217; in $&#8221;<br \/>\n}<\/p>\n<p>aval=old_value<br \/>\necho<br \/>\necho &#8220;Before function call, aval is $aval&#8221;<br \/>\nfunc aval # pass var *name* to func<br \/>\necho &#8220;After function call, aval is $aval&#8221;<\/p>\n<p>Running that, you get:<\/p>\n<p><b>$ bash nref.sh<\/b><br \/>\nBefore function call, aval is old_value<br \/>\nChanging &#8216;aval&#8217; in func<br \/>\nAfter function call, aval is new_value<\/p>\n<p>Since indirection is automatic with nameref variables,<br \/>\nyou don&#8217;t use the exclamation point expansion to get the value<br \/>\nof the referenced variable; normal $var expansion works.<br \/>\nIn the case of namerefs, the exclamation point expansion<br \/>\nyields a different result: the name of the referenced variable.<br \/>\nSo, this slight detour dealt with parameter expansion after all.<\/p>\n<h3>Transformation<\/h3>\n<p>There are also a number of expansions of the form $,<br \/>\nwhere the &#8220;?&#8221; is one of the letters &#8220;Q&#8221;, &#8220;E&#8221;, &#8220;P&#8221;, &#8220;A&#8221; or &#8220;a&#8221;<br \/>\nthat can transform the value or get you information about<br \/>\nthe variable itself.<br \/>\nFor example:<\/p>\n<p>$ declare -a array=(1 2)<br \/>\n$ echo Attributes: $<br \/>\nAttributes: a # i.e. array was declared with -a<\/p>\n<p>Check the man page for more information about these &#8220;@&#8221; expansions.<\/p>\n<h3>Unset or Null<\/h3>\n<p>And to wrap it up, one other subtle thing that can be easy to<br \/>\noverlook when reading the parameter expansion section relates<br \/>\nto the colon (:) in many of the expansions.<br \/>\nFor example, the :- form of expansion allows a default value<br \/>\nto be specified if a variable is unset or null:<\/p>\n<p>unset var<br \/>\n$ echo var: $<br \/>\nvar: default<\/p>\n<p>var=<br \/>\n$ echo var: $<br \/>\nvar: default<\/p>\n<p>And now if you leave out the colon:<\/p>\n<p>unset var<br \/>\n$ echo var: $<br \/>\nvar: default<\/p>\n<p>var=<br \/>\n$ echo var: $<br \/>\nvar:<\/p>\n<p>So leaving out the colon changes the test from &#8220;unset or null&#8221; to<br \/>\njust a test for &#8220;unset&#8221;.<br \/>\nThis applies to the :-, :=, :?, and :+ forms of<br \/>\nparameter expansion as well.<\/p>\n<h3>Your Mileage May Vary<\/h3>\n<p>If something doesn&#8217;t seem to work, check your bash version:<\/p>\n<p>$ echo $BASH_VERSION<br \/>\n4.4.23(1)-release<\/p>\n<p><a href=\"https:\/\/www.linuxjournal.com\/content\/whats-new-bash-parameter-expansion\" target=\"_blank\" rel=\"noopener\">Source<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>The bash man page is close to 40K words. It&#8217;s not quite War and Peace, but it could hold its own in a rack of cheap novels. Given the size of bash&#8217;s documentation, missing a useful feature is easy to do when looking through the man page. For that reason, as well as to look &hellip; <\/p>\n<p class=\"link-more\"><a href=\"https:\/\/www.appservgrid.com\/paw92\/index.php\/2018\/11\/20\/whats-new-in-bash-parameter-expansion\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;What&#8217;s New in Bash Parameter Expansion&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[],"class_list":["post-3918","post","type-post","status-publish","format-standard","hentry","category-linux"],"_links":{"self":[{"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/posts\/3918","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/comments?post=3918"}],"version-history":[{"count":1,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/posts\/3918\/revisions"}],"predecessor-version":[{"id":4661,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/posts\/3918\/revisions\/4661"}],"wp:attachment":[{"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/media?parent=3918"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/categories?post=3918"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.appservgrid.com\/paw92\/index.php\/wp-json\/wp\/v2\/tags?post=3918"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}