⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 solve.java

📁 著名IT公司ILog的APS高级排产优化引擎
💻 JAVA
字号:
package com.power.lpsolver.LPSolve;

import java.util.*;
import java.io.*;
import java.awt.geom.*;
import com.power.util.Message.*;
import com.power.pipeengine.*;
/**
 *
 * <p>Title: PIPE Engine</p>
 * <p>Description: Global Planning Optimization Engine</p>
 * <p>Copyright: Copyright (c) 2002</p>
 * <p>Company: Paraster, Inc.</p>
 * @author Wei Tan
 * @version 1.0
 */

/**
 * Solve implements the Simplex algorithm. It provides methods that handles the
 * iteration process of the Simplex algorithm. It is a singular class.
 */
public class Solve
{
    static ResourceBundle res = ResourceBundle.getBundle("com.power.lpsolver.LPSolve.Res",
                                                          EngineConfig.getInstance().getLocale() );
    private static final Solve INSTANCE =
                              new Solve();

    /**
     * Default constructor.
     */
    private Solve( ) {
    }

    public static Solve getInstance( ) {
        return INSTANCE;
    }

    /**
     * a Hashtable that stores all basic variable indice.
     */
    private Hashtable _basicVariables = new Hashtable();

    /**
     * current pivotal row number.
     */
    private int _pivotRow;

    /**
     * current pivotal column number.
     */
    private int _pivotCol;

    /**
     * current iteration number. Used for both Phase I and Phase II. Reset for
     * Phase II.
     */
    private int _iterNum = 1;

    /**
     * stores the optimal solution. The key is a variable's symbolic name, the
     * value is the variable's value in the solution.
     */
     private Hashtable _solution = new Hashtable();

     /**
      * stores the current optimization phase, may only be
      *   0 - one phase algorithm
      *   1 - phase I of two-phase algortihm
      *   2 - phase II of two-phase algorithm
      */
     private int _currentPhase = 0;


     /**
      * Report the size of the model. Number of rows and number of columns
      */
    private void reportModelSize() {
        Model mdl = Model.getInstance();
        String numOfCols = res.getString( "Number of Columns" );
        MessageArea.getInstance().addMessage( numOfCols + ": " + mdl.getNumberOfColumns() );
        String numOfRows = res.getString( "Number of Rows" );
        MessageArea.getInstance().addMessage( numOfRows + ": " + mdl.getNumberOfRows() );
    }


     /**
      * Solves the model in memory.
      */
     public void solve() {

        Model mdl = Model.getInstance();

        reportModelSize();

        //initialization - introduce slack/surplus/artificial variables
        mdl.initialize();

        if( mdl.needTwoPhaseSimplex() ) {
            String msg = res.getString("LPSolve2010");
            MessageArea.getInstance().addMessage( msg );
            mdl.setModelForPhaseOne();
            msg = res.getString("LPSolve2020");
            MessageArea.getInstance().addMessage( msg );
            _currentPhase = 1;
       }

        //optimality test
        _iterNum = 0;
        int status;
        /*while( ! mdl.getObjectiveFunction().isOptimal() ) {
            System.out.print( "Iteration " + _iterNum + ":" );
            //Model.getInstance().getObjectiveFunction().print();
            this.startIteration();
            _iterNum++;
        }*/

        //System.out.print( "Iteration " + _iterNum + ":" );
        while( ( status = this.startIteration( _iterNum ) ) != 1000 ) {
            _iterNum++;
        }


        if( isProblemInfeasible() ) {
            String msg = res.getString("LPSolve2050");
            MessageArea.getInstance().addMessage( msg );
            System.exit( 0 );
        }

        if( mdl.needTwoPhaseSimplex() ) {
            removeArtificialBasicVariables();
            String msg = res.getString("LPSolve2030");
            ObjectiveValuePlot.getInstance().clear();
            MessageArea.getInstance().addMessage( msg );

            mdl.setModelForPhaseTwo();
            _currentPhase = 2;

            _iterNum = 1;
            while( ( status = this.startIteration( _iterNum ) ) != 1000 ) {
                _iterNum++;
            }
        }

		//mdl.print();

        createSolution();
		//System.out.println( _basicVariables );
		//mdl.getObjectiveFunction().print();
    }

