Displaying specific lines from a CSV file

  1. The problem statement, all variables and given/known data:
    Display from a csv file, birthdays that occur today. If there are no birthdays today, the next one in the year.

  2. Relevant commands, code, scripts, algorithms:
    The csv file is ordered from older to younger (ie. the most recent birth is at the bottom of the list).

  3. The attempts at a solution (include all code and scripts):
    I can pull todays birthdays out by the following;

date=`date +"%m"`/`date +"%d"`
cat birthdays.csv | grep $date

However I'm having trouble finding where to start to echo the next birthday if there isn't one today. The CSV file has to be ordered as stated above.

  1. Complete Name of School (University), City (State), Country, Name of Professor, and Course Number (Link to Course):
    Canterbury Christ Church University, Canterbury, UK, Paul Stephens, BSc Forensic Computing (Operating Systems 1)

Any help would be greatly appreciated!

Cheers,
Adzi

Increment the date, do another grep if still no output then increment it again?

How do I check if the out put is null?

I'm used to other languages such as VB etc so a logical port for me would be to do

if
$variable is null then
$date + 1
fi

However I'm pretty sure implementing this would give me horrible errors. So what would be the way to do this in linux/sage?

Many Thanks,
Adzi

Bourne, Korn and Bash compatible code:

if [ -z "${VARIABLE}" ]; then
  echo "VARIABLE is empty."
fi

From what I understand (I may be wrong for Im more french speaking native...):
your csv file has birth dates in sorted from older to most recent.
your code could show up a todays birthday if present but in no way help you find the next...
one possible way to start would be to sort the file on months (1rst) and day (2nd) (but are you allowed?)

looks like you will have to write an algorithm with a couple of loops...

Thanks for the replies. The CSV file is ordered by day and month now, listed as such...

name,telNo,birthday
test 1,123456789,1989/01/26
test 2,123456789,1986/01/27
test 3,123456789,1989/06/09
test 4,123456789,1901/08/15

Which means I should be able to get the next line by performing a simple iteration and adding one to the date field. I cant seem to get this to work. My bash logic isn't fantastic and there is probably a lot of glaring errors but this is what I have (which isn't working)...

#"/bin/bash
date=`date +"%m"`/`date +"%d"`
if [ -z "`cat birthday.csv | grep $date`" ]; then
$newDate=$date+1
$date=$newDate
else
echo cat birthday.csv | grep $date
fi

Am I going about this completely the wrong way?

You dont find a birthday that matches today, then what?
You are to write an algorithm using a loop (e.g. while....) until you find the next date after hoping you are not at EOF...

remember your will have to deal with changing months with your increment....

Good luck
Courage!

If your system supports the -A option for grep, you could try something like this (I'm assuming that the records are stored in a file called file.txt, which does not contain the actual header "name,telno..", only the records):

#!/bin/bash

#copy the content of file.txt to a temporary file
cat file.txt > tmp.txt

#get today's month and day
today=`date +%m'/'%d`

#insert a dummy row, with todays date and time in the temporary file
dummy="test 0,123456789,1800/$today"

echo "$dummy" >> tmp.txt

#sort the file by month and day and output to another temp file
sort -t'/' -k2,3 tmp.txt > tmp2.txt

#no of birthdays today, apart from the dummy row
matches_today=`grep "$today" tmp2.txt | grep -v "$dummy" | wc -l`


#if there are no matches for today, check to see if the dummy is the last record; 
#if it is the next birthday is top of the list, otherwise it's the next row; otherwise, 
#if there are matches for today echo them

if test $matches_today -eq 0
        then
                if test "`tail -1 tmp2.txt`" == "$dummy"
                        then
                                echo "`head -1 tmp2.txt`"
                        else
                                echo "`grep -A1 "$dummy" tmp2.txt | grep -v "$dummy"`"
                fi
        else
                echo "`grep "$today" tmp2.txt | grep -v "$dummy"`"

fi

This is not optimally organized obviously, but I'm writting in a hurry :slight_smile:

Your a star!

Seriously, I was trying to make it too complicated. All it took was 20-odd lines. I modified it to suit my situation and it works an absolute treat.

Cheers,
Adzi