CoolFace
Apppublic

IAUAI/drop_prediction

sourceHugging Facelgplupdated 3y agoView on Hugging Face
0likes
app.py348 linesDownload Raw Back to root
1import gradio as gr2import pandas as pd3import pickle4import os5from docx import Document6from docx.shared import Inches7from docx.dml.color import ColorFormat8import sklearn9from lightgbm import LGBMClassifier10import numpy as np11import pandas as pd12from sklearn.linear_model import LogisticRegression13from sklearn.model_selection import train_test_split, GridSearchCV, StratifiedKFold14from imblearn.under_sampling import RandomUnderSampler15from sklearn.preprocessing import MinMaxScaler16from imblearn.over_sampling import SMOTE, BorderlineSMOTE 17from imblearn.pipeline import Pipeline as imbpipeline18from sklearn.pipeline import Pipeline19from sklearn.model_selection import cross_val_score, cross_val_predict20from sklearn.neighbors import KNeighborsClassifier21from sklearn import model_selection22from sklearn.neural_network import MLPClassifier23from sklearn.ensemble import RandomForestClassifier, BaggingClassifier, ExtraTreesClassifier,GradientBoostingClassifier, VotingClassifier24from sklearn.tree import DecisionTreeClassifier25from sklearn.linear_model import LogisticRegression26from sklearn.svm import SVC27from sklearn.metrics import confusion_matrix28from sklearn.feature_selection import SequentialFeatureSelector29from sklearn.model_selection import GridSearchCV, StratifiedKFold30import docx31from docx.enum.dml import MSO_THEME_COLOR_INDEX32 33def add_hyperlink(paragraph, text, url):34    # This gets access to the document.xml.rels file and gets a new relation id value35    part = paragraph.part36    r_id = part.relate_to(url, docx.opc.constants.RELATIONSHIP_TYPE.HYPERLINK, is_external=True)37 38    # Create the w:hyperlink tag and add needed values39    hyperlink = docx.oxml.shared.OxmlElement('w:hyperlink')40    hyperlink.set(docx.oxml.shared.qn('r:id'), r_id, )41 42    # Create a w:r element and a new w:rPr element43    new_run = docx.oxml.shared.OxmlElement('w:r')44    rPr = docx.oxml.shared.OxmlElement('w:rPr')45 46    # Join all the xml elements together add add the required text to the w:r element47    new_run.append(rPr)48    new_run.text = text49    hyperlink.append(new_run)50 51    # Create a new Run object and add the hyperlink into it52    r = paragraph.add_run ()53    r._r.append (hyperlink)54 55    # A workaround for the lack of a hyperlink style (doesn't go purple after using the link)56    # Delete this if using a template that has the hyperlink style in it57    r.font.color.theme_color = MSO_THEME_COLOR_INDEX.HYPERLINK58    r.font.underline = True59 60    return hyperlink61 62def savedoc(document,name):63    def delete_paragraph(paragraph):64      p = paragraph._element65      p.getparent().remove(p)66      p._p = p._element = None67    for para in document.paragraphs:68        if para.text == '' and para.text != ' ':69          delete_paragraph(para)70    document.save(name)71    72from sklearn.metrics import accuracy_score, confusion_matrix, roc_auc_score, roc_curve, cohen_kappa_score, f1_score, recall_score, precision_score73def measures(predicted, y_test):74    accuracy = accuracy_score(y_test, predicted)75    precision = precision_score(y_test, predicted)76    recall = recall_score(y_test, predicted)77    f1 = f1_score(y_test, predicted)78    matrix = confusion_matrix(y_test, predicted)79    return accuracy80 81def greet(operation,filer):82  try:83      if filer == None:84          return None,"Invalid file submitted"85      import os86      coset = pd.read_csv(filer.name)87      coset = coset.dropna(how='any')88      document = Document('temp.docx')89      allowedcols = ['SID', 'TERM', 'CATALOG_NBR', 'INSTRUCTOR_ID', 'GRADE', 'CGPA', 'PROGRAM', 'PROGRAM.1']90      if operation == "retrain":91        allowedcols = allowedcols[1:]92        for col in coset.columns:93          if col not in allowedcols:94            return None,str(col)+" is undefined column name, allowed columns for training are "+str(allowedcols)95        wanted = coset#.drop(columns=['SUBJECT','SID','CRSE_ID','COURSE','ROLE','GPA','INPUT','STATUS','GRADUATION TERM','CLASS #','COLLEGE','COLLEGE.1'])96        def termize(x):97            if str(x)[-1] == "1":98              return 099            elif str(x)[-1] == "2":100              return 1101            else:102              return 2103        def shorten_major(x):104            if "Computer Science" in x:105              return "CS"106            elif "Computer Information" in x:107              return "CIS"108            elif "Artificial" in x:109              return "AI"110            elif "Cyber" in x:111                return "CYS"112        def binarize_grade(y):113            todrop = ['TR','DN','NP','IP']114            for element in todrop:115                if element in y:116                    return -1117            if 'W' in y:118                return 1119            else:120                return 0121            122        wanted['PROGRAM.1'] = wanted['PROGRAM.1'].apply(shorten_major)123        wanted['GRADE'] = wanted['GRADE'].apply(binarize_grade)124        wanted['TERM'] = wanted['TERM'].apply(termize)125        deleteRow = wanted[wanted['GRADE'] == -1].index126        wanted.drop(deleteRow, inplace=True)127        majors = []128        catalog = []129        acad_prog = []130        instructor = []131        def numberize(y):132            if y not in majors:133                majors.append(y)134                return majors.index(y)135            else:136                return majors.index(y)137            138        def catalogize(z):139            if z not in catalog:140                catalog.append(z)141                return catalog.index(z)142            else:143                return catalog.index(z)144            145        def acadize(w):146            if w not in acad_prog:147                acad_prog.append(w)148                return acad_prog.index(w)149            else:150                return acad_prog.index(w)151        def instructerize(w):152            if w not in instructor:153                instructor.append(w)154                return instructor.index(w)155            else:156                return instructor.index(w)157 158        def removestring(w):159            if any(c.isalpha() for c in w):160                return w[:-1]161            else:162                return w163            164        wanted['PROGRAM.1'] = wanted['PROGRAM.1'].apply(numberize)165        wanted['CATALOG_NBR'] = wanted['CATALOG_NBR'].apply(catalogize)166        wanted['PROGRAM'] = wanted['PROGRAM'].apply(acadize)167        wanted['INSTRUCTOR_ID'] = wanted['INSTRUCTOR_ID'].apply(instructerize)168        document.add_paragraph(' ')169        document.add_heading('Retraining report', 0)170        document.add_paragraph('This report consists of the models retraining information on the new dataset with ('+str(len(coset))+') records')171        records = []172 173        X = wanted.drop(columns=['GRADE'])174        y = wanted['GRADE']175        smote = BorderlineSMOTE(random_state = 11)176        X_smote, y_smote = smote.fit_resample(X, y)177        kf = StratifiedKFold(n_splits=10)178        models1 = [KNeighborsClassifier(leaf_size=10,metric='manhattan'),179        RandomForestClassifier(max_depth=100),180        LGBMClassifier(n_estimators=200, num_leaves=60),181        VotingClassifier(estimators=[('knn',182                                      KNeighborsClassifier(leaf_size=10,183                                                          metric='manhattan')),184                                    ('rf', RandomForestClassifier(max_depth=100)),('gm',LGBMClassifier(n_estimators=200, num_leaves=60))])]185        metrics = dict()186        for model in models1:187            model.fit(X_smote,y_smote)188            preds = cross_val_predict(model, X_smote.values,y_smote.values, cv=kf, n_jobs=-1,);189            metrics[model] = measures(preds,y_smote.values)190            records.append(((str(type(model).__name__),str(metrics[model]))))191        document.add_paragraph(' ')192        records = tuple(records)193 194        table = document.add_table(rows=1, cols=2)195        hdr_cells = table.rows[0].cells196        hdr_cells[0].text = 'Name'197        hdr_cells[1].text = 'Accuracy'198        for ind,qty in records:199            paragraph = document.add_paragraph()200            row_cells = table.add_row().cells201            row_cells[0].text = str(ind)202            row_cells[1].text = str(qty)203        table.style = 'TableGrid'204          205        dir_name = str(os.getcwd())206        test = os.listdir(dir_name)207        number = 0208        for item in test:209            if item.endswith(".sav") and int(item.split("=")[0]) >= number:210                number = int(item.split("=")[0])211                #os.remove(os.path.join(dir_name, item))212        acc = metrics[max(metrics, key=metrics.get)]213        model = max(metrics, key=metrics.get)214        number = number + 1215        filename = str(number)+"="+type(model).__name__+'='+str(acc)+'.sav'216 217        datavalues = {"majors":str(majors),218        'acad_prog':str(acad_prog),219        'catalog':str(catalog),220        'instructor':str(instructor)221        }222 223        dfv = pd.DataFrame(datavalues,index=[0])224        dfv.to_csv(str(number)+"="+"values.csv")225 226        document.add_paragraph(" ")227        document.add_paragraph(type(model).__name__+' has been chosen as the prediction model for achieving an accuracy of '+str(acc)+'%')228        pickle.dump(model, open(filename, 'wb'))229        document.add_paragraph(" ")230        p = document.add_paragraph('For more like this contact us at ')231        add_hyperlink(p, 'contact@mustafasa.com', "contact@mustafasa.com")232        savedoc(document,'retraining_report.docx')233        #document.save('retraining_report.docx')234        return 'retraining_report.docx',str(type(model).__name__+' has been chosen as the prediction model for achieving an accuracy of '+str(round(acc*100,2))+'%')235      allowedcols.remove('GRADE')236      for col in coset.columns:237        if col not in allowedcols:238          return None,str(col)+" is undefined column name, allowed columns for prediction are "+str(allowedcols)239      majors = []240      catalog = []241      acad_prog = []242      instructor = []243      dir_name = str(os.getcwd())244      test = os.listdir(dir_name)245      modelname = ""246      maxnum = 0247      for item in test:248          if item.endswith(".sav") and int(item.split("=")[0]) > maxnum:249              maxnum = int(item.split("=")[0])250              modelname = item251      if maxnum == 0:252          return None,"No model found, please use retrain operation to build one"253      dfv = pd.read_csv(str(maxnum)+"=values.csv")254 255      cols = [majors,acad_prog,catalog,instructor]256      indexc = 0257 258      for column in dfv.columns:259          if "[" in str(dfv[column][0]):260            l = dfv[column][0].replace("'",'')261            cols[indexc][:] = str(l).strip('][').split(', ')262            263            for i,e in enumerate(cols[indexc]):264              cols[indexc][i] = e.replace(' ','')265            print(cols[indexc])266            indexc = indexc + 1267      #modelname = "VotingClassifier=0.95756598831352.sav"268      loaded_model = pickle.load(open(modelname, 'rb'))269      droppers = 0270      total = 0271      document.add_paragraph(' ')272      document.add_heading('Subjects drop prediction report', 0)273      document.add_paragraph('This report consists of students who might potentially drop courses they currently are studying based on the supplied information')274 275      records = []276      for row in coset.iterrows():277          row = list(row)[1]278          semester = 1279          row['CATALOG_NBR'] = str(row['CATALOG_NBR']).replace(' ', '')280          row['TERM'] = str(row['TERM'])281          if row['TERM'][-1] == 2:282              semester = 2283          elif row['TERM'][-1] == 5:284              semester = 3285          c_id = catalog.index(str(row['CATALOG_NBR']))286          in_id = instructor.index(str(row['INSTRUCTOR_ID']))287          p_id = acad_prog.index(row['PROGRAM'])288          major = 0289          x = row['PROGRAM.1']290          if "Computer Science" in x:291              major = 0292          elif "Computer Information" in x:293              major = 1294          elif "Artificial" in x:295              major = 3296          elif "Cyber" in x:297              major = 2298          gpa = row['CGPA']299          prediction = loaded_model.predict([[semester,c_id,in_id,gpa,p_id,major]])[0]300          total = total + 1301          records.append((str(total),str(row['SID']),str(row['TERM']),str(row['CATALOG_NBR']),str(row['INSTRUCTOR_ID']),str(row['CGPA']),str(row['PROGRAM']),str(row['PROGRAM.1']),str(prediction)))302          if prediction == 1:303              droppers = droppers + 1304      document.add_paragraph(' ')305      records = tuple(records)306 307      table = document.add_table(rows=1, cols=9)308      hdr_cells = table.rows[0].cells309      hdr_cells[0].text = 'Index'310      hdr_cells[1].text = 'Student ID'311      hdr_cells[2].text = 'Term'312      hdr_cells[3].text = 'Catalog ID'313      hdr_cells[4].text = 'Instructor ID'314      hdr_cells[5].text = 'Cummulative GPA'315      hdr_cells[6].text = 'Academic Program'316      hdr_cells[7].text = 'Major'317      hdr_cells[8].text = 'Possible Drop Prediction'318      for ind,qty, id1, desc, inst, cgpa,aprog,maj,pred in records:319          paragraph = document.add_paragraph()320          row_cells = table.add_row().cells321          row_cells[0].text = ind322          row_cells[1].text = str(qty)323          row_cells[2].text = id1324          row_cells[3].text = desc325          row_cells[4].text = inst326          row_cells[5].text = cgpa327          row_cells[6].text = aprog328          row_cells[7].text = maj329          if pred == "1":330              pred = "Yes"331          else:332              pred = "No"333          row_cells[8].text = pred334          335      table.style = 'TableGrid'336      #document.add_page_break()337      document.add_paragraph(" ")338      modelname = modelname.split("=")339      lastpara = 'Out of '+str(total)+' records, it is predicted that '+str(droppers)+' courses might be withdrawn from (Prediction model name:'+modelname[1]+'/Accuracy: '+str(float(modelname[2][0:6])*100)+'%)'340      document.add_paragraph(lastpara)341      savedoc(document,'drop_prediction_report.docx')342      #document.save('drop_prediction_report.docx')343      return 'drop_prediction_report.docx', lastpara+" (Model no."+modelname[0]+")"344  except Exception as e:345    return None,str(e)346 347iface = gr.Interface(fn=greet, inputs=[gr.Radio(["predict",'retrain'],value="predict"),"file"], outputs=[gr.File(label='Report generated'),gr.Text(label='Log')],debug=True)348iface.launch()