    /**
     * Gets basic variables Hashtable.
     * @return the basic variables Hashtable.
     */
    public Hashtable getBasicVariables() {
        return _basicVariables;
    }

    /**
     * Updates the basic variables Hashtable by removing an existing entry and
     * adding an incoming entry.
     * @param enteringVarIdx
     * @param leavingVarIdx
     */
    public void updateBasicVariables( int enteringVarIdx, int leavingVarIdx ) {
        MemoryManager memMgr = MemoryManager.getInstance();
        String key = memMgr.getIntegerString( leavingVarIdx );
        _basicVariables.remove( key );
        //Integer newBasic = new Integer( enteringVarIdx );
        _basicVariables.put( memMgr.getIntegerString( enteringVarIdx ),
                                                 memMgr.getInteger( enteringVarIdx ) );
    }

    /**
     * Tests to see if the problem is feasible.
     * @return <code>true</code> if it is;
     *         <code>false></code> otherwise.
     */
    public boolean isProblemInfeasible() {
        Vector cons = Model.getInstance().getModelConstraints().getConstraints();
        for( int i=0; i<cons.size(); i++ ) {
                Constraint con = (Constraint) cons.elementAt( i );
                if( con.getRHS() == 0.0 ) continue;
                int basicVarIdx = con.getBasicVariableIndex();
                Variable var = Model.getInstance().getModelVariables().getVariable( basicVarIdx );
                if( var.getVarName().indexOf( "ART" ) == 0 ) return true;
        }

        return false;
    }

    /**
     * Starts an iteration.
     * @param iterNum the current iteration number.
     * @return the status of the iteration:
     *         1000 - when optimal reached;
     *         0    - normal return.
     */
    public int startIteration( int iterNum ) {
        Model mdl = Model.getInstance();
        _pivotCol = mdl.getObjectiveFunction().getPivotColumn();

        //return when optimal solution found
        if( _pivotCol < 0 ) {
            String msg = res.getString("Engine2500");
            if( _currentPhase != 0 ) {
                if( _currentPhase == 1 ) {
                    msg += res.getString("Phase_I");
                } else {
                    msg += res.getString("Phase_II");
                }
            }

            double objValue = mdl.getObjectiveFunction().getRHS();

            ObjectiveValuePlot.getInstance().addPoint(
                  new Point2D.Double( (double) iterNum, objValue ) );

            MessageArea.getInstance().addMessage( res.getString("Iteration_") + iterNum + "\t\t" +
                  mdl.getObjectiveFunction().getRHS() + "\n" );

            msg += res.getString("completed_Optimal");
            MessageArea.getInstance().addMessage( msg );
            return 1000;
        }

        _pivotRow = mdl.getModelConstraints().getPivotRowNumber( _pivotCol );

        Constraint pivotCon = mdl.getModelConstraints().getConsrtaint( _pivotRow );
        double pivotNumber = pivotCon.getElementAt( _pivotCol ).getCoefficient();
        pivotCon.applyMultiplier( 1.0 / pivotNumber );

        int leavingBasicVar = pivotCon.getBasicVariableIndex();

        mdl.getModelConstraints().gaussianEliminationByRow( _pivotRow, _pivotCol );
        Solve.getInstance().updateBasicVariables( _pivotCol, leavingBasicVar );
        pivotCon.setBasicVariableIndex( _pivotCol );

        //double objValue = Math.abs( mdl.getObjectiveFunction().getRHS() );
        double objValue = mdl.getObjectiveFunction().getRHS();

        if( (iterNum % EngineConfig.getInstance().getUpdateInterval() ) == 0 ) {
            ObjectiveValuePlot.getInstance().addPoint(
                  new Point2D.Double( (double) iterNum, objValue ) );

            MessageArea.getInstance().addMessage( res.getString("Iteration_") + iterNum + "\t\t" +
                  mdl.getObjectiveFunction().getRHS() + "\n" );
        }
        return 0;
    }

    /**
     * Adds a basic variable.
     * @param idx the index of the variable to be added.
     */
    public void addBasicVariable( Integer idx ) {
        _basicVariables.put( idx.toString(), idx );
    }

    /**
     * Prints the current solution.
     */
    public void printSolution() {
        Model mdl = Model.getInstance();
        ModelConstraints constraints = mdl.getModelConstraints();


        Vector allCons = constraints.getConstraints();
        for( int i=0; i<allCons.size(); i++ ) {
                Constraint con = (Constraint) allCons.elementAt( i );
                con.printSolution();
        }

    }

