001    /*
002     * Copyright 2010-2013 JetBrains s.r.o.
003     *
004     * Licensed under the Apache License, Version 2.0 (the "License");
005     * you may not use this file except in compliance with the License.
006     * You may obtain a copy of the License at
007     *
008     * http://www.apache.org/licenses/LICENSE-2.0
009     *
010     * Unless required by applicable law or agreed to in writing, software
011     * distributed under the License is distributed on an "AS IS" BASIS,
012     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013     * See the License for the specific language governing permissions and
014     * limitations under the License.
015     */
016    
017    package org.jetbrains.jet.lang.types;
018    
019    
020    import com.google.common.collect.Sets;
021    import org.jetbrains.annotations.NotNull;
022    import org.jetbrains.jet.lang.descriptors.ClassifierDescriptor;
023    import org.jetbrains.jet.lang.descriptors.TypeParameterDescriptor;
024    import org.jetbrains.jet.lang.descriptors.annotations.AnnotatedImpl;
025    import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor;
026    
027    import java.util.*;
028    
029    public class IntersectionTypeConstructor extends AnnotatedImpl implements TypeConstructor {
030        private final Set<JetType> intersectedTypes;
031        private final int hashCode;
032    
033        public IntersectionTypeConstructor(List<AnnotationDescriptor> annotations, Collection<JetType> typesToIntersect) {
034            super(annotations);
035            this.intersectedTypes = Sets.newLinkedHashSet(typesToIntersect);
036            this.hashCode = intersectedTypes.hashCode();
037        }
038    
039        @NotNull
040        @Override
041        public List<TypeParameterDescriptor> getParameters() {
042            return Collections.emptyList();
043        }
044    
045        @NotNull
046        @Override
047        public Collection<JetType> getSupertypes() {
048            return intersectedTypes;
049        }
050    
051        @Override
052        public boolean isSealed() {
053            return false;
054        }
055    
056        @Override
057        public ClassifierDescriptor getDeclarationDescriptor() {
058            return null;
059        }
060    
061        @Override
062        public String toString() {
063            return makeDebugNameForIntersectionType(intersectedTypes);
064        }
065    
066        private static String makeDebugNameForIntersectionType(Iterable<JetType> resultingTypes) {
067            StringBuilder debugName = new StringBuilder("{");
068            for (Iterator<JetType> iterator = resultingTypes.iterator(); iterator.hasNext(); ) {
069                JetType type = iterator.next();
070    
071                debugName.append(type.toString());
072                if (iterator.hasNext()) {
073                    debugName.append(" & ");
074                }
075            }
076            debugName.append("}");
077            return debugName.toString();
078        }
079    
080        @Override
081        public boolean equals(Object o) {
082            if (this == o) return true;
083            if (o == null || getClass() != o.getClass()) return false;
084    
085            IntersectionTypeConstructor that = (IntersectionTypeConstructor) o;
086    
087            if (intersectedTypes != null ? !intersectedTypes.equals(that.intersectedTypes) : that.intersectedTypes != null) return false;
088    
089            return true;
090        }
091    
092        @Override
093        public int hashCode() {
094            return hashCode;
095        }
096    
097    }