Data Analysis in Python through creation of a Data Visualizer tool
Aim: Goal of the project is to develop a data visualiser tool in python for data analysis.
Background:
The input provided is an engine data file extracted from CONVERGE. The file consists of multiple data columns like pressure, volume, crank angle, viscosity, etc..
It is necessary to extract data from the file to analyse them by either plotting the curve or calculating the required data (like work or power).
The code accomplishes that by taking user input, doing the calculations needed and plotting the graphs required by the user automatically.
Program flow:
- File check, wherein '#' as a commented line is compulsory in the data file
- Traversing commented lines and extracting column numbers, column names and units for data.
- Table to display extracted data in a readable format
- Taking user input and calculating power/work and SFC.
- Plotting and saving of plots.
- Using standard formulae, brake specific fuel consumption is calculated.
Code:
import numpy as nm
from numpy import array
from scipy.integrate import odeint
from scipy.optimize import curve_fit
from statistics import mean
import matplotlib.pyplot as plt
import math
import time
from tabulate import tabulate
#-------------------------------Initial data and declarations-------------------
rpm = 1500
linecount = 1
col = nm.array([])
hashline = 0
xdata = [] # pressure
ydata = [] # temperature
numline = nm.array([])
colname = nm.array([])
unitsline = nm.array([])
#-------------------------------Comment line check and file check---------------
for data in open('engine_data.out'):
linecount = linecount + 1
if '#' or '%' or '/' in data:
hashline = hashline + 1
if hashline == 2:
numline = data.split()
elif hashline == 3:
colname = data.split()
elif hashline == 4:
unitsline = data.split()
else:
print('Please entre the right CONVERGE file type; file must contain headers with comments in "#" form')
#-------------------------------Making indices extraction generic--------------
i = 0
num1 = []
col1 = []
units = []
for i in range(len(numline)):
if numline[i].isnumeric():
num1.append(numline[i])
i = 0
for i in range(len(colname)):
if colname[i] != '#':
col1.append(colname[i])
i = 0
for i in range(len(unitsline)):
if colname[i] != '#':
units.append(unitsline[i])
#------------------------------Table for Displaying indices--------------------
table = [num1, col1, units]
table2 = zip(*table)
headers = ['Column numbers', 'Column name', 'Units']
print(tabulate(table2, headers, tablefmt = 'grid'))
#------------------------------Inputs start here-------------------------------
x = int(input('Entre x axis column number: '))
y = int(input('Entre y axis column number: '))
#------------------------------Extracting data---------------------------------
for data in open('engine_data.out'):
if '#' not in data:
col = data.split()
ydata.append(nm.float(col[y-1]))
xdata.append(nm.float(col[x-1]))
#------------------------------Area, Power and Work calculation-----------------
area = nm.trapz(ydata, xdata)
work = area
power = 2*math.pi*rpm*work/60
print('work (in MJ) = ', work)
print('power (in MW)= ', power)
fuelconsm = float(input('Entre fuel consumption rate "per stroke" in mg: '))
fuelrate = (fuelconsm * rpm) / (2*60*1000)
sfc = (fuelrate*3600)/(power*1000)
print('Brake Specific fuel consumption (g/kWh) = ', sfc)
#-----------------------------Plotting------------------------------------------
plt.plot(xdata, ydata, linewidth = 4)
plt.xlabel(col1[x-1] + ' ' + units[x-1])
plt.ylabel(col1[y-1] + ' ' + units[y-1])
filename = col1[y-1] + '-' + col1[x-1] + ' graph'
plt.savefig(filename)
plt.show()
Output:
+------------------+---------------+-----------+
| Column numbers | Column name | Units |
+==================+===============+===========+
| 1 | Crank | (DEG) |
+------------------+---------------+-----------+
| 2 | Pressure | (MPa) |
+------------------+---------------+-----------+
| 3 | Max_Pres | (MPa) |
+------------------+---------------+-----------+
| 4 | Min_Pres | (MPa) |
+------------------+---------------+-----------+
| 5 | Mean_Temp | (K) |
+------------------+---------------+-----------+
| 6 | Max_Temp | (K) |
+------------------+---------------+-----------+
| 7 | Min_Temp | (K) |
+------------------+---------------+-----------+
| 8 | Volume | (m^3) |
+------------------+---------------+-----------+
| 9 | Mass | (kg) |
+------------------+---------------+-----------+
| 10 | Density | (kg/m^3) |
+------------------+---------------+-----------+
| 11 | Integrated_HR | (J) |
+------------------+---------------+-----------+
| 12 | HR_Rate | (J/time) |
+------------------+---------------+-----------+
| 13 | C_p | (J/kg-K) |
+------------------+---------------+-----------+
| 14 | C_v | (J/kg-K) |
+------------------+---------------+-----------+
| 15 | Gamma | (none) |
+------------------+---------------+-----------+
| 16 | Kin_Visc | (m^2/s) |
+------------------+---------------+-----------+
| 17 | Dyn_Visc | (N*s/m^2) |
+------------------+---------------+-----------+
Entre x axis column number: 8
Entre y axis column number: 2
work (in MJ) = 0.0005005866274680075
power (in MW)= 0.07863196356693915
Entre fuel consumption rate "per stroke" in mg: 20
Brake Specific fuel consumption (g/kWh) = 11.445727146745265
Pressure-Volume diagram:
Errors:
Label error in plot command
Solution: mistyped "ylabel". Corrected the spelling.