LinuxQuestions.org
Register a domain and help support LQ
Go Back   LinuxQuestions.org > Forums > Linux Forums > Linux - Newbie
User Name
Password
Linux - Newbie This Linux forum is for members that are new to Linux.
Just starting out and have a question? If it is not in the man pages or the how-to's this is the place!

Notices


Reply
  Search this Thread
Old 12-12-2012, 02:48 PM   #1
Alkass
Member
 
Registered: Mar 2010
Posts: 47

Rep: Reputation: 0
Reading line and assign multidimensional variable


Hi

I do have xml, which do have lines like

Code:
#<pdfrwt "2"> n_vars code(1) ... code1(2).... code1(n_vars) code2(1) ... code2(n_vars) code3(1) ... code3(n_vars)</pdfrwt>

So actually, depending in the "n_vars" each time, I do have a sequence of numbers which correspond to three classes, ie code1, code2,code3 and for each of these classes I get "n_vars" entries for each one.. So, how can I smartly read the line (ok, this I know ;-) and get to assign a "n_vars" multidimensional variables ie something like - Would prefer this in bash

Code:
output1[1]=code1(1)
output1[2]=code1(2)
...
output1[n]=code1(n)
and likewise

output2[1]=code2(1)
..
output2[1]=code2(1)
thanks in advance

Alex

Last edited by Alkass; 12-12-2012 at 02:51 PM.
 
Old 12-15-2012, 09:01 PM   #2
towheedm
Member
 
Registered: Sep 2011
Location: Trinidad & Tobago
Distribution: Debian Jessie
Posts: 592

Rep: Reputation: 119Reputation: 119
There is no such thing as a multi-dimensional array in BASH, but since you prefer to use BASH you can achieve a similar result using several techniques.

First, we must strip the tags from the line. The remaining contents is now your data to be put into the arrays with the first number (n_vars) being the number of elements in the arrays. The elements of each class will make up the array for that particular class. But this is still a one-dimensional array. By creating three arrays (one per class), we will have effectively created a two-dimensional array of size (classes x n_vars).

If your data file has more than one line, we can extend this to create a three-dimensional array where the data in the z-axis represents the arrays from each line. This gives us an array of size (classes x n_vars x line_num).

This can only be true if the arrays base-name are the same. You will normally access the element of a two-dimensional array with array(m,n) or a three-dimensional array with array(m.n.z). We cannot do this in BASH, so I propose that we use a naming convention where the name of the array var contains the row number and z-axis number. Let's use this format for our array name: codey_z[element], where y si the row, z represents the line number from the data file and of course element is the element of that particular cell. We can use indirect referencing to create the array names on the fly.

This is my attempt to achieve the above
Code:
#! /bin/bash

# The class var holds the class number, starting from 1.
# The entries for the classes are kept in the array:
# code$class=( value1 value2 . . . value[n_vars].
# The code$class var name are created dynamically, ie:
# code1 for class=1, code2 for class=2, etc.
# This would be fine for emulating a two-dimensional array.
# But, if the data file contains more than one line of data,
# we must emulate a 3-dimensional array.  We can expand the
# above naming convention to include the line number from
# the data file, ie: code$class_$line_no, so that:
# code1_1 = array for class 1 on line 1, code2_1 = array for class 2 on line 1 etc
# code1_2 = array for class 1 on line 2, code2_2 = array for class 2 on line 2 etc
# etc etc etc.

line=0

create_array () {
  # The contents of the array are passed as the positional parameters.
  # The n_vars is the first element of the array.
  n_vars="$1"
  # Remove the first element of the array.
  shift
  while [ ! -z "$1" ]; do
    let class++
    # We dynamically create the code1, code2, etc vars here and create
    # the array with n_vars number of elements.
    array=( "$@" )
    eval code${class}_${line}="( ${array[@]:0:$n_vars} )"
    echo $(eval "echo \${code${class}_${line}[@]}")
    shift $n_vars
  done
}

while read data; do
  let line++
  # Remove tags and assign the values between the tags to the array.
  array=( $(sed 's,^#<.*> \(.*\)<.*>$,\1,' <<< "$data") )
  class=0
  create_array ${array[@]}
  echo -e "\n"
  echo "number of classes = $class"
  echo "line no = $line"
  # Print array elements
  for (( y=1; y <= $class; y++ )); do
    for (( element=0; element < $n_vars; element++ )); do
      echo "code${y}_${line}[$element] = $(eval echo \${code${y}_${line}[$element]})"
    done
  done
  echo -e "\n"
