0

my.txt:

AAAAA -- [4, 2, 1, 2, 4, 2, 4, 4, 5, 2, 2, 1, 5, 2, 4, 3, 1, 1, 3, 3, 5]

BBB -- [5, 2, 1, 2, 4, 5, 4, 4, 1, 2, 2, 2, 4, 4, 4, 3, 1, 2, 3, 3, 2]

K -- [4, 1, 2, 1, 2, 1, 2, 5, 1, 1, 1, 1, 4, 2, 2, 1, 5, 1, 3, 4, 1]

How can I make a code that outputs this: (averages of all numbers in each string)

AAAAA,2.857142857142857

BBB,2.857142857142857

K,2.142857142857143

Note: the code has to work for any other text files contains different numbers/sizes of lists, so I can't just do something like str = "AAAAA -- [4, 2, 1, 2, 4, 2, 4, 4, 5, 2, 2, 1, 5, 2, 4, 3, 1, 1, 3, 3, 5]" and then find the average of this

the_file = "1.txt"

fileRef = open(the_file,"r")      
localList_ofstrings=[]            
for line in fileRef:
    string = line[0:len(line)-1]
    localList_ofstrings.append(string)
    print(string)

  • "causes error" is not a proper problem description. Please include the full traceback _in your post_ – ForceBru Dec 01 '19 at 08:09

3 Answers3

2

The entries in the file are formatted exactly as ordinary Python dictionaries, so you could treat them as such:

import ast

data = {}
with open(the_file) as f:
    for line in f:
        key, value = line.split('--')
        data[key.strip()] = ast.literal_eval(value.strip())  # parse data as Python list literal

Now data will be a dictionary like this:

{
    'AAA': [4, 2, 1, 2, 4, 2, 4, 4, 5, 2, 2, 1, 5, 2, 4, 3, 1, 1, 3, 3, 5],
    ...
}

I hope this data structure will help you calculate the means and write them back to the file

ForceBru
  • 43,482
  • 10
  • 63
  • 98
  • Is there a way for it to print all of the lines, not just aaa also for bbb –  Dec 01 '19 at 08:19
  • @PatrickPichart, it's supposed to include all the lines - I didn't include them in the sample output in order not to clutter the post – ForceBru Dec 01 '19 at 08:20
  • I'm getting error: File "", line 1 [4, 2, 1, 2, 4, 2, 4, 4, 5, 2, 2, 1, 5, 2, 4, 3, 1, 1, 3, 3, 5] ^ IndentationError: unexpected indent –  Dec 01 '19 at 08:25
  • It does not print anything, the output is just the same as mine before –  Dec 01 '19 at 08:30
  • @PatrickPichart, exactly, it doesn't print anything. It provides you with a more useful data structure. Now you can calculate all your means with a simple dictionary comprehension. – ForceBru Dec 01 '19 at 08:32
  • I've never used dictionaries before, the way I'm trying to do it is to open the txt file in python then use readlines() to somehow calculate the average, but I'm not sure how to use it –  Dec 01 '19 at 08:33
  • @PatrickPichart, then you should [consider learning more about dictionaries](https://realpython.com/python-dicts/). The dictionary is one of the basic data structures in Python. Hint about calculating the means: to get sums of each list in the dictionary, use `{key: sum(the_list) for key, the_list in data.items()}` – ForceBru Dec 01 '19 at 08:36
  • Is there any other simpler way to do this? –  Dec 01 '19 at 08:50
  • @PatrickPichart, `ast.literal_eval(value.strip())` returns a list of numbers for each line. If you know how to calculate the mean of a list, then you can solve that in one line. It's also not necessary to build the dictionary: you can print the results right from within the loop – ForceBru Dec 01 '19 at 08:53
  • yes i have no trouble with calculating the mean from a string or a list, but for this i have no clue because its calculating it from a txt file that is not directly typed in python –  Dec 01 '19 at 08:57
  • @PatrickPichart, `literal_eval` already does the job of converting the data from text to a Python list, and you know how to calculate the mean of a list. I don't see what the issue is – ForceBru Dec 01 '19 at 08:59
  • I don't know/never used ast.literal_eval(value.strip()) –  Dec 01 '19 at 09:01
  • @PatrickPichart, then go on and use it, I suppose? [Read the docs](https://docs.python.org/3/library/ast.html#ast.literal_eval), see what `ast.literal_eval('1234')` or `ast.literal_eval('[1,2,3, (4, 5)]')` evaluate to - and then you'll understand what it's doing – ForceBru Dec 01 '19 at 09:05
0

This is my solution:

import re
from os.path import exists


def calculate(path: str):
    pattern_digit = re.compile(r"\d")
    pattern_alpha = re.compile(r"[A-Za-z]")
    digits = []
    alphas = []
    if exists(path):
     try:
        with open(path) as file:
            string = file.read()
        listed_str = string.splitlines()

        for emp_str in listed_str:
            if emp_str == '':
                listed_str.remove(emp_str)

        for number in range(len(listed_str)):
            digits.append(sum([int(n) for n in pattern_digit.findall(listed_str[number])]))

        for alphabet in range(len(listed_str)):      
          alphas.append(''.join(pattern_alpha.findall(listed_str[alphabet])))
     except FileNotFoundError:
       return "No such file or directory found"


    for p in range(len(alphas)):
        print(f"{alphas[p]}---- {digits[p] / len(digits)}")

I know It's a bit complicated, but I guarantee It Will work as you want.

moh80s
  • 763
  • 1
  • 7
  • 21
  • Comments are not for extended discussion; this conversation has been [moved to chat](https://chat.stackoverflow.com/rooms/203422/discussion-on-answer-by-moh-vahedi-how-can-i-find-the-average-of-the-numbers-in). – Samuel Liew Dec 01 '19 at 12:14
  • Unfortunately, the loop with `list_str.remove` won't work for all cases because you're modifying the list you're iterating over, so it may occasionally skip the lines you intended to delete: [Try it online!](https://tio.run/##ZY7BCsIwEETv/Yq9SBsIhVpE7KU/IAheRaw2CQaabNmkgl8fkwZ6cS67DG@Gmb/@jbYNQUgFJA1@5EPbEYnk6Kuzdp51BUSVZbne68o4eE4ToBBgF/OS5EARGhhSYKjhQiAwQtr3W3h9FBJE20ICc3GSVtHdwb6DzUpKUJ1HVY7lBpJ@oZwvipm09dXf7FvDW37gR37iTXNnLIQf "Python 3 – Try It Online") Also see [this answer](https://stackoverflow.com/a/1207427/4354477). – ForceBru Dec 01 '19 at 14:07
0

Okay so I have a pretty simple solution.

with open('file.txt','r') as f:

    for line in f.readlines():
        try:
            name, l = tuple(line.split('--'))
        except ValueError:
            continue
        name = str.strip(name)
        l = str.strip(l,' []\n')
        l = list(map(int, l.split(',')))
        print("{},{}".format(name, sum(l)/len(l)))

So allow me to explain this to you. All I did is read the file, then split them with -- delimiter, then strip the white space in name and then, striped white space, new line character and third bracket. Then I split the list elements by , then mapped them to int using map function. If you are not familiar with map then you can also use list comprehension. Then, I simply calculated the average and print it.

If you are not familiar with map, just replace the line with l = [int(i) for i in l.split(',')] and it should work just fine.
Hope it helps you. Cheers :)

Debdut Goswami
  • 1,301
  • 12
  • 28