arsenal88
arsenal88

Reputation: 1160

Adding elements to list based on condition of previous elements

I have a txt file that I am reading with the following format:

Event B     0     40
Event B     0     75    
Event B     1     30    
Event A         
Event B     1     50    
Event B     1     70    
Event A         
Event A                     
Event B     2     40

I am trying to code the following logic:

For every Event A: print columns 1 and 2 of first Event B SINCE the last Event A

So the output would be the following:

Event B     0     40
Event B     0     75    
Event B     1     30    
Event A     0     40
Event B     1     50    
Event B     1     70    
Event A     1     50    
Event A     N/A   N/A               
Event B     2     40
etc...

I can read in the file ok as a list:

with open(event_file) as schedule:
     schedule = schedule.readlines()


for i in range(0, len(schedule)):
     if schedule[i][0] == 'Event A':
          if schedule[i-X][0] == 'Event A':
               print(schedule[i-X+1])  # Where X is how many lines before Event A the last one was... but I really dont know how to determine this.. Nor do I know if any of this is the right way to go about it.

I hope I'm making sense.

Upvotes: 2

Views: 65

Answers (4)

Sumit Jha
Sumit Jha

Reputation: 1691

You can use regular expression to extract data from the rows and implement logic. Here is another way of doing it:

import re

#Get rows with complete column
regex1 = r"^Event\s+(A|B)\s+(\w+)\s+(\w+)\s*$"
#Get rows with incomplete column
regex2 = r"^Event\s+(A|B)\s+$"


with open(event_file) as schedule:
    schedule = schedule.readlines()

last_B = ()
for string in schedule:
    string_search = re.search(regex1, string)

    if string_search:
        event = string_search.group(1)
        if event == 'B':
            column1 = string_search.group(2)
            column2 = string_search.group(3)
            print((event,column1,column2))
            if len(last_B) == 0:
                last_B = (event,column1,column2)

        continue

    string_search = re.search(regex2, string)

    if string_search:
        event = string_search.group(1)
        if event == 'A' and len(last_B) == 3:
            A = (event, last_B[1],last_B[2]) 
            last_B = ()
        else:
            A = (event, 'N/A', 'N/A') 

        print(A)
        continue

Output:

('B', '0', '40')
('B', '0', '75')
('B', '1', '30')
('A', '0', '40')
('B', '1', '50')
('B', '1', '70')
('A', '1', '50')
('A', 'N/A', 'N/A')
('B', '2', '40')

Upvotes: 1

Patrick Artner
Patrick Artner

Reputation: 51653

You simply have to remember the last Event B:

txt = """Event B  ,   0 ,    40
Event B  ,   0    , 75    
Event B  ,   1    , 30    
Event A
Event B  ,   1    , 50    
Event B  ,   1    , 70    
Event A
Event A        
Event B  ,   2    , 40
"""

# split your data:
data = [ [k.strip() for k in row.strip().split(",")] for row in txt.split("\n")]

rv = []
b = None
for d in data: 
    if d[0] == "Event A":
        # either add the remembered B or N/A's
        if b:
            rv.append([ d[0], b[1],b[2] ])
        else:
            rv.append([ d[0], "N/A","N/A" ])
        b = None     # delete remebered b
        continue
    elif b == None:  # remember first b
        b = d
    if d and d[0]:   # if not empty, add to results 
        rv.append(d)

print (rv) # print results

Output:

[['Event B', '0', '40'], 
 ['Event B', '0', '75'], 
 ['Event B', '1', '30'], 
 ['Event A', '0', '40'], 
 ['Event B', '1', '50'], 
 ['Event B', '1', '70'], 
 ['Event A', '1', '50'], 
 ['Event A', 'N/A', 'N/A'], 
 ['Event B', '2', '40']]

Upvotes: 3

zwer
zwer

Reputation: 25789

I'm very skeptical your code works at all given that you never parse/split the lines so schedule[i][0] will always point to the first character, not to the whole Event A substring.

Either way, one way to do what you want is to just cache the last Event B columns and append them to the next Event A, then blank out the cache, rinse and repeat, something like:

empty_cache = "     N/A   N/A"  # use this as cache when no previous Event B available
with open(event_file) as f:  # open your file
    cache = empty_cache  # begin with an empty cache
    for line in f:  # loop the event file line by line
        line = line.rstrip()  # clear out the whitespace at the line's end
        if line[:7] == "Event B" and cache == empty_cache:  # first Event B encountered
            cache = line[7:]
        elif line[:7] == "Event A":  # Event A encountered
            line = line[:7] + cache  # update the Event A with the cache
            cache = empty_cache  # empty out the cache
        print(line)  # print the current line

No need to parse/split the event lines at all, provided your data is exactly as you're presenting it.

Upvotes: 0

gillyhl
gillyhl

Reputation: 475

This is a really rough attempt. May be wide off the mark, but I hope it helps.

for i in range(0, len(schedule))
    last_a = 0
    if schedule[i][0] == 'Event A'
        res = ('N/A', 'N/A')
        for j in range(last_a, i)
            if schedule[j][0] == 'Event B'
                res = (schedule[j][1], schedule[j][2])
                break
        print 'Event A' + res[0] + res[1]
        last_a = i
    else
       print 'Event B' + schedule[i][1] + schedule[i][2]

Upvotes: 0

Related Questions