package de.renew.formalism.fs;

import de.renew.simulatorontology.shadow.ShadowNetElement;


/**
 * Represents an "is-a" relationship between two shadow concepts in a shadow Petri net.
 * <p>
 * The source concept is a subconcept of the target concept.
 * This class supports optional disjunctive inheritance.
 */
public class ShadowIsa extends ShadowNetElement {

    /**
     * The source concept of this "is-a" relationship.
     */
    private ShadowConcept _from;

    /**
     * The target concept of this "is-a" relationship.
     */
    private ShadowConcept _to;

    /**
     * Flag indicating whether this "is-a" relationship is disjunctive.
     */
    private boolean _isDisjunctive;


    /**
     * Creates an "is-a" relationship from the source concept to the target concept
     * with non-disjunctive inheritance.
     *
     * @param from the source concept
     * @param to the target concept
     */
    public ShadowIsa(ShadowConcept from, ShadowConcept to) {
        this(from, to, false);
    }

    /**
     * Creates an "is-a" relationship from the source concept to the target concept.
     * <p>
     * The association can optionally be marked as disjunctive.
     *
     * @param from the source concept
     * @param to the target concept
     * @param isDisjunctive {@code true} if this is a disjunctive inheritance, {@code false} otherwise
     */
    public ShadowIsa(ShadowConcept from, ShadowConcept to, boolean isDisjunctive) {
        super(from.getNet());
        this._from = from;
        this._to = to;
        this._isDisjunctive = isDisjunctive;
        from.add(this);
    }

    /**
     * Returns the source concept of this "is-a" relationship.
     *
     * @return the {@link ShadowConcept} that is the source of this inheritance
     */
    public ShadowConcept getSource() {
        return _from;
    }

    /**
     * Returns the target concept of this "is-a" relationship.
     *
     * @return the {@link ShadowConcept} that is the target of this inheritance
     */
    public ShadowConcept getTarget() {
        return _to;
    }

    /**
     * Indicates whether this "is-a" relationship is disjunctive.
     *
     * @return {@code true} if the inheritance is disjunctive, {@code false} otherwise
     */
    public boolean isDisjunctive() {
        return _isDisjunctive;
    }


    /**
     * Deserialization method, behaves like default readObject
     * method, additionally re-registers the Isa at its
     * <code>from</code> concept.
     *
     * @param in the input stream to read the object from
     * @throws java.io.IOException if an I/O error occurs
     * @throws ClassNotFoundException if a class cannot be found during deserialization
     */
    private void readObject(java.io.ObjectInputStream in)
        throws java.io.IOException, ClassNotFoundException
    {
        in.defaultReadObject();
        _from.add(this);
    }
}