All Downloads are FREE. Search and download functionalities are using the official Maven repository.

oms3.dsl.Efficiency Maven / Gradle / Ivy

There is a newer version: 0.8.1
Show newest version
/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package oms3.dsl;

import oms3.ComponentException;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.EventObject;
import java.util.List;
import java.util.Locale;
import oms3.Compound;
import oms3.Notification.*;
import ngmf.util.cosu.Efficiencies;

import oms3.Conversions;
import static oms3.SimConst.*;

/**
 *
 * @author od
 */
public class Efficiency implements Buildable {

    String methods = NS;
    String obs;
    int[] obs_idx;
    String sim;
    String precip;
    List obs_l = new ArrayList();
    List sim_l = new ArrayList();
    List precip_l = new ArrayList();

    // output file optional
    String file;

    public void setFile(String file) {
        this.file = file;
    }

    public void setMethods(String methods) {
        this.methods = methods;
    }

    public void setPrecip(String precip) {
        this.precip = precip;
    }

    public void setObs(String obs) {
        String[] l = Conversions.parseArrayElement(obs);
        this.obs = l[0];
        obs_idx = Util.arraysDims(l);
    }

    public void setSim(String sim) {
        this.sim = sim;
    }

    @Override
    public Buildable create(Object name, Object value) {
        return LEAF;
    }

    public void setup(Object comp) {
        if (obs == null || sim == null) {
            throw new ComponentException("obs/sim variable not set.");
        }
        if (comp instanceof Compound) {
            Compound c = (Compound) comp;
            c.addListener(new Listener() {

                @Override
                public void notice(Type T, EventObject E) {
                    if (T == Type.OUT) {
                        DataflowEvent e = (DataflowEvent) E;
                        if (e.getAccess().getField().getName().equals(obs)) {
                            if (obs_idx == null) {
                                obs_l.add((Double) e.getValue());
                            } else {
                                obs_l.add((Double) Util.accessArray(obs, e.getValue(), obs_idx));
                            }
                        } else if (e.getAccess().getField().getName().equals(sim)) {
                            sim_l.add((Double) e.getValue()); //TODO use arrays here too.
                        }
                        if (e.getAccess().getField().getName().equals(precip)) {
                            precip_l.add((Double)e.getValue());
                        }
//                    System.err.println(E.getAccess().getField().getName() + "/" +
//                    E.getComponent().getClass().getName() + E.getValue());
                    }
                }
            });
        }
    }

    String result() {
        if (sim_l.size() != obs_l.size()) {
            throw new ComponentException("obs/sim mismatch: " + obs_l.size() + "/" + sim_l.size());
        }
        if (methods.isEmpty()) {
            return "No efficiency specified.";
        }

        StringBuffer b = new StringBuffer(String.format(Locale.US, "%-15s ", "Efficiencies"));
        for (String m : methods.split(" ")) {
            b.append(String.format(Locale.US, "%10s ", m));
        }
        b.append('\n');
        b.append(String.format(Locale.US, "%15s ", obs + "/" + sim));

        double[] obsarr = Util.convert(obs_l);
        double[] simarr = Util.convert(sim_l);

        double eff = 0;
        for (String m : methods.split(" ")) {
            if (NS.startsWith(m)) {
                eff = Efficiencies.nashSutcliffe(obsarr, simarr, 2);
//            } else if (NS2.startsWith(m)) {
//                eff = Efficiencies.nashSutcliffe(obsarr, simarr, 2);
            } else if (LOGNS.startsWith(m)) {
                eff = Efficiencies.nashSutcliffeLog(obsarr, simarr, 1);
            } else if (LOGNS2.startsWith(m)) {
                eff = Efficiencies.nashSutcliffeLog(obsarr, simarr, 2);
            } else if (IOA.startsWith(m)) {
                eff = Efficiencies.ioa(obsarr, simarr, 1);
            } else if (IOA2.startsWith(m)) {
                eff = Efficiencies.ioa(obsarr, simarr, 2);
            } else if (R2.startsWith(m)) {
                double[] rc = Efficiencies.linearReg(obsarr, simarr);
                eff = rc[2];
            } else if (GRAD.startsWith(m)) {
                double[] rc = Efficiencies.linearReg(obsarr, simarr);
                eff = rc[1];
            } else if (WR2.startsWith(m)) {
                double[] rc = Efficiencies.linearReg(obsarr, simarr);
                if (rc[1] <= 1) {
                    eff = Math.abs(rc[1]) * rc[2];
                } else {
                    eff = Math.pow(Math.abs(rc[1]), -1.0) * rc[2];
                }
            } else if (DSGRAD.startsWith(m)) {
                eff = Efficiencies.dsGrad(obsarr, simarr);
            } else if (AVE.startsWith(m)) {
                eff = Efficiencies.absVolumeError(obsarr, simarr);
            } else if (RMSE.startsWith(m)) {
                eff = Efficiencies.rmse(obsarr, simarr);
            } else if (PBIAS.startsWith(m)) {
                eff = Efficiencies.pbias(obsarr, simarr);
            } else if (PMCC.startsWith(m)) {
                eff = Efficiencies.pearsonsCorrelatrion(obsarr, simarr);
            } else if (ABSDIF.startsWith(m)) {
                eff = Efficiencies.absDiff(obsarr, simarr);
            } else if (LOGABSDIF.startsWith(m)) {
                eff = Efficiencies.absDiffLog(obsarr, simarr);
            } else if (TRMSE.startsWith(m)) {
                eff = Efficiencies.transformedRmse(obsarr, simarr);
            } else if (ROCE.startsWith(m)) {
                if (precip_l.size() == 0) {
                    throw new ComponentException("missing precip for computing ROCE");
                }
                double[] precarr = Util.convert(precip_l);
                eff = Efficiencies.runoffCoefficientError(obsarr, simarr, precarr);
            } else {
                throw new ComponentException("Unknown Efficiency'"+ m + '"');
            }
            b.append(String.format(Locale.US, "%10.5f ", eff));
        }
        return b.toString();
    }

    void printEff(File dir) throws IOException {
        PrintWriter w;
        if (file!= null) {
            w  = new PrintWriter(new FileWriter(new File(dir,file), true));
        } else {
            w = new PrintWriter(new OutputStreamWriter(System.out));
        }
        w.println(result());
        w.flush();
        if (file != null) {
            w.close();
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy