/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.drill.common.expression;

import java.util.Iterator;
import java.util.List;
import java.util.Set;

import org.apache.drill.common.expression.visitors.ExprVisitor;
import org.apache.drill.common.types.TypeProtos.DataMode;
import org.apache.drill.common.types.TypeProtos.MajorType;
import org.apache.drill.common.types.TypeProtos.MinorType;
import org.apache.drill.common.types.Types;
import com.google.common.base.Preconditions;
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;

public class IfExpression extends LogicalExpressionBase {

  public final IfCondition ifCondition;
  public final LogicalExpression elseExpression;
  public final MajorType outputType;

  private IfExpression(ExpressionPosition pos, IfCondition conditions, LogicalExpression elseExpression, MajorType outputType) {
    super(pos);
    this.ifCondition = conditions;
    this.elseExpression = elseExpression;
    this.outputType = outputType;
  }

  public static class IfCondition{
    public final LogicalExpression condition;
    public final LogicalExpression expression;

    public IfCondition(LogicalExpression condition, LogicalExpression expression) {
      //logger.debug("Generating IfCondition {}, {}", condition, expression);

      this.condition = condition;
      this.expression = expression;
    }
  }

  @Override
  public <T, V, E extends Exception> T accept(ExprVisitor<T, V, E> visitor, V value) throws E {
    return visitor.visitIfExpression(this, value);
  }

  public static class Builder {
    IfCondition conditions;
    private LogicalExpression elseExpression;
    private ExpressionPosition pos = ExpressionPosition.UNKNOWN;
    private MajorType outputType;

    public Builder setPosition(ExpressionPosition pos) {
      this.pos = pos;
      return this;
    }

    public Builder setElse(LogicalExpression elseExpression) {
      this.elseExpression = elseExpression;
      return this;
    }

    public Builder setIfCondition(IfCondition conditions) {
      this.conditions = conditions;
      return this;
    }

    public Builder setOutputType(MajorType outputType) {
      this.outputType = outputType;
      return this;
    }

    public IfExpression build(){
      Preconditions.checkNotNull(pos);
      Preconditions.checkNotNull(conditions);
      return new IfExpression(pos, conditions, elseExpression, outputType);
    }
  }

  @Override
  public MajorType getMajorType() {
    if (outputType != null) {
      return outputType;
    }

    MajorType elseType = elseExpression.getMajorType();
    MajorType ifType = ifCondition.expression.getMajorType();
    if (elseType.getMinorType() == MinorType.UNION) {
      Set<MinorType> subtypes = Sets.newHashSet();
      for (MinorType subtype : elseType.getSubTypeList()) {
        subtypes.add(subtype);
      }
      for (MinorType subtype : ifType.getSubTypeList()) {
        subtypes.add(subtype);
      }
      MajorType.Builder builder = MajorType.newBuilder().setMinorType(MinorType.UNION).setMode(DataMode.OPTIONAL);
      for (MinorType subtype : subtypes) {
        builder.addSubType(subtype);
      }
      return builder.build();
    }

    MajorType.Builder builder = MajorType.newBuilder().setMinorType(ifType.getMinorType());
    builder.setMode(elseType.getMode() == DataMode.OPTIONAL || ifType.getMode() == DataMode.OPTIONAL ? DataMode.OPTIONAL : elseType.getMode());
    builder = Types.calculateTypePrecisionAndScale(ifType, elseType, builder);
    return builder.build();
  }

  public static Builder newBuilder() {
    return new Builder();
  }

  @Override
  public Iterator<LogicalExpression> iterator() {
    List<LogicalExpression> children = Lists.newLinkedList();

    children.add(ifCondition.condition);
    children.add(ifCondition.expression);
    children.add(this.elseExpression);
    return children.iterator();
  }

  @Override
  public int getCumulativeCost() {
    // return the average cost of operands for a boolean "and" | "or"
    int cost = this.getSelfCost();

    int i = 0;
    for (LogicalExpression e : this) {
      cost += e.getCumulativeCost();
      i++;
    }

    return cost / i;
  }
}
