/*
 * Copyright (c) 2009 JSCAPE
 * 1147 S. 53rd Pl., Mesa, Arizona, 85206, U.S.A.
 * All rights reserved.
 *
 * This software is the confidential and proprietary information of
 * JSCAPE. ("Confidential Information").  You shall not disclose such
 * Confidential Information and shall use it only in accordance with
 * the terms of the license agreement you entered into with JSCAPE.
 *
 */

package com.jscape.util.functor;

import java.io.Serializable;

/**
 * @author Alex Usun
 */
public abstract class BinaryProcedure<F, S>
        implements Serializable {

    /**
     * @param first  first
     * @param second second
     */
    public abstract void evaluate(F first, S second);

    /**
     * @param next next
     *
     * @return BinaryProcedure instance
     */
    public BinaryProcedure<F, S> then(BinaryProcedure<? super F, ? super S> next) {
        return new Chain<F, S>(this, next);
    }

    /**
     * @param <T>
     * @param <U>
     */
    public static class Chain<T, U>
            extends BinaryProcedure<T, U> {

        private BinaryProcedure<? super T, ? super U> first;
        private BinaryProcedure<? super T, ? super U> second;

        /**
         * @param first  first
         * @param second second
         */
        private Chain(BinaryProcedure<? super T, ? super U> first, BinaryProcedure<? super T, ? super U> second) {
            this.first = first;
            this.second = second;
        }

        /**
         * @param first  first
         * @param second second
         */
        public void evaluate(T first, U second) {
            this.first.evaluate(first, second);
            this.second.evaluate(first, second);
        }

    }

}