Operand.java
package Hoot.Runtime.Values;
import Hoot.Runtime.Faces.Named;
import Hoot.Runtime.Faces.Selector;
import Hoot.Runtime.Faces.Resulting;
import Hoot.Runtime.Names.TypeName;
import Hoot.Runtime.Emissions.Item;
import Hoot.Runtime.Emissions.Emission;
import static Hoot.Runtime.Behaviors.HootRegistry.*;
import Hoot.Runtime.Emissions.NamedItem;
/**
* An operand. Many methods get overridden by subclasses.
*
* @author nik <nikboyd@sonic.net>
* @see "Copyright 2010,2021 Nikolas S Boyd."
* @see "Permission is granted to copy this work provided this copyright statement is retained in all copies."
*/
public abstract class Operand extends NamedItem implements Resulting {
protected Operand(Item container) { super(container); }
protected Operand(NamedItem container) { super(container); }
public Operand cleanTerm() { this.clean(); return this; }
public Operand makeAssigned() { return this; }
protected boolean isResult = false;
public Operand makeResult() { this.isResult = true; return this; }
@Override public boolean isResult() { return this.isResult; }
public boolean hasCascades() { return false; }
public boolean hasOnlyValue() { return false; }
@Override public boolean isFramed() { return false; }
public boolean isLiteral() { return false; }
public boolean isConstruct() { return false; }
public boolean isMessage() { return false; }
public boolean isNest() { return false; }
// public boolean isReference() { return false; }
public boolean producesPredicate() { return false; }
public boolean throwsException() { return false; }
public boolean needsStatement() { return true; }
public boolean refersToMetaclass() { return false; }
public boolean receiverNeedsTerm() { return false; }
public boolean selfIsPrimary() { return false; }
public Named asReference() { return (Named)this; }
public TypeName typeResolver() { return RootType(); }
public Class resolvedType() { return RootClass(); }
public String resolvedTypeName() { return typeResolver().fullName(); }
public boolean resolvesToPrimitive() { return typeResolver().isPrimitiveType(); }
/**
* @return whether the receiver consumes an (operand)
* @param operand a potentially consumable operand
*/
public boolean consumes(Operand operand) { return false; }
/**
* @return whether a (selector) can be optimized against this operand
* @param selector a method selector
*/
public boolean optimizes(Selector selector) {
if (selector.isOptimized()) return true;
TypeName resolver = typeResolver();
if (RootType().matches(resolver)) return false;
if (BehaviorType().matches(resolver)) return false;
return true; }
@Override public Emission emitItem() { return emitOperand(); }
@Override public Emission emitOptimized() { return emitOperand(); }
@Override public Emission emitPrimitive() { return emitOperand(); }
public Emission emitTerm() { return emitTerm(emitOperand()); }
public Emission emitResult() { return emitResult(emitItem("Object"), emitOperand()); }
public Emission emitOperand() { return emitEmpty(); } // override this!
public Emission emitStatement() { return emitStatement(emitOperand()); }
public Emission emitBooleanTerm() { return emitCast(BooleanType().fullName(), emitOperand()); }
public Emission emitReceiver() { return (receiverNeedsTerm()) ? emitTerm() : emitOperand(); }
} // Operand