    /**
     * Creates a solution and stores it in a solution class.
     */
    public void createSolution() {
        String msg = res.getString("Engine2600");
        MessageArea.getInstance().addMessage( msg );
        Vector cons = Model.getInstance().getModelConstraints().getConstraints();
        int totOriginalVars = Model.getInstance().getTotOriginalVariables();

        /*for( int i=0; i<cons.size(); i++ ) {
                Constraint con = (Constraint) cons.elementAt( i );
                if( con.getRHS() == 0.0 ) continue;
                int basicVarIdx = con.getBasicVariableIndex();
                if( basicVarIdx >= totOriginalVars ) continue;

                Variable var = Model.getInstance().getModelVariables().getVariable( basicVarIdx );
                _solution.put( var.getVarName(), new Double( con.getRHS() ) );
                //System.out.println( var.getVarName() + "\t" + con.getRHS() );
        }*/
        BufferedReader d = null;
        try{
            FileInputStream r = new FileInputStream( "C:\\paraster\\lpsolver\\model.out" );
            d = new BufferedReader( new InputStreamReader( r ) );
        } catch (Exception e ) {
            MessageArea.getInstance().addMessage( "Error: " + e.getMessage() + "\n" );
        }

        if( null == d ) {
          return;
        }

        try{
            //read and discard
            String aLine = d.readLine();
            String token = " ";

            aLine = d.readLine();

            while( aLine != null ) {
                if( aLine.length() <= 1 ) {
                    break;
                }
                StringTokenizer st = new StringTokenizer( aLine, token );
                String varMPSName = new String( st.nextToken() );
                Double varValue = new Double( st.nextToken() );

                if( varValue.doubleValue() != 0 ) {
                    _solution.put( Model.getInstance().getRegularVarName( varMPSName ),
                                   varValue );
                }

                aLine = d.readLine();
            }

            d.close();
        } catch (Exception e) {
            MessageArea.getInstance().addMessage( "Error: " + e.getMessage() + "\n" );
        }


    }

    /**
     * Gets the current incubent solution.
     * @return
     */
    public Hashtable getSolution() {
        return _solution;
    }

    /**
     * Removes the artificial variables after Phase I and before starting Phase II.
     */
    public void removeArtificialBasicVariables( ) {
        Model mdl = Model.getInstance();
        _pivotCol = mdl.getObjectiveFunction().getPivotColumn();

        Vector allCons = mdl.getModelConstraints().getConstraints();

        for( int i=0; i<allCons.size(); i++ ) {
              Constraint con = (Constraint) allCons.elementAt( i );

              int leavingVarIdx = con.getBasicVariableIndex();
              //if( null == _basicVariables.get( MemoryManager.getInstance().getIntegerString( leavingVarIdx ) ) ) {
                      //continue;
              //}

              if( false == mdl.isArtVarIndex( leavingVarIdx ) ) continue;

              //con.print();
              _pivotRow = i;
              _pivotCol = con.getColIdxOfFirstPositiveCoefficient();


              //return when optimal solution found
              if( _pivotCol < 0 ) {
                      MessageArea.getInstance().addMessage( res.getString("LPSolver2000_Remove") );
                      mdl.getModelConstraints().removeConstraint( con );
                      i--;
                      continue;
              }

              double pivotNumber = con.getElementAt( _pivotCol ).getCoefficient();
              con.applyMultiplier( 1.0 / pivotNumber );

              mdl.getModelConstraints().gaussianEliminationByRow( _pivotRow, _pivotCol );
              this.updateBasicVariables( _pivotCol, leavingVarIdx );
              con.setBasicVariableIndex( _pivotCol );

              mdl.normalize();

        }

    }

    /**
     * Tests to see if a variable index is a basic variable index.
     * @param idx the index to be tested.
     * @return <code>true</code> if it is a basic variable index.
     *         <code>false</code> otherwise.
     */
    public boolean isBasicVariable( int idx ) {
        Integer anInt = (Integer) _basicVariables.get( MemoryManager.getInstance().getIntegerString( idx ) );
        if( null != anInt ) {
                return true;
        }

        return false;
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -