from typing import OrderedDict


def format_errors(err, mode=1):
    """From error dictionary *err*, returns a LaTeX-formatted string,
    after handling None entries.

    """
    onedecimal = r"""{0:8.1f}"""
    twodecimal = r"""{0:8.2f}"""
    threedecimal = r"""{0:12.3f}"""
    fourdecimal = r"""{0:12.4f}"""
    shortblank = r"""{0:8s}""".format('')
    longblank = r"""{0:12s}""".format('')

    if mode == 1:
        me = ' ----' if err['me'] is None else '%+.2f' % (err['me'])
        stde = '----' if err['stde'] is None else '%.2f' % (err['stde'])
        mae = '  ----' if err['mae'] is None else '%6.2f' % (err['mae'])
        mape = '  ----  ' if err['mape'] is None else '%6.1f\%%' % (100 * err['mape'])
        mapbe = '  ----  ' if err['mapbe'] is None else '%6.1f\%%' % (100 * err['mapbe'])
        mapce = '  ----  ' if err['mapce'] is None else '%6.1f\%%' % (100 * err['mapce'])
        text = """$\{%s; %s\}$ %s %s %s""" % \
               (me, stde, mae, mape, mapce)
        return text

    if mode == 2:
        sdict = OrderedDict()
        for lbl in ['pexe', 'nexe', 'maxe', 'mine', 'me', 'mae', 'rmse', 'stde']:
            sdict[lbl] = '        ----' if err[lbl] is None else fourdecimal.format(err[lbl])
        for lbl in ['pexpe', 'nexpe', 'maxpe', 'minpe', 'mpe', 'mape', 'rmspe', 'stdpe',
                    'pexpbe', 'nexpbe', 'maxpbe', 'minpbe', 'mpbe', 'mapbe', 'rmspbe', 'stdpbe',
                    'pexpce', 'nexpce', 'maxpce', 'minpce', 'mpce', 'mapce', 'rmspce', 'stdpce']:
            sdict[lbl] = '        ----' if err[lbl] is None else threedecimal.format(100 * err[lbl])
        text = """nex: {nexe}{nexpe}{nexpbe}{nexpce}\n""" \
               """pex: {pexe}{pexpe}{pexpbe}{pexpce}\n""" \
               """min: {mine}{minpe}{minpbe}{minpce}\n""" \
               """max: {maxe}{maxpe}{maxpbe}{maxpce}\n""" \
               """m:   {me}{mpe}{mpbe}{mpce}\n""" \
               """ma:  {mae}{mape}{mapbe}{mapce}\n""" \
               """rms: {rmse}{rmspe}{rmspbe}{rmspce}\n""" \
               """std: {stde}{stdpe}{stdpbe}{stdpce}\n""".format(**sdict)
        return text

    if mode == 3:
        sdict = OrderedDict()
        # shortblanks changed from empty strings Aug 2015
        for lbl in ['pexe', 'nexe', 'maxe', 'mine', 'me', 'mae', 'rmse', 'stde']:
            sdict[lbl] = shortblank if err[lbl] is None else twodecimal.format(err[lbl])
        for lbl in ['pexpe', 'nexpe', 'maxpe', 'minpe', 'mpe', 'mape', 'rmspe', 'stdpe',
                    'pexpbe', 'nexpbe', 'maxpbe', 'minpbe', 'mpbe', 'mapbe', 'rmspbe', 'stdpbe',
                    'pexpce', 'nexpce', 'maxpce', 'minpce', 'mpce', 'mapce', 'rmspce', 'stdpce']:
            sdict[lbl] = shortblank if err[lbl] is None else onedecimal.format(100 * err[lbl])
        return sdict