Linux Shell Script: extract values from string in specified manner - linux

I have one variable contain values like:
USER1:USER2,USER3:USER4,USER5:USER6
I want to extract values like USER1,USER3,USER5
For Example:
VALUE = USER1:USER2,USER3:USER4,USER5:USER6
how I echo to extract like this
USER1,USER3,USER5

#!/bin/bash
string=USER1:USER2,USER3:USER4,USER5:USER6
IFS=', ' read -r -a array <<< "$string"
output=
for kv in ${array[#]}; do
key=$(echo $kv | cut -d':' -f1)
output="$output,$key"
done
output=$(echo $output | cut -c 2-)
echo $output

Related

Unix Script loop through individual variables in a list and execute code

I have been busting my head all day long without coming up with a sucessfull solution.
Setup:
We have Linux RHEL 8.3 and a file, script.sh
There is an enviroment variable set by an application with a dynamic string in it.
export PROGARM_VAR="abc10,def20,ghi30"
The delimiter is always "," and the values inside vary from 1 to 20.
Inside the script I have defined 20 variables which take the values
using "cut" command I take each value and assign it to a variable
var1=$(echo $PROGARM_VAR | cut -f1 -d,)
var2=$(echo $PROGARM_VAR | cut -f2 -d,)
var3=$(echo $PROGARM_VAR | cut -f3 -d,)
var4=$(echo $PROGARM_VAR | cut -f4 -d,)
etc
In our case we will have:
var1="abc10" var2="def20" var3="ghi30" and var4="" which is empty
The loop must take each variable, test if its not empty and execute 10 pages of code using the tested variable. When it reaches an empty variable it should break.
Could you give me a hand please?
Thank you
Just split it with a comma. There are endless possibilities. You could:
10_pages_of_code() { echo "$1"; }
IFS=, read -a -r vars <<<"abc10,def20,ghi30"
for i in "${vars[#]}"; do 10_pages_of_code "$i"; done
or:
printf "%s" "abc10,def20,ghi30" | xargs -n1 -d, bash -c 'echo 10_pages_of_code "$1"' _
A safer code could use readarray instead of read to properly handle newlines in values, but I doubt that matters for you:
IFS= readarray -d , -t vars < <(printf "%s" "abc10,def20,ghi30")
You could also read in a stream up:
while IFS= read -r -d, var || [[ -n "$var" ]]; do
10_pages_of_code "$var"
done < <(printf "%s" "abc10,def20,ghi30")
But still you could do it with cut... just actually write a loop and use an iterator.
i=0
while var=$(printf "%s\n" "$PROGARM_VAR" | cut -f"$i" -d,) && [[ -n "$var" ]]; do
10_pages_of_code "$var"
((i++))
done
or
echo "$PROGRAM_VAR" | tr , \\n | while read var; do
: something with $var
done

How to fetch value of variable of variable (parameter expansion) in unix?

How to fetch value of variable of variable (parameter expansion) in unix?
I have a text file(comma separated) filename='workdir.txt' as below which I am reading in unix shell script:
$AC_WORKDIR,current,FILE
$AC_WORKDIR,1 week,DIR
and so on
$AC_WORKDIR is env varriable AC_WORKDIR="/home/ascxd01/data/workdir" already defined.
My code is as below:
filename='workdir.txt'
while read line; do
work_dir=`echo $line | cut -d',' -f1`
echo "$work_dir"
done< $filename
When I am doing echo "$work_dir" its giving me $AC_WORKDIR however I want the actual value of $AC_WORKDIR which is "/home/ascxd01/data/workdir"
Please tell me how to do it.
If you drop the leading $ the indirect expansion should work normally, eg.
while read line; do
work_dir=`echo $line | cut -d',' -f1 | tr -d '$'` # delete "$"
echo "${!work_dir}"
done< $filename
The linked answer provides other maybe less good alternatives that would work, like eval "echo $work_dir".

Split value in a variable using another string and store in array (Bash)

I have a variable diagnosisCodes having value as shown below :
echo $diagnosisCodes
{"code":"some code1","codeSet":"some set1","description":"some description1"} {"code":"some code2","codeSet":"some set2","description":"some description2"} {"code":"some code3","codeSet":"some set3","description":"some description3"}
I want to split these using delimiter "} {", so that I get 3 different values and then store them in an array (in bash).
I found the solution using the below command (suggested by Incrivel Monstro Verde in the comments):
IFS='|' read -r -a array <<< $(echo $string | sed 's/{"code/|"code/g;s/\"}/"/g')
But this solution would fail if my string has "codeSet" attribute which comes before the "code" attribute.
You can use read:
#!/bin/bash
string='{"code":"some code1","codeSet":"some set1","description":"some description1"} {"code":"some code2","codeSet":"some set2","description":"some description2"} {"code":"some code3","codeSet":"some set3","description":"some descripti
IFS='{' read -r -a array <<< $(echo $string | sed 's/}//g')
echo "${array[1]}"
echo "${array[2]}"
echo "${array[3]}"
Try this out
#!/bin/bash
string='{"code":"some code1","codeSet":"some set1","description":"some description1"} {"code":"some code2","codeSet":"some set2","description":"some description2"} {"code":"some code3","codeSet":"some set3","description":"some description3"}'
var="${string//\} {/$'|'}" #replace '} {' with '|' , works for one space only between '} {'
IFS='|' read -r -a array <<< $(echo $var | sed 's/{//g;s/}//g')
for i in "${array[#]}"
do
echo $i
done

linux replace string with another string

I want to replace a string in a file.
I have a textfile which looks like this: id#string.
123456#some new string
234567#some other new string
345678#still some other new string
and then I have alot of folders based on the id of the textfile.
so now I want to replace the string in a textfile
{"fields":[{"t":"B","v":"false or true","n":"SomeText"},{"t":"S","v":"","n":"Keywords"},{"t":"S","v":"","n":"Author"},{"t":"S","v":"","n":"SomeText"},{"t":"S","v":"THI$ is THE old §TRING I want to REPLACE","n":"SomeText"},{"t":"S","v":"","n":"SomeText"},{"t":"A","n":"SomeText"},{"t":"A","v":"SomeInt","n":"SomeText"}]}
but i dont know how to do this since the newstring and or oldstring may contain additional characters
#!/bin/bash
FOLDER=`echo 123456#string | cut -d# -f1`
NEWSTRING=`echo 123456#string | cut -d# -f2`
sed -i ??? $FOLDER/filename.txt
thanks for your help
of the issue is not clear what should be engaged and what replaced, but maybe you need is:
#!/bin/bash
#
# t1 file contains your strings
#
ROW='{"fields":[{"t":"B","v":"false or true","n":"SomeText"},{"t":"S","v":"","n":"Keywords"},{"t":"S","v":"","n":"Aut
IFS=$'\n'
for S in $(cat ./t1); do
F=$(echo $S | awk -F# '{print $1}')
N=$(echo $S | awk -F# '{print $2}')
if [ -z "$N" ]; then continue; fi
NROW=$(echo ${ROW/THIS is THE old STRING I want to REPLACE/$S})
NROW=$(echo ${NROW/Keywords/$N})
NROW=$(echo ${NROW/false or true/$F})
#mkdir $F
#echo $NROW >> file.json
echo $NROW
done

Bash Shell Script - Cut

How i can transform this in a while in bash shell script? Thank you.
a[4]=$(echo $c | cut -c1)
a[3]=$(echo $c | cut -c2)
a[2]=$(echo $c | cut -c3)
a[1]=$(echo $c | cut -c4)
a[0]=$(echo $c | cut -c5)
b[4]=$(echo $d | cut -c1)
b[3]=$(echo $d | cut -c2)
b[2]=$(echo $d | cut -c3)
b[1]=$(echo $d | cut -c4)
b[0]=$(echo $d | cut -c5)
You don't need cut also, following will work:
a=(); for ((i=0; i<5; i++)); do a+=( "${c:$i:1}" ); done
b=(); for ((i=0; i<5; i++)); do b+=( "${d:$i:1}" ); done
There are several ways of getting a reversed string into an array, here is one:
#!/bin/bash
STRING="test string"
# First, reverse the string into a new variable
REV_STRING=$(rev <<< $STRING)
# Declare the array
declare -a ARRAY
ARRAY_LEN=${#REV_STRING}
ARRAY_UPPER_BOUND=$((ARRAY_LEN - 1))
for i in $(seq 0 $ARRAY_UPPER_BOUND); do
# Here, ${REV_STRING:$i:1} is equivalent to say REV_STRING.charAtPosition(i)
ARRAY[$i]=${REV_STRING:$i:1}
done
# To print the array content
for i in $(seq 0 $ARRAY_UPPER_BOUND); do
echo ${ARRAY[$i]}
done
Also, you can use cut in the loop, like this:
#!/bin/bash
STRING="test string"
REV_STRING=$(rev <<< $STRING)
declare -a ARRAY
ARRAY_LEN=${#REV_STRING}
for i in $(seq 1 $ARRAY_LEN); do
# Here, ${REV_STRING:$i:1} is equivalent to say REV_STRING.charAtPosition(i)
# ARRAY[$i]=${REV_STRING:$i:1}
ARRAY[$i]=$(echo $REV_STRING | cut -c$i)
done
# To print the array content
for i in $(seq 1 $ARRAY_LEN); do
echo ${ARRAY[$i]}
done
If I'm understanding your end goal correctly, here's a quick one-liner (although it uses a couple external utilities, not just bash code):
b=( $( rev <<< "${c}" | sed -e 's/./& /g' ) )
That should take whatever ${c} contains, reverse it, split it into individual characters, and assign each character to an entry in the array b. Note that if the original ${c} contains spaces, those will get lost (i.e. there won't be any array elements containing a space).

Resources