0

I have the following arrays defined in a bash script

IFS=, read -r -a start_files <<< $(head -n 1 file.txt)
IFS=, read -r -a end_files <<< $(tail -n 1 file.txt)

I read also two values from a file

micro=1000000
IFS=#

[ ! -f $INPUT ] && { echo "$INPUT file not found"; exit 99; }
while read start_time end_time
do

    start_time=$(bc <<< "scale=6; $start_time/$micro")
    end_time=$(bc <<< "scale=6; $end_time/$micro")

    ...

done < $INPUT
IFS=$OLDIFS

The values stored in the arrays and in start_time and end_time are epoch times, I mean values like 1361810326.840284000, 1361862515.600478000, 1361990369.166456000

In the "..." line I want to compare the values of start_time and end_time with all the values stored in an array in the following way

for i in `seq 0 116`;
do
    if [ $start_time -ge ${start_files[$i]} && $start_time -le ${end_files[$i]}]; then
        startF=$i
    fi        
done


for j in `seq 0 116`;
do
    if [ $end_time -ge ${start_files[$j]} && $end_time -le ${end_files[$j]}]; then
        endF = $j
    fi        
done

However this code yields a syntax error. What am I doing wrong?

7
  • Arguments to a command need to be separated by e.g. a space. Commented Oct 28, 2014 at 17:08
  • 3
    It would be helpful if you indicated what your syntax error was in the question. Commented Oct 28, 2014 at 17:09
  • 2
    You are missing a space before the closing ] of the test [. Commented Oct 28, 2014 at 17:09
  • What version of bash are you using? There is a bug, fixed in 4.3, that can cause problems when using pre-command assignments to IFS and reading from a here string at the same time. The result is that the here string is split into space-separate words on the embedded commas, but the entire space-separated string is placed in the first argument of the array, rather than one word per element. Commented Oct 28, 2014 at 17:14
  • Take a look at shellcheck.net. Commented Oct 28, 2014 at 17:19

1 Answer 1

1

If you are using POSIX shell-style comparisons, it is good practice to put each test in its own square brackets. Also, you were missing a space from the end of the comparison. Remember that ] is an argument to the function [, rather than a syntactical construct:

for i in {0..116}; do
    if [ "$start_time" -ge "${start_files[$i]}" ] && [ "$start_time" -le "${end_files[$i]}" ]; then
        startF="$i"
    fi        
done

Same for the other one. I have quoted your variables as it is a good habit to get into. I have also used a brace expansion rather than calling seq.

If you are using bash, you can take advantage of the nicer arithmetic syntax:

for ((i=0; i<=116; ++i)); do
    if (( start_time >= ${start_files[$i]} && start_time <= ${end_files[$i]} )); then
        startF="$i"
    fi        
done
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.