Oops, depends on this base class ;-)

import java.io.File;

import java.util.StringTokenizer;

import org.apache.tools.ant.BuildException;

import org.apache.tools.ant.types.Parameter;

import org.apache.tools.ant.types.selectors.FileSelector;
import org.apache.tools.ant.types.selectors.BaseExtendSelector;

/**
* Base class for composite selectors.
*/
public abstract class AbstractCompositeSelector
                     extends BaseExtendSelector {

   private FileSelector _root;

   /**
    * Configures this composite selector.
    * <p>
    * This method is guaranteed for be called only once,
    * when [EMAIL PROTECTED] #isSelected} is called the first time.
    *
    * @param  params the selectors type-less parameters.
    * @return the configured composite selector.
    */
   protected abstract FileSelector configure(Parameter[] params);

   /** Gets the root selector, configuring it if necessary. */
   private FileSelector getRoot() {
       if (_root == null) {
           _root = configure(getParameters());
       }
       return _root;
   }

   /**
    * Checks whether a given file should be selected or not.
    *
    * @param  basedir the base directory
    * @param  filename the file path name relative to <code>basedir</code>
    * @param  file the file instance corresponding to <code>filename</code>
    * @return <code>true</code> if selected; <code>false</code> otherwise.
    */
   public boolean isSelected(File basedir, String filename, File file) {
       return getRoot().isSelected(basedir, filename, file);
   }

}



On 1/24/07, Dominique Devienne <[EMAIL PROTECTED]> wrote:
On 1/24/07, Matt Benson <[EMAIL PROTECTED]> wrote:
> If we can think of an elegant way to design this, this
> question comes up enough that it might be useful to
> include such a selector in Ant core.

This is not exactly the same selector, but close enough that the code
should be trivial to adapt to this new particular need. Stefan's
pseudo-code selector is not far from the pseudo-code selector in the
javadoc below. --DD

import java.io.File;

import java.util.List;
import java.util.ArrayList;
import java.util.StringTokenizer;

import org.apache.tools.ant.Project;
import org.apache.tools.ant.BuildException;

import org.apache.tools.ant.types.Parameter;

import org.apache.tools.ant.types.selectors.FileSelector;
import org.apache.tools.ant.types.selectors.OrSelector;
import org.apache.tools.ant.types.selectors.AndSelector;
import org.apache.tools.ant.types.selectors.PresentSelector;

/**
 * A selector that looks whether the given file from the source directory
 * exists in more than one of the target directories, and returns
 * <code>true</code> in this condition only.
 * <p>
 * This selector is useful when one is attempting to partition a directory
 * hierarchy into many separate independent directory hierarchies, to find
 * the <em>duplicate</em> files of the source hierarchy which were put into
 * more than one of the target hierarchies.
 * <p>
 * Equivalent to the following composite selector:
 * <pre>
 *   &lt;or&gt;
 *     &lt;and&gt;
 *       &lt;present targetdir="dir#1"/&gt;
 *       &lt;or&gt;
 *         &lt;present targetdir="dir#2"/&gt;
 *         &lt;present targetdir="dir#3"/&gt;
 *         etc...
 *         &lt;present targetdir="dir#N"/&gt;
 *       &lt;/or&gt;
 *     &lt;/and&gt;
 *     &lt;and&gt;
 *       &lt;present targetdir="dir#2"/&gt;
 *       &lt;or&gt;
 *         &lt;present targetdir="dir#3"/&gt;
 *         &lt;present targetdir="dir#4"/&gt;
 *         etc...
 *         &lt;present targetdir="dir#N"/&gt;
 *       &lt;/or&gt;
 *     &lt;/and&gt;
 *     etc...
 *     &lt;and&gt;
 *       &lt;present targetdir="dir#N-1"/&gt;
 *       &lt;or&gt;
 *         &lt;present targetdir="dir#N"/&gt;
 *       &lt;/or&gt;
 *     &lt;/and&gt;
 *   &lt;/or&gt;
 * </pre>
 */
public class MultiPresentSelector
             extends AbstractCompositeSelector {

    /** [EMAIL PROTECTED] */
    protected FileSelector configure(Parameter[] params) {
        String path = null;
        String suffix = "";

        for (int i = 0; i < params.length; ++i) {
            Parameter param = params[i];
            if (param.getName().equals("path")) {
                path = param.getValue();
            }
            else if (param.getName().equals("suffix")) {
                suffix = param.getValue();
            }
            else {
                throw new BuildException("Unknown param: " + param.getName());
            }
        }

        if (path == null) {
            throw new BuildException("Unset required param: path");
        }

        File[] files = getFiles(path, suffix);
        if (files.length < 2) {
            throw new BuildException("Empty selector");
        }

        OrSelector or = new OrSelector();
        for (int i = 0; i < files.length - 1; ++i) {
            AndSelector and = new AndSelector();
            PresentSelector present = new PresentSelector();
            present.setTargetdir(files[i]);
            and.appendSelector(present);
            OrSelector or2 = new OrSelector();
            for (int j = i+1; j < files.length; ++j) {
                PresentSelector present2 = new PresentSelector();
                present2.setTargetdir(files[j]);
                or2.appendSelector(present2);
            }
            and.appendSelector(or2);
            or.appendSelector(and);
        }

        return or;
    }

    private File[] getFiles(String path, String suffix) {
        List files = new ArrayList(32);
        StringTokenizer st = new StringTokenizer(path, File.pathSeparator);
        while (st.hasMoreTokens()) {
            File file = new File(st.nextToken() + suffix);
            if (file.isDirectory()) {
                files.add(file);
            }
        }
        return (File[])files.toArray(new File[0]);
    }

}


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to