![]() |
writing list to csv file problem - Printable Version +- Python Forum (https://python-forum.io) +-- Forum: Python Coding (https://python-forum.io/forum-7.html) +--- Forum: General Coding Help (https://python-forum.io/forum-8.html) +--- Thread: writing list to csv file problem (/thread-42396.html) |
writing list to csv file problem - jacksfrustration - Jun-29-2024 im making a task reminder that will send emails and sms reminding of tasks and events. my problem that im stuck with is with saving the data. i chose csv as it is easy to maintain and construct using the pandas library. the problem is where i am extending my send_date_list even though the variable itself is a list, whilst looking inside the csv file i notice that that cell in question is a list in quotation marks meaning that it writes the value as a string and not a list. obviously i need it to be saved as a list in order to search or delete specific entries. an example of my code follows def save_info(): names_list,due_dates_list,send_date_list,end_date_list,desc_list,phone_number_list,email_address_list=[],[],[],[],[],[],[] """Save the entered reminder information if valid.""" try: df = pd.read_csv("data.csv") except FileNotFoundError: with open("data.csv", "w") as file: writer = csv.writer(file) writer.writerow(["name", "date", "description", "phone number","email address","recurring"]) df = pd.DataFrame(columns=["name", "date", "description", "phone number","email address","recurring"]) client=kickbox.Client(api_key) kbx=client.kickbox() send_date = send_date_ent.get() end_date=end_date_ent.get() due_date=reminder_date_ent.get() to_email_address=email_ent.get() response=kbx.verify(to_email_address) if response.body['result']!="undeliverable": if check_date(send_date): if check_date(due_date): if check_date(end_date): frequency=simpledialog.askinteger(title="Task frequency",prompt="How many days should the task occur?") name = name_ent.get().title() name_parts = name.split(" ") if len(name_parts) < 2: messagebox.showerror(title="Ooooooops", message="You have not entered a first and last name!!\nPlease try again!!") return desc = description_ent.get() phone_number = phone_ent.get() pattern=r'^\d{11}' if len(str(phone_number))!=11 or not re.match(pattern,phone_number): messagebox.showerror(title="OOOOOOps", message="You have not entered a valid phone number!!\n" "Please enter a valid UK phone number \n" "The phone number should be 12 digits long!!\n") return if check_alphabetical(name): if check_alphabetical(desc): if messagebox.askyesno(title="Save this information?", message=f"On the {due_date} {name_parts[1]}, {name_parts[0]} should be reminded to {desc}!!" f"A text message will be sent on {send_date}\n " f"Their phone number is {phone_number}\n" f"Their email address is {to_email_address}\n" f"Do you want to save this information?\n"): saved_data=df.to_dict("records") if var1.get()==1: end_date_index=dates_list_starting_from_today.index(end_date) send_date=dates_list_starting_from_today[:end_date_index:frequency] send_date_list.extend(send_date) recurring=True print(send_date_list) else: due_dates_list.append(due_date) send_date=send_date_ent.get() send_date_list.append(send_date) due_date=reminder_date_ent.get() recurring=False names_list.append(name) desc_list.append(desc) phone_number_list.append(phone_number) email_address_list.append(to_email_address) saved_data.append({"name":names_list,"send date":send_date_list,"due date":due_dates_list,"description":desc_list,"phone number":phone_number_list,"email address":email_address_list,"recurring":recurring}) df2=pd.DataFrame(saved_data) df2.to_csv("data.csv", index=False) send_date_ent.delete(0, END) reminder_date_ent.delete(0,END) name_ent.delete(0, END) description_ent.delete(0, END) phone_ent.delete(0, END) email_ent.delete(0,END) end_date_ent.delete(0,END) else: messagebox.showerror(title="OOOOOops", message="You have entered a date set in the past!!\nPlease remedy this mistake and try again!!") else: messagebox.showerror(title="OOOOOops", message="You have entered a date set in the past!!\nPlease remedy this mistake and try again!!") else: messagebox.showerror(title="OOOOOOPs",message="The email address you entered does not exist!!\nPlease correct the mistake and submit again!!\n") RE: writing list to csv file problem - deanhystad - Jun-30-2024 If you are using pandas, why are you using a CSV writer? Pandas knows how to read and write CSV files. Your save_info function should be: events_dataframe.to_csv(csv_filename)I think csv files and pandas are poor fits for your problem. I would use a json file and dictionaries, or maybe a dataclass. Pandas does a poor job acting like a list. import pandas as pd from datetime import datetime import json date_format = "%m/%d/%Y" def add_event(events): events.append({ "name": input("Name: "), "description": input("Description: "), "date": datetime.strptime(input("Date: "), date_format), }) def print_events(events): temp = events.copy() for event in temp: event["date"] = event["date"].strftime(date_format) print(pd.DataFrame(temp)) def load_events(filename): try: with open(filename, "r") as file: events = json.load(file) for event in events: event["date"] = datetime.strptime(event["date"], date_format) return events except IOError: return [] def save_events(filename, events): temp = events.copy() for event in temp: event["date"] = event["date"].strftime(date_format) with open(filename, "w") as file: json.dump(events, file) events = load_events("events.json") while True: choice = input("1: Add event\n2: Print events\n3: Quit\n> ") if choice == '1': add_event(events) elif choice == '2': print_events(events) elif choice == '3': break save_events("events.json", events) RE: writing list to csv file problem - Pedroski55 - Jun-30-2024 Quote:json might not be the best choice for on-disk formats; The trouble it has with appending data is a good example of why this might be. Specifically, json objects have a syntax that means the whole object must be read and parsed in order to understand any part of it. If I were collecting information like this and storing it in a database, I would use MySQL and collect the data in an html form. You can access MySQL from Python easily. RE: writing list to csv file problem - deanhystad - Jun-30-2024 I don't see this being an "on disk format" type application. With reoccurring events, expired events, and adding events that may fall anywhere within the range of existing events there is going to be a lot of shuffling in the order of event records. Appending events to the end of a file is not going to a requirement. A database would work, but I think most queries will have to pull up the entire table. Queries, the biggest advantage of a database, may not be useful for the kinds of comparisons that must be made to find all events scheduled for a particular day. But the choice of file format or database is not the issue here. The problem is that save_info() is a poorly designed function. You should have a function that collects information from the user, and a different function for making the information persistent. When you describe what a function does, "and" should not appear in the description. save_info() pulls information from the form, validates the information, adds the information to the dataframe, and saves the dataframe to a CSV file. That is two to many commas and one to many "and"s RE: writing list to csv file problem - jacksfrustration - Jul-01-2024 (Jun-30-2024, 03:55 AM)deanhystad Wrote: If you are using pandas, why are you using a CSV writer? Pandas knows how to read and write CSV files. Your save_info function should be: i use both csvwriter and pandas library approaches to practice using both of them. plus with the csvwriter approach i get to just add the headers. and clear all of the data. i chose list of dictionaries (dataframes/csv) because it is easy to get a hold of data by something like the following from tkinter import messagebox import pandas as pd current_time = datetime.now().strfttime("%d%m%Y") df=pd.read_csv("data.csv") saved_data=df.to_dict("records") for entry in saved_data: if ent["send_date"]==current_time: if messagebox.askyesorno(title="Save information",message=f"On {ent['send_date']} {ent['name']} should be reminded to {ent['task']}\nShould i send this sms?")so for my purposes a csv file is more fitting seeing as with json file i would have a problem with choosing which value to use as the key. if i were to use json i would maybe use the send date as a key and the value as a dictionary that has name,task,phone number and email address key and value pairs. but seeing how there may be multiple tasks to remind about in the same day then the json file approach loses its appeal. if you can please help me with the subject at hand (writing string instead of list of strings in a csv cell) i would greatly appreciate it. |