done < pdfwrt.txt
exit
With the contents of the data file (pdfwrt.txt) being:
Code:
#<pdfrwt "2"> 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40</pdfrwt>
#<pdfrwt "2"> 10 101 102 103 104 105 106 107 108 109 110 201 202 203 204 205 206 207 208 209 210 301 302 303 304 305 306 307 308 309 310</pdfrwt>
#<pdfrwt "2"> 10 1001 1002 1003 1004 1005 1006 1007 1008 1009 1010 1101 1102 1103 1104 1105 1106 1107 1108 1109 1110 1211 1212 1213 1214 1215 1216 1217 1218 1219 1220</pdfrwt>
We get:
Code:
$ ./pdfwrt.sh
11 12 13 14 15 16 17 18 19 20
21 22 23 24 25 26 27 28 29 30
31 32 33 34 35 36 37 38 39 40


number of classes = 3
line no = 1
code1_1[0] = 11
code1_1[1] = 12
code1_1[2] = 13
code1_1[3] = 14
code1_1[4] = 15
code1_1[5] = 16
code1_1[6] = 17
code1_1[7] = 18
code1_1[8] = 19
code1_1[9] = 20
code2_1[0] = 21
code2_1[1] = 22
code2_1[2] = 23
code2_1[3] = 24
code2_1[4] = 25
code2_1[5] = 26
code2_1[6] = 27
code2_1[7] = 28
code2_1[8] = 29
code2_1[9] = 30
code3_1[0] = 31
code3_1[1] = 32
code3_1[2] = 33
code3_1[3] = 34
code3_1[4] = 35
code3_1[5] = 36
code3_1[6] = 37
code3_1[7] = 38
code3_1[8] = 39
code3_1[9] = 40


101 102 103 104 105 106 107 108 109 110
201 202 203 204 205 206 207 208 209 210
301 302 303 304 305 306 307 308 309 310


number of classes = 3
line no = 2
code1_2[0] = 101
code1_2[1] = 102
code1_2[2] = 103
code1_2[3] = 104
code1_2[4] = 105
code1_2[5] = 106
code1_2[6] = 107
code1_2[7] = 108
code1_2[8] = 109
code1_2[9] = 110
code2_2[0] = 201
code2_2[1] = 202
code2_2[2] = 203
code2_2[3] = 204
code2_2[4] = 205
code2_2[5] = 206
code2_2[6] = 207
code2_2[7] = 208
code2_2[8] = 209
code2_2[9] = 210
code3_2[0] = 301
code3_2[1] = 302
code3_2[2] = 303
code3_2[3] = 304
code3_2[4] = 305
code3_2[5] = 306
code3_2[6] = 307
code3_2[7] = 308
code3_2[8] = 309
code3_2[9] = 310


1001 1002 1003 1004 1005 1006 1007 1008 1009 1010
1101 1102 1103 1104 1105 1106 1107 1108 1109 1110
1211 1212 1213 1214 1215 1216 1217 1218 1219 1220


number of classes = 3
line no = 3
code1_3[0] = 1001
code1_3[1] = 1002
code1_3[2] = 1003
code1_3[3] = 1004
code1_3[4] = 1005
code1_3[5] = 1006
code1_3[6] = 1007
code1_3[7] = 1008
code1_3[8] = 1009
code1_3[9] = 1010
code2_3[0] = 1101
code2_3[1] = 1102
code2_3[2] = 1103
code2_3[3] = 1104
code2_3[4] = 1105
code2_3[5] = 1106
code2_3[6] = 1107
code2_3[7] = 1108
code2_3[8] = 1109
code2_3[9] = 1110
code3_3[0] = 1211
code3_3[1] = 1212
code3_3[2] = 1213
code3_3[3] = 1214
code3_3[4] = 1215
code3_3[5] = 1216
code3_3[6] = 1217
code3_3[7] = 1218
code3_3[8] = 1219
code3_3[9] = 1220
Here are two links:
http://tldp.org/LDP/abs/html/arrays.html
http://tldp.org/LDP/abs/html/ivr.html

Hope this helps.
 
1 members found this post helpful.
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
[SOLVED] BASH: Assign a variable to a variable name... c_henry Programming 9 06-04-2012 12:33 PM
Assign Command value to a variable rabir Linux - Newbie 10 05-21-2012 10:01 AM
reading variable while remaining on the same line - bash GSMD Programming 3 04-24-2011 10:47 AM
How do you assign a variable to be a variable file name in a directory? David_Elliott Programming 4 04-14-2009 11:19 AM
how to select a particular line from a file and assign it to a variable? pdklinux79 Linux - Newbie 4 06-18-2008 08:21 PM


All times are GMT -5. The time now is 04:27 PM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Facebook: linuxquestions Google+: linuxquestions
Open Source Consulting | Domain Registration