├── .gitignore ├── CMAPSSData ├── Damage Propagation Modeling.pdf ├── RUL_FD001.txt ├── RUL_FD002.txt ├── RUL_FD003.txt ├── RUL_FD004.txt ├── final_test.txt ├── readme.txt ├── test_FD001.txt ├── test_FD002.txt ├── test_FD003.txt ├── test_FD004.txt ├── train_FD001.txt ├── train_FD002.txt ├── train_FD003.txt └── train_FD004.txt ├── Challenge_Data ├── Challenge Data Description 2016.pdf ├── final_test.txt ├── readme.txt ├── test.txt └── train.txt ├── Explorative_analysis.ipynb ├── LICENSE ├── LoadData.py ├── PlottingHelpers.py ├── ProcessingHelpers.py ├── README.md ├── TrainSimpleClassifier.ipynb ├── TrainSimpleRegressor.ipynb ├── TrainTensorFlow.ipynb └── requirements.txt /.gitignore: -------------------------------------------------------------------------------- 1 | CMAPSSData.zip 2 | Challenge_Data.zip 3 | git 4 | .ipynb_checkpoints 5 | 6 | *.pyc 7 | .idea -------------------------------------------------------------------------------- /CMAPSSData/Damage Propagation Modeling.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/TobiasGlaubach/python-ml-turbofan/2a96a8034f6442e6daac536222c1fc2202274cf7/CMAPSSData/Damage Propagation Modeling.pdf -------------------------------------------------------------------------------- /CMAPSSData/RUL_FD001.txt: -------------------------------------------------------------------------------- 1 | 112 2 | 98 3 | 69 4 | 82 5 | 91 6 | 93 7 | 91 8 | 95 9 | 111 10 | 96 11 | 97 12 | 124 13 | 95 14 | 107 15 | 83 16 | 84 17 | 50 18 | 28 19 | 87 20 | 16 21 | 57 22 | 111 23 | 113 24 | 20 25 | 145 26 | 119 27 | 66 28 | 97 29 | 90 30 | 115 31 | 8 32 | 48 33 | 106 34 | 7 35 | 11 36 | 19 37 | 21 38 | 50 39 | 142 40 | 28 41 | 18 42 | 10 43 | 59 44 | 109 45 | 114 46 | 47 47 | 135 48 | 92 49 | 21 50 | 79 51 | 114 52 | 29 53 | 26 54 | 97 55 | 137 56 | 15 57 | 103 58 | 37 59 | 114 60 | 100 61 | 21 62 | 54 63 | 72 64 | 28 65 | 128 66 | 14 67 | 77 68 | 8 69 | 121 70 | 94 71 | 118 72 | 50 73 | 131 74 | 126 75 | 113 76 | 10 77 | 34 78 | 107 79 | 63 80 | 90 81 | 8 82 | 9 83 | 137 84 | 58 85 | 118 86 | 89 87 | 116 88 | 115 89 | 136 90 | 28 91 | 38 92 | 20 93 | 85 94 | 55 95 | 128 96 | 137 97 | 82 98 | 59 99 | 117 100 | 20 101 | -------------------------------------------------------------------------------- /CMAPSSData/RUL_FD002.txt: -------------------------------------------------------------------------------- 1 | 18 2 | 79 3 | 106 4 | 110 5 | 15 6 | 155 7 | 6 8 | 90 9 | 11 10 | 79 11 | 6 12 | 73 13 | 30 14 | 11 15 | 37 16 | 67 17 | 68 18 | 99 19 | 22 20 | 54 21 | 97 22 | 10 23 | 142 24 | 77 25 | 88 26 | 163 27 | 126 28 | 138 29 | 83 30 | 78 31 | 75 32 | 11 33 | 53 34 | 173 35 | 63 36 | 100 37 | 151 38 | 55 39 | 48 40 | 37 41 | 44 42 | 27 43 | 18 44 | 6 45 | 15 46 | 112 47 | 131 48 | 13 49 | 122 50 | 13 51 | 98 52 | 53 53 | 52 54 | 106 55 | 103 56 | 152 57 | 123 58 | 26 59 | 178 60 | 73 61 | 169 62 | 39 63 | 39 64 | 14 65 | 11 66 | 121 67 | 86 68 | 56 69 | 115 70 | 17 71 | 148 72 | 104 73 | 78 74 | 86 75 | 98 76 | 36 77 | 94 78 | 52 79 | 91 80 | 15 81 | 141 82 | 74 83 | 146 84 | 17 85 | 47 86 | 194 87 | 21 88 | 79 89 | 97 90 | 8 91 | 9 92 | 73 93 | 183 94 | 97 95 | 73 96 | 49 97 | 31 98 | 97 99 | 9 100 | 14 101 | 106 102 | 8 103 | 8 104 | 106 105 | 116 106 | 120 107 | 61 108 | 168 109 | 35 110 | 80 111 | 9 112 | 50 113 | 151 114 | 78 115 | 91 116 | 7 117 | 181 118 | 150 119 | 106 120 | 15 121 | 67 122 | 145 123 | 180 124 | 7 125 | 179 126 | 124 127 | 82 128 | 108 129 | 79 130 | 121 131 | 120 132 | 39 133 | 38 134 | 9 135 | 167 136 | 87 137 | 88 138 | 7 139 | 51 140 | 55 141 | 155 142 | 47 143 | 81 144 | 43 145 | 98 146 | 10 147 | 92 148 | 11 149 | 165 150 | 34 151 | 115 152 | 59 153 | 99 154 | 103 155 | 108 156 | 83 157 | 171 158 | 15 159 | 9 160 | 42 161 | 13 162 | 41 163 | 88 164 | 14 165 | 155 166 | 188 167 | 96 168 | 82 169 | 135 170 | 182 171 | 36 172 | 107 173 | 14 174 | 95 175 | 142 176 | 23 177 | 6 178 | 144 179 | 35 180 | 97 181 | 68 182 | 14 183 | 67 184 | 191 185 | 19 186 | 10 187 | 158 188 | 183 189 | 43 190 | 12 191 | 148 192 | 13 193 | 37 194 | 122 195 | 80 196 | 93 197 | 132 198 | 32 199 | 103 200 | 174 201 | 111 202 | 68 203 | 192 204 | 121 205 | 134 206 | 48 207 | 85 208 | 8 209 | 23 210 | 8 211 | 6 212 | 57 213 | 83 214 | 172 215 | 101 216 | 81 217 | 86 218 | 165 219 | 73 220 | 121 221 | 139 222 | 75 223 | 151 224 | 145 225 | 11 226 | 108 227 | 14 228 | 126 229 | 61 230 | 85 231 | 8 232 | 101 233 | 153 234 | 89 235 | 190 236 | 12 237 | 62 238 | 134 239 | 101 240 | 121 241 | 167 242 | 17 243 | 161 244 | 181 245 | 16 246 | 152 247 | 148 248 | 56 249 | 111 250 | 23 251 | 84 252 | 12 253 | 43 254 | 48 255 | 122 256 | 191 257 | 56 258 | 131 259 | 51 260 | -------------------------------------------------------------------------------- /CMAPSSData/RUL_FD003.txt: -------------------------------------------------------------------------------- 1 | 44 2 | 51 3 | 27 4 | 120 5 | 101 6 | 99 7 | 71 8 | 55 9 | 55 10 | 66 11 | 77 12 | 115 13 | 115 14 | 31 15 | 108 16 | 56 17 | 136 18 | 132 19 | 85 20 | 56 21 | 18 22 | 119 23 | 78 24 | 9 25 | 58 26 | 11 27 | 88 28 | 144 29 | 124 30 | 89 31 | 79 32 | 55 33 | 71 34 | 65 35 | 87 36 | 137 37 | 145 38 | 22 39 | 8 40 | 41 41 | 131 42 | 115 43 | 128 44 | 69 45 | 111 46 | 7 47 | 137 48 | 55 49 | 135 50 | 11 51 | 78 52 | 120 53 | 87 54 | 87 55 | 55 56 | 93 57 | 88 58 | 40 59 | 49 60 | 128 61 | 129 62 | 58 63 | 117 64 | 28 65 | 115 66 | 87 67 | 92 68 | 103 69 | 100 70 | 63 71 | 35 72 | 45 73 | 99 74 | 117 75 | 45 76 | 27 77 | 86 78 | 20 79 | 18 80 | 133 81 | 15 82 | 6 83 | 145 84 | 104 85 | 56 86 | 25 87 | 68 88 | 144 89 | 41 90 | 51 91 | 81 92 | 14 93 | 67 94 | 10 95 | 127 96 | 113 97 | 123 98 | 17 99 | 8 100 | 28 101 | -------------------------------------------------------------------------------- /CMAPSSData/RUL_FD004.txt: -------------------------------------------------------------------------------- 1 | 22 2 | 39 3 | 107 4 | 75 5 | 149 6 | 78 7 | 94 8 | 14 9 | 99 10 | 162 11 | 143 12 | 7 13 | 71 14 | 105 15 | 12 16 | 160 17 | 162 18 | 104 19 | 194 20 | 82 21 | 91 22 | 11 23 | 26 24 | 142 25 | 39 26 | 92 27 | 76 28 | 124 29 | 64 30 | 118 31 | 6 32 | 22 33 | 147 34 | 126 35 | 36 36 | 73 37 | 89 38 | 11 39 | 151 40 | 10 41 | 97 42 | 30 43 | 42 44 | 60 45 | 85 46 | 134 47 | 34 48 | 45 49 | 24 50 | 86 51 | 119 52 | 151 53 | 142 54 | 176 55 | 157 56 | 67 57 | 97 58 | 8 59 | 154 60 | 139 61 | 51 62 | 33 63 | 184 64 | 46 65 | 12 66 | 133 67 | 46 68 | 46 69 | 12 70 | 33 71 | 15 72 | 176 73 | 23 74 | 89 75 | 124 76 | 163 77 | 25 78 | 74 79 | 78 80 | 114 81 | 96 82 | 10 83 | 172 84 | 166 85 | 115 86 | 70 87 | 94 88 | 56 89 | 86 90 | 96 91 | 50 92 | 73 93 | 154 94 | 129 95 | 171 96 | 71 97 | 105 98 | 113 99 | 37 100 | 7 101 | 13 102 | 22 103 | 9 104 | 120 105 | 100 106 | 107 107 | 41 108 | 153 109 | 126 110 | 59 111 | 18 112 | 66 113 | 13 114 | 14 115 | 139 116 | 13 117 | 75 118 | 8 119 | 109 120 | 137 121 | 41 122 | 192 123 | 23 124 | 86 125 | 184 126 | 15 127 | 195 128 | 126 129 | 120 130 | 165 131 | 101 132 | 116 133 | 126 134 | 36 135 | 7 136 | 122 137 | 159 138 | 88 139 | 173 140 | 146 141 | 130 142 | 108 143 | 53 144 | 162 145 | 59 146 | 100 147 | 56 148 | 145 149 | 76 150 | 57 151 | 31 152 | 88 153 | 173 154 | 34 155 | 7 156 | 133 157 | 172 158 | 6 159 | 22 160 | 83 161 | 82 162 | 84 163 | 95 164 | 174 165 | 111 166 | 72 167 | 109 168 | 87 169 | 179 170 | 158 171 | 126 172 | 12 173 | 8 174 | 10 175 | 123 176 | 103 177 | 12 178 | 106 179 | 12 180 | 32 181 | 37 182 | 116 183 | 15 184 | 10 185 | 46 186 | 142 187 | 24 188 | 135 189 | 56 190 | 43 191 | 178 192 | 71 193 | 104 194 | 15 195 | 166 196 | 89 197 | 36 198 | 11 199 | 92 200 | 96 201 | 59 202 | 13 203 | 167 204 | 151 205 | 154 206 | 109 207 | 116 208 | 91 209 | 11 210 | 88 211 | 108 212 | 76 213 | 14 214 | 89 215 | 145 216 | 17 217 | 66 218 | 154 219 | 41 220 | 182 221 | 73 222 | 39 223 | 58 224 | 14 225 | 145 226 | 88 227 | 162 228 | 189 229 | 120 230 | 98 231 | 33 232 | 184 233 | 110 234 | 68 235 | 24 236 | 75 237 | 18 238 | 16 239 | 166 240 | 98 241 | 176 242 | 81 243 | 118 244 | 35 245 | 131 246 | 194 247 | 112 248 | 26 249 | -------------------------------------------------------------------------------- /CMAPSSData/readme.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/TobiasGlaubach/python-ml-turbofan/2a96a8034f6442e6daac536222c1fc2202274cf7/CMAPSSData/readme.txt -------------------------------------------------------------------------------- /Challenge_Data/Challenge Data Description 2016.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/TobiasGlaubach/python-ml-turbofan/2a96a8034f6442e6daac536222c1fc2202274cf7/Challenge_Data/Challenge Data Description 2016.pdf -------------------------------------------------------------------------------- /Challenge_Data/readme.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/TobiasGlaubach/python-ml-turbofan/2a96a8034f6442e6daac536222c1fc2202274cf7/Challenge_Data/readme.txt -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Tobias Glaubach 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /LoadData.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | """ 3 | Created on Mon Nov 12 14:04:23 2018 4 | 5 | @author: GLA_A 6 | """ 7 | 8 | #%% 9 | 10 | import pandas as pd 11 | import os 12 | 13 | #%% 14 | def load_data(pth, names=None, n_data_sets=4): 15 | 16 | if names is None: 17 | names = ['unit_nr', 'time', 'os_1', 'os_2', 'os_3'] 18 | names += ['sensor_{0:02d}'.format(s + 1) for s in range(26)] 19 | 20 | dc = {} 21 | 22 | for i in range(n_data_sets): 23 | p = os.path.join(pth, 'RUL_FD00{}.txt'.format(i+1)) 24 | df_RUL = pd.read_csv(p, sep= ' ', header=None, names=['RUL_actual'], index_col=False) 25 | p = os.path.join(pth, 'train_FD00{}.txt'.format(i+1)) 26 | df_train = pd.read_csv(p, sep= ' ', header=None, names=names, index_col=False) 27 | p = os.path.join(pth, 'test_FD00{}.txt'.format(i+1)) 28 | df_test = pd.read_csv(p, sep= ' ', header=None, names=names, index_col=False) 29 | s = 'FD_00{}'.format(i+1) 30 | dc[s] = {'df_RUL': df_RUL, 'df_train': df_train, 'df_test': df_test} 31 | 32 | 33 | return dc 34 | 35 | 36 | 37 | 38 | -------------------------------------------------------------------------------- /PlottingHelpers.py: -------------------------------------------------------------------------------- 1 | import matplotlib.pyplot as plt 2 | import pandas as pd 3 | import numpy as np 4 | import ProcessingHelpers 5 | import seaborn as sns 6 | import colorsys 7 | 8 | def plot_grouped_by_RUL(df_sub, leg=True, cols_data=None): 9 | 10 | if cols_data is None: 11 | cols = [col for col in df_sub.columns if len(df_sub[col].unique()) > 2] 12 | cols_data = [col for col in cols if col.startswith('sen') or col.startswith('os')] 13 | 14 | g = sns.PairGrid(data=df_sub, x_vars="RUL", y_vars=cols_data,hue="unit_nr", height=2, aspect=6,) 15 | g = g.map(plt.plot, alpha=0.5) 16 | g = g.set(xlim=(df_sub['RUL'].max(),df_sub['RUL'].min())) 17 | if leg: 18 | g = g.add_legend() 19 | 20 | 21 | def plot_rolling_by_unit(df_sub): 22 | nrs = df_sub['unit_nr'].unique()[:5] 23 | N = len(nrs) 24 | 25 | HSV_tuples = [(x*1.0/N, 0.5, 0.5) for x in range(N)] 26 | colors = map(lambda x: colorsys.hsv_to_rgb(*x), HSV_tuples) 27 | 28 | fig, axes = plt.subplots(len(df_sub.columns),1, figsize = (15,22)) 29 | axes = axes.flatten() 30 | 31 | for unit_nr, color in zip(nrs, colors): 32 | idx = df_sub['unit_nr']==unit_nr 33 | df_sub2 = df_sub.loc[idx].copy() 34 | plot_rolling_stats(df_sub2, 0.1, color, axes) 35 | 36 | for ax in axes: 37 | ax.set_xlim((df_sub.index.max(), df_sub.index.min())) 38 | 39 | def plot_rolling_stats(df_sub2, wind_p, color, axes): 40 | wind_n = int(len(df_sub2) * wind_p) 41 | 42 | for col, ax in zip(df_sub2.columns, axes): 43 | ser_std = df_sub2[col].rolling(wind_n).std()[::wind_n] 44 | ser_mean = df_sub2[col].rolling(wind_n).mean()[::wind_n] 45 | plot_line(ser_mean+ser_std, ser_mean, ser_mean-ser_std, color, ax=ax) 46 | 47 | def plot_line(ser_high, ser_mid, ser_low, col, ax=None, fig=None): 48 | if ax is None: 49 | ax = plt.gca 50 | ax.plot(ser_high.index, ser_high.values, marker='o', linestyle='dashed', color=col) 51 | ax.plot(ser_mid.index, ser_mid.values, marker='o', color=col) 52 | ax.plot(ser_low.index, ser_low.values, marker='o', linestyle='dashed', color=col) 53 | 54 | def plot_imshow(df, resample=True): 55 | cols_data = [col for col in df.columns if col.startswith('s')] 56 | fig, axes = plt.subplots(int(np.ceil(len(cols_data)/3)), 3, figsize=(17, 10)) 57 | axes = axes.flatten() 58 | 59 | m = len(df['unit_nr'].unique()) 60 | 61 | if resample: 62 | n = 3 * m 63 | else: 64 | n = int(df['time'].values.max()) 65 | 66 | t = np.linspace(0, 1, m) 67 | dc_tmp = dict([(col, np.zeros((m, n))) for col in cols_data]) 68 | 69 | for i, (nr, d) in enumerate(df.groupby('unit_nr')): 70 | tmp = ProcessingHelpers.resample_fixed(d, n) if resample else d 71 | 72 | for ax, col in zip(axes, cols_data): 73 | v = np.zeros((1, n)) 74 | v[:] = np.nan 75 | v[0, (n - len(tmp)):] = tmp[col].values 76 | dc_tmp[col][i, :] = v 77 | 78 | for ax, col in zip(axes, cols_data): 79 | 80 | mat = dc_tmp[col] 81 | ax.imshow(mat) 82 | ax.set_ylabel(col) 83 | ax.grid(False) 84 | 85 | for i in range(len(axes) - len(cols_data)): 86 | fig.delaxes(axes[-(i+1)]) -------------------------------------------------------------------------------- /ProcessingHelpers.py: -------------------------------------------------------------------------------- 1 | import numpy as np 2 | import pandas as pd 3 | from scipy.signal import filtfilt 4 | 5 | def rolling_mean_by_unit(df, n, verbose=False): 6 | cols_sensors = [c for c in df.columns if c.startswith('sensor')] 7 | df_new = df.copy() 8 | unit_nrs = df['unit_nr'].unique() 9 | 10 | for nr in unit_nrs: 11 | if verbose: 12 | print('processing unit nr: {}'.format(nr)) 13 | idx = df['unit_nr'] == nr 14 | df_new.loc[idx,cols_sensors] = df.loc[idx, cols_sensors].rolling(n, min_periods=1).mean() 15 | return df_new 16 | 17 | def apply_filtfilt_by_unit(df, b, a=1.0): 18 | cols_data = [col for col in df.columns if col.startswith('sen') or col.startswith('os')] 19 | df_new = pd.DataFrame(columns=df.columns) 20 | 21 | for unit_nr, df_sub in df.groupby('unit_nr'): 22 | n = len(df_sub) 23 | for col in df_sub.columns: 24 | if col.startswith('s'): 25 | df_sub[col] = filtfilt(b, a, df_sub[col].copy().values, padlen=5 * len(b)) 26 | df_new = df_new.append(df_sub) 27 | 28 | return df_new 29 | 30 | def apply_rolling_by_unit(df, fun, win_size_p=0.05, subsample=0): 31 | cols_data = [col for col in df.columns if col.startswith('sen') or col.startswith('os')] 32 | df_new = pd.DataFrame(columns=df.columns) 33 | 34 | for unit_nr, df_sub in df.groupby('unit_nr'): 35 | n = len(df_sub) 36 | if isinstance(win_size_p, int): 37 | win_size_n = int(win_size_p) 38 | else: 39 | win_size_n = int(n * win_size_p) 40 | 41 | df_windowed = df_sub.copy() 42 | df_windowed[cols_data] = df_windowed[cols_data].rolling(win_size_n).apply(fun) 43 | if subsample > 0: 44 | df_windowed = df_windowed[::subsample] 45 | df_new = df_new.append(df_windowed) 46 | 47 | return df_new 48 | 49 | def normalize_col_by_unit(df, col): 50 | df_sub = df.copy() 51 | 52 | rul_abs = df_sub[col].copy().values 53 | rul_rel = np.array([]) 54 | for unit_nr in df_sub['unit_nr'].unique(): 55 | tmp = np.array(rul_abs[df_sub['unit_nr']==unit_nr], copy=True) 56 | tmp = tmp - tmp.min() 57 | tmp = tmp / tmp.max() 58 | rul_rel = np.append(rul_rel, tmp) 59 | 60 | df_sub[col] = rul_rel 61 | return df_sub 62 | 63 | def resample_fixed(df, n_new): 64 | n_old, m = df.values.shape 65 | mat_old = df.values 66 | mat_new = np.zeros((n_new, m)) 67 | x_old = np.linspace(df.index.min(), df.index.max(), n_old) 68 | x_new = np.linspace(df.index.min(), df.index.max(), n_new) 69 | 70 | for j in range(m): 71 | y_old = mat_old[:, j] 72 | y_new = np.interp(x_new, x_old, y_old) 73 | mat_new[:, j] = y_new 74 | 75 | return pd.DataFrame(mat_new, index=x_new, columns=df.columns) 76 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | A repository intended to host some machine learning models for gas turbine health monitoring based on the datasets provided by NASA (1) (2) hosted here [article](https://ti.arc.nasa.gov/tech/dash/groups/pcoe/prognostic-data-repository/#turbofan). 2 | 3 | This repository is inspired by Srinath Pereras and Roshan Alwis [article](https://www.infoq.com/articles/machine-learning-techniques-predictive-maintenance) on infoq about predictive maintenance for gas turbines. 4 | 5 | Literature: 6 | 1. A. Saxena and K. Goebel (2008). "Turbofan Engine Degradation Simulation Data Set", NASA Ames Prognostics Data Repository (http://ti.arc.nasa.gov/project/prognostic-data-repository), NASA Ames Research Center, Moffett Field, CA 7 | 8 | 2. A. Saxena and K. Goebel (2008). "PHM08 Challenge Data Set", NASA Ames Prognostics Data Repository (http://ti.arc.nasa.gov/project/prognostic-data-repository), NASA Ames Research Center, Moffett Field, CA 9 | -------------------------------------------------------------------------------- /requirements.txt: -------------------------------------------------------------------------------- 1 | numpy 2 | pandas 3 | seaborn 4 | matplotlib 5 | scikit-learn 6 | tensorflow --------------------------------------------------------------------------------