2021-05-14 17:41:01 +02:00
|
|
|
package formulae
|
|
|
|
|
|
|
|
import (
|
|
|
|
"fmt"
|
|
|
|
"strings"
|
|
|
|
)
|
|
|
|
|
|
|
|
/* ---------------------------------------------------------------- *
|
|
|
|
* TYPE Formula
|
|
|
|
* ---------------------------------------------------------------- */
|
|
|
|
|
|
|
|
type Formula struct {
|
|
|
|
kind string
|
|
|
|
expr string
|
|
|
|
valence int
|
|
|
|
subformulae [](*Formula)
|
|
|
|
}
|
|
|
|
|
|
|
|
/* ---------------------------------------------------------------- *
|
|
|
|
* METHODS
|
|
|
|
* ---------------------------------------------------------------- */
|
|
|
|
|
|
|
|
func (fml *Formula) SetKind(kind string) { fml.kind = kind }
|
|
|
|
|
|
|
|
func (fml Formula) GetKind() string { return fml.kind }
|
|
|
|
|
|
|
|
func (fml *Formula) SetExpr(expr string) { fml.expr = expr }
|
|
|
|
|
|
|
|
func (fml Formula) GetExpr() string { return fml.expr }
|
|
|
|
|
2021-05-14 19:23:53 +02:00
|
|
|
func (fml *Formula) SetSubformulae(subfmls [](*Formula)) {
|
|
|
|
fml.subformulae = subfmls
|
|
|
|
fml.valence = len(subfmls)
|
2021-05-14 17:41:01 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) GetSubFormulae() []Formula {
|
|
|
|
var n int = fml.valence
|
2021-05-14 19:23:53 +02:00
|
|
|
var subfmls = make([]Formula, n)
|
2021-05-14 17:41:01 +02:00
|
|
|
for i, subfml := range fml.subformulae {
|
2021-05-14 19:23:53 +02:00
|
|
|
subfmls[i] = *subfml
|
2021-05-14 17:41:01 +02:00
|
|
|
}
|
2021-05-14 19:23:53 +02:00
|
|
|
return subfmls
|
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) GetAllSubFormulae() []Formula {
|
|
|
|
var subfml = fml.GetSubFormulae()
|
|
|
|
var result = []Formula{fml.Copy()}
|
|
|
|
for _, child := range subfml {
|
|
|
|
result = append(result, child.GetAllSubFormulae()...)
|
|
|
|
}
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) GetAllSubFormulaeStrict() []Formula {
|
|
|
|
var subfml = fml.GetSubFormulae()
|
|
|
|
var result = []Formula{}
|
|
|
|
for _, child := range subfml {
|
|
|
|
result = append(result, child.GetAllSubFormulae()...)
|
|
|
|
}
|
|
|
|
return result
|
2021-05-14 17:41:01 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) GetChild(indexOpt ...int) Formula {
|
|
|
|
var index int = 0
|
|
|
|
if len(indexOpt) > 0 {
|
|
|
|
index = indexOpt[0]
|
|
|
|
}
|
|
|
|
var subfml Formula
|
|
|
|
if 0 <= index && index < fml.valence {
|
|
|
|
subfml = *(fml.subformulae[index])
|
|
|
|
} else {
|
|
|
|
panic(fmt.Sprintf("Instance has no child of index %d !", index))
|
|
|
|
}
|
|
|
|
return subfml
|
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) Pretty(preindentOpt ...string) string {
|
|
|
|
var preindent string = ""
|
|
|
|
if len(preindentOpt) > 0 {
|
|
|
|
preindent = preindentOpt[0]
|
|
|
|
}
|
|
|
|
return fml.pretty(preindent, " ", "", 0)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (fml Formula) pretty(preindent string, tab string, prepend string, depth int) string {
|
|
|
|
var indent string = preindent + strings.Repeat(tab, depth)
|
|
|
|
switch fml.valence {
|
|
|
|
case 0:
|
|
|
|
switch kind := fml.kind; kind {
|
|
|
|
case "atom", "generic":
|
|
|
|
return indent + prepend + kind + " " + fml.expr
|
|
|
|
default:
|
|
|
|
return indent + prepend + kind
|
|
|
|
}
|
|
|
|
default:
|
|
|
|
var lines string = indent + prepend + fml.kind
|
|
|
|
prepend = "|__ "
|
|
|
|
for _, subfml := range fml.subformulae {
|
|
|
|
lines += "\n" + subfml.pretty(preindent, tab, prepend, depth+1)
|
|
|
|
}
|
|
|
|
return lines
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2021-05-14 19:23:53 +02:00
|
|
|
// shallow copy
|
|
|
|
func (fml Formula) Copy() Formula {
|
|
|
|
return Formula{
|
|
|
|
expr: fml.expr,
|
|
|
|
kind: fml.kind,
|
|
|
|
valence: fml.valence,
|
|
|
|
subformulae: fml.subformulae,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2021-05-14 17:41:01 +02:00
|
|
|
func (fml Formula) Deepcopy() Formula {
|
2021-05-14 19:23:53 +02:00
|
|
|
var subfmls = make([](*Formula), len(fml.subformulae))
|
|
|
|
for i, subfml := range fml.subformulae {
|
|
|
|
subfmlCopy := subfml.Deepcopy()
|
|
|
|
subfmls[i] = &subfmlCopy
|
2021-05-14 17:41:01 +02:00
|
|
|
}
|
|
|
|
return Formula{
|
|
|
|
expr: fml.expr,
|
|
|
|
kind: fml.kind,
|
|
|
|
valence: fml.valence,
|
2021-05-14 19:23:53 +02:00
|
|
|
subformulae: subfmls,
|
2021-05-14 17:41:01 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ *
|
|
|
|
* METHODS: Recognition of Formula-Types
|
|
|
|
* ---------------------------------------------------------------- */
|
|
|
|
|
|
|
|
func (fml Formula) IsIrreducible() bool { return fml.valence == 0 }
|
|
|
|
func (fml Formula) IsAtom() bool { return fml.kind == "atom" }
|
|
|
|
func (fml Formula) IsPositiveLiteral() bool { return fml.IsAtom() }
|
|
|
|
func (fml Formula) IsNegativeLiteral() bool { return fml.IsNegation() && fml.GetChild().IsAtom() }
|
|
|
|
func (fml Formula) IsLiteral() bool { return fml.IsPositiveLiteral() || fml.IsNegativeLiteral() }
|
|
|
|
func (fml Formula) IsGeneric() bool { return fml.kind == "generic" }
|
|
|
|
func (fml Formula) IsTautologySymbol() bool { return fml.kind == "taut" }
|
|
|
|
func (fml Formula) IsContradictionSymbol() bool { return fml.kind == "contradiction" }
|
|
|
|
func (fml Formula) IsConnective() bool { return fml.valence > 0 }
|
|
|
|
func (fml Formula) IsNegation() bool { return fml.kind == "not" }
|
|
|
|
func (fml Formula) IsConjunction2() bool { return fml.kind == "and2" }
|
|
|
|
func (fml Formula) IsConjunction() bool { return fml.kind == "and" || fml.kind == "and2" }
|
|
|
|
func (fml Formula) IsDisjunction2() bool { return fml.kind == "or2" }
|
|
|
|
func (fml Formula) IsDisjunction() bool { return fml.kind == "or" || fml.kind == "or2" }
|
|
|
|
func (fml Formula) IsImplication() bool { return fml.kind == "implies" }
|
2021-05-15 00:05:03 +02:00
|
|
|
func (fml Formula) IsDoubleImplication() bool { return fml.kind == "iff" }
|