Skip to content

Commit

Permalink
Show aliased functions in the -h output.
Browse files Browse the repository at this point in the history
This pull request closes #68 by showing aliased functions specially
in the output of yal when running with "-h".

For example:

```
$ ./yal  -h hms
hms
===
hms is an alias for time:hms.

time:hms
========
Return the current time as a string, formatted as 'HH:MM:SS'.

zero-pad-single-number (num:number)
===================================
Return the given number, padded to two digits, as a string.
i.e. Add a '0' prefix to the specified number, for values less than ten.

This is designed to pad the hours, minutes, and seconds in (hms).

```

When called via `(help)` everything works as-is, so there is no
mention of the alias when this code runs:

```
(print (help hms))
```

(Because we don't have access to the name, to lookup the function,
we just the result, when our arguments are expanded.)
  • Loading branch information
skx committed Oct 28, 2022
1 parent 78bdd79 commit 63070d1
Show file tree
Hide file tree
Showing 2 changed files with 28 additions and 5 deletions.
23 changes: 18 additions & 5 deletions eval/eval.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,11 @@ type Eval struct {
// Recurse keeps track of how many times we've recursed
recurse int

// Symbols contains our (interned) symbol table
// Symbols contains our (interned) symbol atom
symbols map[string]primitive.Primitive

// aliases contains any record of aliased functionality
aliases map[string]string
}

// New constructs a new evaluator.
Expand Down Expand Up @@ -74,6 +77,9 @@ func New(src string) *Eval {
e.symbols["#\\\\r"] = primitive.Character("\r")
e.symbols["#\\\\t"] = primitive.Character("\t")

// Record aliases here
e.aliases = make(map[string]string)

// tokenize our input program into a series of terms
e.tokenize(src)

Expand All @@ -88,6 +94,11 @@ func (ev *Eval) SetContext(ctx context.Context) {
ev.context = ctx
}

// Aliased returns records of anything that has been aliased with "(alias ..)"
func (ev *Eval) Aliased() map[string]string {
return ev.aliases
}

// tokenize splits the input string into tokens, via a horrific regular
// expression which I don't understand!
func (ev *Eval) tokenize(str string) {
Expand Down Expand Up @@ -586,12 +597,14 @@ func (ev *Eval) eval(exp primitive.Primitive, e *env.Environment, expandMacro bo
for i := 0; i < len(args); i += 2 {

// The key/val pair we're working with
key := args[i]
val := args[i+1]
new := args[i]
orig := args[i+1]

old, ok := e.Get(val.ToString())
old, ok := e.Get(orig.ToString())
if ok {
e.Set(key.ToString(), old)
e.Set(new.ToString(), old)

ev.aliases[new.ToString()] = orig.ToString()
}
}
return primitive.Nil{}
Expand Down
10 changes: 10 additions & 0 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,9 @@ func main() {
// We can only get help for functions which are present.
interpreter.Evaluate(environment)

// Show aliased functions, separately
aliased := interpreter.Aliased()

// Build up a list of all things known in the environment
keys := []string{}

Expand Down Expand Up @@ -143,6 +146,13 @@ func main() {
// Get the text
txt := prc.Help

// Is this an aliased function?
target, ok := aliased[key]
if ok {

txt = fmt.Sprintf("%s is an alias for %s.", key, target)
}

// Build up the arguments
args := ""

Expand Down

0 comments on commit 63070d1

Please sign in to comment.