Expecting this to print out abc - but I get nothing, every time, nothing.
echo abc=xyz | g="$(awk -F "=" '{print $1}')" | echo $g
A pipeline isn't a set of separate assignments. However, you could rewrite your current code as follows:
result=$(
echo 'abc=xyz' | awk -F '=' '{print $1}'
)
echo "$result"
However, a more Bash-centric solution without intermediate assignments could take advantage of a here-string. For example:
awk -F '=' '{print $1}' <<< 'abc=xyz'
Other solutions are possible, too, but this should be enough to get you started in the right direction.
Related
I'm trying to cut the below string starting on the single quote:
name1=O'Reilly
so it leaves:
name2=Reilly
That's easy from the command line with the following commands:
echo $name | cut -d\' -f
echo $name | awk -F\' '{print $2}'
However when I run these commands from a script the string remains unaltered. I've been looking into problems with using single quotes as a delimiter but couldn't find anything. Any way to solve this issue?
That does not change the string the variable expands to, it just outputs the result of string manipulation.
If you want to create a new reference for variable name, use command substitution to save the result of cut/awk operation as variable name:
% name="O'Reilly"
% echo "$name" | awk -F\' '{print $2}'
Reilly
% name=$(echo "$name" | awk -F\' '{print $2}')
% echo "$name"
Reilly
On the other hand, if you want to declare the input as one (name1), and save the output as a different variable (name2):
% name1="O'Reilly"
% name2=$(echo "$name1" | awk -F\' '{print $2}')
% echo "$name2"
Reilly
This might be easier to get using Parameter expansion though:
$ name="O'Reilly"
$ echo "${name#*\'}"
Reilly
$ name="${name#*\'}"
$ echo "$name"
Reilly
In my script I have a variable $var which will hold a value "00135 00136 00137". I want to generate three files based on the values available in $var - if possible without using a loop.
For example, I need touch files with these names:
test.00136.txt
test.00137.txt
test.00138.txt
Avioding a while loop is possible with xargs.
First split the var into lines, use the string num as a placeholder and touch the files:
var="000135 00136 00137 00138 00139"
echo "${var}" | tr " " "\n" | xargs -I num touch test.num.txt
Edit:
Avoid tr with
echo -n "$var" | xargs -d' ' -n1 -Inum echo test.num.txt
The awk utility makes processing columnar data quite simple:
var="00135 00136 00137"
var1=$(echo "$var" | awk '{print $1}')
var2=$(echo "$var" | awk '{print $2}')
var3=$(echo "$var" | awk '{print $3}')
touch "test.${var1}.txt"
touch "test.${var2}.txt"
touch "test.${var3}.txt"
I'm new to shell scripting. I've tried to search online, but I couldn't find what I was looking for - how do I cut a variable to get the value I'm looking for?
for example I have:
Result=`awk -F : -v "Title=" -v "Author=" 'tolower() == tolower(Title) && tolower() == tolower(Author)' BookDB.txt`
//which will return:
//Result= Black:Hat:12.30:20:30
I've tried doing this, but it won't work:
PRICE= cut -d ":" -f 3 $Result
Any help would be appreciated, thanks!
Your code is not wrong ... well, at least most of it!
Doing echo 'Result= Black:Hat:12.30:20:30' | cut -d ":" -f 3 will give the result 12.30.
The issue is that you probably want to use it on a shell script.
To do that just try the following:
PRICE=`cut -d ":" -f 3 $Result`
What I did was basically putting ` before and after the expression that you want to store in your variable.
Reference to learn more: http://www.freeos.com/guides/lsst/ch02sec08.html
Best of luck!
How about using awk...
input="Black:Hat:12.30:20:30"
first=$(echo input | awk -F":" '{print $1}')
echo $first
second=$(echo $input | awk -F":" '{print $2}')
echo $second
date=$(echo $input | awk -F":" '{print $3 ":" $4 ":" $5}')
echo $date
You might have to edit to fit your exact requirements.
I am writing a shell script and I would like to have this code
echo $(awk '{print $1}' /proc/uptime) / 3600 | bc
without the newline character at the end.
I wanted to write it using echo -n, but this code
echo -n $(awk '{print $1}' /proc/uptime) / 3600 | bc
results a syntax error:
(standard_in) 1: syntax error
Can you help me with this?
Thank you very much!
echo $(awk '{print $1}' /proc/uptime) / 3600 | bc | tr -d "\n"
Alternatives:
echo -n $(($(cut -d . -f 1 /proc/uptime)/3600))
mapfile A </proc/uptime; echo -n $((${A%%.*}/3600))
A solution using echo -n:
echo -n $(echo $(awk '{print $1}' /proc/uptime) / 3600 | bc)
In general, if foo produces a line of output, you can print the same output without a newline using echo -n $(foo), even if foo is complicated.
A more straightforward solution using pure awk (since awk does arithmetic and output formatting, there's not much point in using both awk and bc):
awk '{printf("%d", $1 / 3600)}' /proc/uptime
I am having a problem getting my shellscript working using backticks. Here is an example version of the script I am having an issue with:
#!/bin/sh
ECHO_TEXT="Echo this"
ECHO_CMD="echo ${ECHO_TEXT} | awk -F' ' '{print \$1}'"
result=`${ECHO_CMD}`;
echo $result;
result=`echo ${ECHO_TEXT} | awk -F' ' '{print \$1}'`;
echo $result;
The output of this script is:
sh-3.2$ ./test.sh
Echo this | awk -F' ' '{print $1}'
Echo
Why does the first backtick using a variable for the command not actually execute the full command but only returns the output of the first command along with the second command? I am missing something in order to get the first backtick to execute the command?
You need to use eval to get it working
result=`eval ${ECHO_CMD}`;
in place of
result=`${ECHO_CMD}`;
Without eval
${ECHO_TEXT} | awk -F' ' '{print \$1}
which will be expanded to
Echo this | awk -F' ' '{print \$1}
will be treated as argument to echo and will be output verbatim. With eval that line will actually be run.
You Hi,
you need to know eval command.
See :
#!/bin/sh
ECHO_TEXT="Echo this"
ECHO_CMD="echo ${ECHO_TEXT} | awk -F' ' '{print \$1}'"
result="`eval ${ECHO_CMD}`"
echo "$result"
result="`echo ${ECHO_TEXT} | awk -F' ' '{print $1}'`"
echo "$result"
Take a look to the doc :
help eval
In your first example echo is parsing the parameters - the shell never sees them. In the second example it works because the shell is doing the parsing and knows what to do with a pipe. If you change ECHO_CMD to be "bash echo ..." it will work.
Bash is escaping your command for you. Try
ECHO_TEXT="Echo this"
ECHO_CMD='echo ${ECHO_TEXT} | awk -F" " "'"{print \$1}"'"'
result=`${ECHO_CMD}`;
echo $result;
result=`echo ${ECHO_TEXT} | awk -F' ' '{print \$1}'`;
echo $result;
Or even better, try set -x on the first line, so you see what bash is doing