Abhishek Bagi

Erstelle dein Portfolio mit ProoVErstelle dein Portfolio mit ProoV
ProoV
EN Verifiziertes Arbeitsportfolio

ProoV Portfolio

Abhishek Bagi

Information science and engineering · Don Bosco institute of technology

Zum ProoV-Leaderboard

Projekte

Zertifiziert

Selbstgesteuertes Projekt

Energy and Renewable: Machine Learning for the Power Grid

Junior Machine Learning Engineer · KI / ML · Juli 2026

91/ 100

Built a leakage-free turbine yield predictor end to end: framed TEY as the target, excluded downstream CO/NOx emissions, trained a LinearRegression baseline and a tuned RandomForest, and validated on a genuine time-based hold-out split. Reported honest held-out performance (MAE 1.53 MWh, RMSE 1.94 MWh, R2 0.98) and documented practical limits plus a monitoring/retraining plan.

Bewertet nach

  • Build and validate the model correctly35%
  • Optimize and evaluate honestly25%
  • Write the Model Card (clarity + honesty)25%
  • Explain it to a non-expert15%

Bestanden · Bestehensgrenze 60/100

Was herausstach6
  • Correctly excluded CO and NOx as downstream emissions and kept the 8 legitimate sensor features
  • Used an earlier-years train / later-years test split instead of a random shuffle
  • Compared LinearRegression against RandomForest and showed a clear held-out improvement
  • Checked residuals and explicitly noted the model may not generalize to a different plant
  • Leakage-Free Feature Engineering
  • Honest Held-Out Evaluation
Meine eingereichte Arbeit12 Aufgaben

Problem Frame

Meine Lösung
{"target":"TEY","taskType":"regression","metric":"mae","intendedUse":"Predict energy output sensor data to help engineers monitor performance","passed":true,"attempt":1}

Leakage Flags

Meine Lösung
{"excluded":["CO","NOX","TEY"],"kept":["AT","AP","AH","AFDP","GTEP","TIT","TAT","CDP"],"passed":true,"attempt":1}

Train Validate Baseline

Meine Lösung
{"checkpointId":"turbine-baseline","code":"import pandas as pd\nfrom sklearn.linear_model import LinearRegression\nfrom sklearn.metrics import mean_absolute_error, r2_score\n\ndf = pd.read_csv('gas_turbine.csv')\n\n# The 8 legitimate features. CO and NOX are dropped on purpose: both are\n# measured AFTER the turbine has already made its output, so you would not\n# have them yet at the moment you need to predict TEY.\nfeatures = ['AT', 'AP', 'AH', 'AFDP', 'GTEP', 'TIT', 'TAT', 'CDP']  # fill in the 8th feature\n\ntarget = 'TEY'\n\n# Time-based split: train on 2011-2013, test on 2014-2015.\n# Never shuffle a time-ordered stream at random. That would let the model\n# peek at rows from right next to the ones it gets tested on.\ntrain = df[df['year'] <= 2013]\ntest = df[df['year'] >= 2014]  # fill in: which year should testing start at?\n\nX_train, y_train = train[features], train[target]\nX_test, y_test = test[features], test[target]\n\nmodel = LinearRegression()\nmodel.fit(X_train, y_train)\npreds = model.predict(X_test)\n\nmae = mean_absolute_error(y_test, preds)\nr2 = r2_score(y_test, preds)\n\nprint(\"Baseline: Linear Regression\")\nprint(f\"MAE: {mae:.2f} MWh\")\nprint(f\"R2:  {r2:.3f}\")\n","stdout":"Baseline: Linear Regression\nMAE: 2.90 MWh\nR2:  0.957\n","stderr":"","error":null,"imageCount":0,"durationMs":5983,"ranAt":"2026-07-25T06:49:22.599Z"}

Train Validate Forest

Meine Lösung
{"checkpointId":"turbine-forest","code":"from sklearn.ensemble import RandomForestRegressor\n\n# Same 8 features, same target, same time-based split as Step 1. Only the\n# model changes: a forest of decision trees instead of one straight line.\nmodel_rf = RandomForestRegressor(n_estimators=120, max_depth=12, random_state=42)  # fill in the depth from the brief\nmodel_rf.fit(X_train, y_train)\npreds_rf = model_rf.predict(X_test)\n\nmae_rf = mean_absolute_error(y_test, preds_rf)\nr2_rf = r2_score(y_test, preds_rf)\n\nprint(\"Random Forest (n_estimators=120, max_depth=12)\")\nprint(f\"MAE: {mae_rf:.2f} MWh\")\nprint(f\"R2:  {r2_rf:.3f}\")\nprint(f\"Improvement vs baseline: {mae - mae_rf:.2f} MWh lower MAE\")\n","stdout":"Random Forest (n_estimators=120, max_depth=12)\nMAE: 1.53 MWh\nR2:  0.983\nImprovement vs baseline: 1.37 MWh lower MAE\n","stderr":"","error":null,"imageCount":0,"durationMs":6046,"ranAt":"2026-07-25T06:51:27.876Z"}

Train Validate

Meine Lösung
{"baselinePassed":true,"baselineMae":2.9,"baselineR2":0.957,"rfPassed":true,"rfMae":1.53,"rfR2":0.983,"improvementMae":1.37}

Tune Evaluate Setup

