1/*
2 * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26package com.sun.xml.internal.xsom.impl.scd;
27
28import com.sun.xml.internal.xsom.SCD;
29import com.sun.xml.internal.xsom.XSComponent;
30
31import java.util.Iterator;
32
33/**
34 * Schema component designator.
35 *
36 * @author Kohsuke Kawaguchi
37 */
38public final class SCDImpl extends SCD {
39    /**
40     * SCD is fundamentally a list of steps.
41     */
42    private final Step[] steps;
43
44    /**
45     * The original textual SCD representation.
46     */
47    private final String text;
48
49    public SCDImpl(String text, Step[] steps) {
50        this.text = text;
51        this.steps = steps;
52    }
53
54    public Iterator<XSComponent> select(Iterator<? extends XSComponent> contextNode) {
55        Iterator<XSComponent> nodeSet = (Iterator)contextNode;
56
57        int len = steps.length;
58        for( int i=0; i<len; i++ ) {
59            if(i!=0 && i!=len-1 && !steps[i-1].axis.isModelGroup() && steps[i].axis.isModelGroup()) {
60                // expand the current nodeset by adding abbreviatable complex type and model groups.
61                // note that such expansion is not allowed to occure in in between model group axes.
62
63                // TODO: this step is not needed if the next step is known not to react to
64                // complex type nor model groups, such as, say Axis.FACET
65                nodeSet = new Iterators.Unique<XSComponent>(
66                    new Iterators.Map<XSComponent,XSComponent>(nodeSet) {
67                        protected Iterator<XSComponent> apply(XSComponent u) {
68                            return new Iterators.Union<XSComponent>(
69                                Iterators.singleton(u),
70                                Axis.INTERMEDIATE_SKIP.iterator(u) );
71                        }
72                    }
73                );
74            }
75            nodeSet = steps[i].evaluate(nodeSet);
76        }
77
78        return nodeSet;
79    }
80
81    public String toString() {
82        return text;
83    }
84}
85