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
017package org.jetbrains.jet.lang.resolve.calls.results;
018
019import org.jetbrains.annotations.NotNull;
020import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
021import org.jetbrains.jet.lang.resolve.DelegatingBindingTrace;
022import org.jetbrains.jet.lang.resolve.calls.model.ResolvedCallWithTrace;
023
024import java.util.Collection;
025import java.util.Collections;
026
027public class OverloadResolutionResultsImpl<D extends CallableDescriptor> implements OverloadResolutionResults<D> {
028
029    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> success(@NotNull ResolvedCallWithTrace<D> candidate) {
030        return new OverloadResolutionResultsImpl<D>(Code.SUCCESS, Collections.singleton(candidate));
031    }
032
033    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> nameNotFound() {
034        return new OverloadResolutionResultsImpl<D>(Code.NAME_NOT_FOUND, Collections.<ResolvedCallWithTrace<D>>emptyList());
035    }
036
037    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> singleFailedCandidate(ResolvedCallWithTrace<D> candidate) {
038        return new OverloadResolutionResultsImpl<D>(Code.SINGLE_CANDIDATE_ARGUMENT_MISMATCH, Collections.singleton(candidate));
039    }
040    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> manyFailedCandidates(Collection<ResolvedCallWithTrace<D>> failedCandidates) {
041        return new OverloadResolutionResultsImpl<D>(Code.MANY_FAILED_CANDIDATES, failedCandidates);
042    }
043
044    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> candidatesWithWrongReceiver(Collection<ResolvedCallWithTrace<D>> failedCandidates) {
045        return new OverloadResolutionResultsImpl<D>(Code.CANDIDATES_WITH_WRONG_RECEIVER, failedCandidates);
046    }
047
048    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> ambiguity(Collection<ResolvedCallWithTrace<D>> candidates) {
049        return new OverloadResolutionResultsImpl<D>(Code.AMBIGUITY, candidates);
050    }
051
052    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> incompleteTypeInference(Collection<ResolvedCallWithTrace<D>> candidates) {
053        return new OverloadResolutionResultsImpl<D>(Code.INCOMPLETE_TYPE_INFERENCE, candidates);
054    }
055
056    public static <D extends CallableDescriptor> OverloadResolutionResultsImpl<D> incompleteTypeInference(ResolvedCallWithTrace<D> candidate) {
057        return incompleteTypeInference(Collections.singleton(candidate));
058    }
059
060    private final Collection<ResolvedCallWithTrace<D>> results;
061    private final Code resultCode;
062    private DelegatingBindingTrace trace;
063
064    private OverloadResolutionResultsImpl(@NotNull Code resultCode, @NotNull Collection<ResolvedCallWithTrace<D>> results) {
065        this.results = results;
066        this.resultCode = resultCode;
067    }
068
069    @Override
070    @NotNull
071    public Collection<ResolvedCallWithTrace<D>> getResultingCalls() {
072        return results;
073    }
074
075    @Override
076    @NotNull
077    public ResolvedCallWithTrace<D> getResultingCall() {
078        assert isSingleResult();
079        return results.iterator().next();
080    }
081
082    @NotNull
083    @Override
084    public D getResultingDescriptor() {
085        return getResultingCall().getResultingDescriptor();
086    }
087
088    @Override
089    @NotNull
090    public Code getResultCode() {
091        return resultCode;
092    }
093
094    @Override
095    public boolean isSuccess() {
096        return resultCode.isSuccess();
097    }
098
099    @Override
100    public boolean isSingleResult() {
101        return results.size() == 1 && getResultCode() != Code.CANDIDATES_WITH_WRONG_RECEIVER;
102    }
103
104    @Override
105    public boolean isNothing() {
106        return resultCode == Code.NAME_NOT_FOUND;
107    }
108
109    @Override
110    public boolean isAmbiguity() {
111        return resultCode == Code.AMBIGUITY;
112    }
113
114    @Override
115    public boolean isIncomplete() {
116        return resultCode == Code.INCOMPLETE_TYPE_INFERENCE;
117    }
118
119    //
120//    public OverloadResolutionResultsImpl<D> newContents(@NotNull Collection<D> functionDescriptors) {
121//        return new OverloadResolutionResultsImpl<D>(resultCode, functionDescriptors);
122//    }
123
124    public DelegatingBindingTrace getTrace() {
125        return trace;
126    }
127
128    public OverloadResolutionResultsImpl<D> setTrace(DelegatingBindingTrace trace) {
129        this.trace = trace;
130        return this;
131    }
132}