Meine Lösung
{"checkpointId":"tune_evaluate_setup","code":"import pandas as pd\nimport numpy as np\nfrom sklearn.ensemble import RandomForestRegressor\nfrom sklearn.metrics import mean_absolute_error, mean_squared_error, r2_score\n\ndf = pd.read_csv('gas_turbine.csv')\n\nFEATURES = ['AT', 'AP', 'AH', 'AFDP', 'GTEP', 'TIT', 'TAT', 'CDP']\nTARGET = 'TEY'\n\n# Time-based split: train on the earlier years, lock the latest year away as test.\ntrain = df[df['year'] <= 2013]\ntest = df[df['year'] >= 2014]\n\nX_train, y_train = train[FEATURES], train[TARGET]\nX_test, y_test = test[FEATURES], test[TARGET]\n\n# These starter values are deliberately modest. Judge every change ONLY on the\n# held-out numbers printed below, never on how the model looks on training data.\nn_estimators = 120\nmax_depth = 12\n\nmodel = RandomForestRegressor(\n    n_estimators=n_estimators,\n    max_depth=max_depth,\n    random_state=42,\n)\nmodel.fit(X_train, y_train)\npreds = model.predict(X_test)\n\nmae = mean_absolute_error(y_test, preds)\nrmse = mean_squared_error(y_test, preds) ** 0.5\nr2 = r2_score(y_test, preds)\n\nprint(f\"n_estimators={n_estimators}  max_depth={max_depth}\")\nprint(f\"Held-out MAE:  {mae:.3f} MWh\")\nprint(f\"Held-out RMSE: {rmse:.3f}\")\nprint(f\"Held-out R2:   {r2:.4f}\")\n","stdout":"n_estimators=120  max_depth=12\nHeld-out MAE:  1.532 MWh\nHeld-out RMSE: 1.937\nHeld-out R2:   0.9833\n","stderr":"","error":null,"imageCount":0,"durationMs":5630,"ranAt":"2026-07-25T07:01:18.053Z"}

Tune Evaluate Residuals

Meine Lösung
{"checkpointId":"tune_evaluate_residuals","code":"preds = model.predict(X_test)\nresid = y_test.values - preds  # true TEY minus predicted TEY, in MWh\n\nprint(f\"Residual mean: {resid.mean():.3f} MWh\")\nprint(f\"Residual std:  {resid.std():.3f} MWh\")\n\n# A quick text histogram: how spread out are the misses across the held-out year?\ncounts, edges = np.histogram(resid, bins=8)\nfor c, lo, hi in zip(counts, edges[:-1], edges[1:]):\n    print(f\"{lo:6.2f} to {hi:6.2f} MWh | \" + \"#\" * c)\n","stdout":"Residual mean: 1.115 MWh\nResidual std:  1.583 MWh\n -8.48 to  -6.54 MWh | ##\n -6.54 to  -4.60 MWh | ##########\n -4.60 to  -2.66 MWh | ##################################\n -2.66 to  -0.71 MWh | #####################################################################################################################################################################################################################################################################################################################\n -0.71 to   1.23 MWh | #######################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################\n  1.23 to   3.17 MWh | ############################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################\n  3.17 to   5.12 MWh | ###########################
…

Tune Evaluate

Meine Lösung
{"nEstimators":120,"maxDepth":12,"heldOutMAE":1.532,"heldOutRMSE":1.937,"heldOutR2":0.9833,"residualMean":1.115,"residualStd":1.583}

Residual Read

Meine Lösung
{"category":"heteroscedastic","sentence":"My hold-out MAE,RSME and R2 show good performance on this plant, but they do not prove  the model will work on a different plant","passed":true,"attempt":1}

Drift Monitor

Meine Lösung
{"monitorSignal":"rolling_error","retrainThreshold":4,"exploredDriftC":55,"observedMae":9.52}

Model Card

Meine Lösung
{"predicts":"Predicts turbine energy yield(TEY) in MWh from turbine sensor readings.","features":"Uses AT,AP,AH,AFDP,GTEP,TIT,TAT and CDP.CO and NOx were excluded because they are not needed for predicting TEY.","accuracy":"Held-out MAE=1.53 MWh, RMSE=1.94MWh,R2=0.98 KW h","limits":"trained on one plant only. performance may degrade at high loads or when the temperatures go outside the training range, so retraining and monitoring are required","monitor":"Monitor the input distribution and the rolling error. Retrain the model when inputs fall outside the training range or when the rolling  MAE keeps increasing.","hits":{"predicts":true,"features":true,"accuracy":true,"limits":true,"monitor":true},"passed":true,"attempt":1}

Teach Back

Meine Lösung
{"prompt":"Explain your model to the plant manager running tonight’s shift, not to another engineer. In plain words, address four things: what the model predicts, roughly how accurate it is, why you trust that number, and the one situation in which it would let the plant down.","summary":"The model predicts turbine energy yield in MWh. On average it is off by about 1.5 MWh. I trust this result because it was tested on data the model had never seen before. It could become less reliable if future temperature or operating conditions go outside the range it was trained on, So the model should then be monitored and retrained if needed.","wordCount":63,"elementsHit":["predicts","accuracy","trust","failure"],"jargonTerms":[],"passed":true,"attempt":1}
Verifiziertes ZertifikatFälschungssicher · ausgestellt von ProoV
1Abgeschlossenes Projekt
1Verifiziertes Zertifikat
91Durchschnittsnote
Erstelle dein Portfolio mit ProoV