Norbu Samdrup
Norbu Samdrup

Reputation: 3

Take in values from CSV to use in a function

I have written a function that takes in the normal force, mass, acceleration, and coefficient of friction and calculates the applied force. I have the values of the parameter for which I need the applied force to be calculated. How do I take in the value from CSV and calculate the applied force. I have tried many times but could not figure it out. Here's my code:

import matplotlib.pyplot as plt
import csv
import math

def forceAppliedCalc(mass, acceleration, normalForce, muVal):
    forceYcomp =  -(-9.8 * mass) - normalForce
    forceXcomp = (mass * acceleration) + (muVal * normalForce)
    return math.sqrt(math.pow(forceXcomp, 2) + math.pow(forceYcomp, 2))


file = open("Data.csv")
reader = csv.reader(file, delimiter=",")
data = dict()

headerRead = False
headers = []

for row in reader:
    if headerRead == False:
        for i in range(len(row)):
            data[row[i]] = []

        headers = row
        headerRead = True
    else:
        for i in range(len(row)):
            data[headers[i]].append(row[i])

And, here's the CSV file I am working with:

Normal,Acceleration,Mass,Mu,Name,Guess
300,0.333,40,0.525,Alf,150
300,0.333,40,0.525,Benny,160
300,0.333,40,0.525,Claire,170
250,0.2,50,0.3,Claire,250
250,0.2,50,0.3,Alf,265
250,0.2,50,0.3,Benny,255
260,0.4,55,0.32,Claire,280
260,0.4,55,0.32,Alf,284
260,0.4,55,0.32,Benny,300
280,0.3,60,0.4,Benny,340
280,0.3,60,0.4,Claire,360
280,0.3,60,0.4,Alf,330
210,0.14,90,0.6,Alf,700
210,0.14,90,0.6,Benny,800
210,0.14,90,0.6,Claire,600
140,0.167,45,0.144,Claire,300
140,0.167,45,0.144,Alf,145
140,0.167,45,0.144,Benny,167
60,1.2,130,0.178,Claire,1225
60,1.2,130,0.178,Alf,1444
60,1.2,130,0.178,Benny,1467
625,0.9,50,0.35,Benny,200
625,0.9,50,0.35,Claire,250
625,0.9,50,0.35,Alf,213
266,0.12,57,0.787,Alf,370
266,0.12,57,0.787,Benny,567
266,0.12,57,0.787,Claire,809
267,0.268,115,0.235,Benny,900
267,0.268,115,0.235,Claire,905
267,0.268,115,0.235,Alf,1020

Thanks in advance

Upvotes: 1

Views: 85

Answers (3)

Winter Squad
Winter Squad

Reputation: 167

First, welcome to SOF!

I think a little approach about you are asking can be the following script (attempting to be simplest and more similar to your original code):

import csv
import math


def force_applied_calc(mass, acceleration, normal_force, mu_val):
    force_y_comp = -(-9.8 * mass) - normal_force
    force_x_comp = (mass * acceleration) + (mu_val * normal_force)
    return math.sqrt(math.pow(force_x_comp, 2) + math.pow(force_y_comp, 2))


if __name__ == '__main__':
    data = []
    headers = []
    save_data = False
    with open('Data.csv', 'r') as read_obj:
        csv_dict_reader = csv.DictReader(read_obj)
        headers = csv_dict_reader.fieldnames
        for csv_dict in csv_dict_reader:
            csv_dict.update(
                {
                    "Force": force_applied_calc(
                        int(csv_dict['Mass']),
                        float(csv_dict['Acceleration']),
                        int(csv_dict['Normal']),
                        float(csv_dict['Mu'])
                    )
                }
            )
            data.append(csv_dict)
            print(csv_dict)

    # Overwrite file with new data.
    if save_data and 'Force' not in headers:
        headers.append('Force')
        with open('Data.csv', 'w', newline='') as write_obj:
            csv_dict_writer = csv.DictWriter(write_obj, delimiter=',', fieldnames=headers)
            csv_dict_writer.writeheader()
            csv_dict_writer.writerows(data)

Note: @tandat it's a really good answer.

Upvotes: 1

Vijayendar Gururaja
Vijayendar Gururaja

Reputation: 860

Something like this would help.

import csv

final_file = open('output.csv', 'a')
writer = csv.writer(final_file)

with open('file.csv', 'r') as file:
    header = next(file).split(",") # exclude header
    header.append("appliedForce")
    writer.writerow(header) # add header to new outputfile
    reader = csv.reader(file, delimiter=',')
    for row in reader:
        appliedForce = forceAppliedCalc(row[2], row[1], row[0], row[3])
        row.append(appliedForce)
        writer.writerow(row)

Upvotes: 0

tandat
tandat

Reputation: 255

You can try using pandas, a well-known library for data processing.

Sample code:

import math
import pandas as pd


def forceAppliedCalc(mass, acceleration, normalForce, muVal):
    forceYcomp =  -(-9.8 * mass) - normalForce
    forceXcomp = (mass * acceleration) + (muVal * normalForce)
    return math.sqrt(math.pow(forceXcomp, 2) + math.pow(forceYcomp, 2))


csv = pd.read_csv('abcd.csv')
csv['force'] = csv[['Mass', 'Acceleration', 'Normal', 'Mu']].apply(lambda x: forceAppliedCalc(*x), axis=1)
print(csv.head())

Output

   Normal  Acceleration  Mass     Mu    Name  Guess       force
0     300         0.333    40  0.525     Alf    150  194.019258
1     300         0.333    40  0.525   Benny    160  194.019258
2     300         0.333    40  0.525  Claire    170  194.019258
3     250         0.200    50  0.300  Claire    250  254.607541
4     250         0.200    50  0.300     Alf    265  254.607541

In case you don't want to use pandas, you can achieve your goal via a complicated python zip, list and map, for example:

# Notice that data is a dictionary of (string: list of string)
force = [forceAppliedCalc(*map(float, params)) for params in zip(data['Mass'], data['Acceleration'], data['Normal'], data['Mu'])]

Output:

[194.01925780705378, 194.01925780705378, 194.01925780705378, 254.60754112948035, 254.60754112948035, 254.60754112948035, 298.1745126599522, 298.1745126599522, 298.1745126599522, 334.3112322372672, 334.3112322372672, 334.3112322372672, 686.1442705437394, 686.1442705437394, 686.1442705437394, 302.269590969717, 302.269590969717, 302.269590969717, 1225.3890086009421, 1225.3890086009421, 1225.3890086009421, 296.29219108845916, 296.29219108845916, 296.29219108845916, 363.79859417540365, 363.79859417540365, 363.79859417540365, 865.0747997861225, 865.0747997861225, 865.0747997861225]

Upvotes: 1

Related Questions