mirror of
https://github.com/ProgramSnail/Lama.git
synced 2025-12-07 23:38:47 +00:00
Better eq
This commit is contained in:
parent
c3671a0a38
commit
f6d4a475b4
4 changed files with 51 additions and 21 deletions
|
|
@ -48,3 +48,4 @@ F,disableGC;
|
||||||
F,random;
|
F,random;
|
||||||
F,time;
|
F,time;
|
||||||
F,rawTag;
|
F,rawTag;
|
||||||
|
F,compareTags;
|
||||||
|
|
|
||||||
|
|
@ -67,6 +67,7 @@ void __post_gc_subst () {}
|
||||||
# define ARRAY_TAG 0x00000003
|
# define ARRAY_TAG 0x00000003
|
||||||
# define SEXP_TAG 0x00000005
|
# define SEXP_TAG 0x00000005
|
||||||
# define CLOSURE_TAG 0x00000007
|
# define CLOSURE_TAG 0x00000007
|
||||||
|
# define UNBOXED_TAG 0x00000009 // Not actually a tag; used to return from LrawTag
|
||||||
|
|
||||||
# define LEN(x) ((x & 0xFFFFFFF8) >> 3)
|
# define LEN(x) ((x & 0xFFFFFFF8) >> 3)
|
||||||
# define TAG(x) (x & 0x00000007)
|
# define TAG(x) (x & 0x00000007)
|
||||||
|
|
@ -175,11 +176,34 @@ void *global_sysargs;
|
||||||
|
|
||||||
// Gets a raw tag
|
// Gets a raw tag
|
||||||
extern int LrawTag (void *p) {
|
extern int LrawTag (void *p) {
|
||||||
ASSERT_UNBOXED ("rawTag, 0", p);
|
if (UNBOXED(p)) return UNBOXED_TAG;
|
||||||
|
|
||||||
return TAG(TO_DATA(p)->tag);
|
return TAG(TO_DATA(p)->tag);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Compare sexprs tags
|
||||||
|
extern int LcompareTags (void *p, void *q) {
|
||||||
|
data *pd, *qd;
|
||||||
|
|
||||||
|
ASSERT_BOXED ("compareTags, 0", p);
|
||||||
|
ASSERT_BOXED ("compareTags, 1", q);
|
||||||
|
|
||||||
|
pd = TO_DATA(p);
|
||||||
|
qd = TO_DATA(q);
|
||||||
|
|
||||||
|
if (TAG(pd->tag) == SEXP_TAG && TAG(qd->tag) == SEXP_TAG) {
|
||||||
|
return
|
||||||
|
#ifndef DEBUG_PRINT
|
||||||
|
(TO_SEXP(p)->tag) - (TO_SEXP(q)->tag);
|
||||||
|
#else
|
||||||
|
(GET_SEXP_TAG(TO_SEXP(p)->tag)) - (GET_SEXP_TAG(TO_SEXP(p)->tag));
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else failure ("not a sexpr in compareTags: %d, %d\n", TAG(pd->tag), TAG(qd->tag));
|
||||||
|
|
||||||
|
return 0; // never happens
|
||||||
|
}
|
||||||
|
|
||||||
// Functional synonym for built-in operator ":";
|
// Functional synonym for built-in operator ":";
|
||||||
void* Ls__Infix_58 (void *p, void *q) {
|
void* Ls__Infix_58 (void *p, void *q) {
|
||||||
void *res;
|
void *res;
|
||||||
|
|
|
||||||
|
|
@ -1 +1 @@
|
||||||
let version = "Version 1.00, c29ab4901, Sun Aug 2 23:56:21 2020 +0300"
|
let version = "Version 1.00, c3671a0a3, Tue Aug 4 15:11:14 2020 +0300"
|
||||||
|
|
|
||||||
|
|
@ -47,29 +47,34 @@ fun eq (x, y) {
|
||||||
fi
|
fi
|
||||||
esac
|
esac
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun eqargs (x, y, from) {
|
||||||
|
local continue = true;
|
||||||
|
|
||||||
|
if x.length != y.length
|
||||||
|
then false
|
||||||
|
else
|
||||||
|
for local i = from;, i<x.length && continue, i := i + 1 do
|
||||||
|
continue := eqrec (x[i], y[i])
|
||||||
|
od;
|
||||||
|
|
||||||
|
continue
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
fun eqrec (x, y) {
|
fun eqrec (x, y) {
|
||||||
if alreadyEq (x, y)
|
if alreadyEq (x, y)
|
||||||
then true
|
then true
|
||||||
else
|
else
|
||||||
case [x, y] of
|
if rawTag (x) != rawTag (y) then false
|
||||||
[#array, #array] ->
|
else
|
||||||
if x.length == y.length
|
case x of
|
||||||
then
|
#array -> eqargs (x, y, 0)
|
||||||
local continue = true;
|
| #fun -> if x[0] == y[0] then eqargs (x, y, 1) else false fi
|
||||||
|
| #sexp -> if compareTags (x, y) == 0 then eqargs (x, y, 0) else false fi
|
||||||
for local i = 0;, i<x.length && continue, i := i + 1 do
|
| _ -> compare (x, y) == 0
|
||||||
continue := eqrec (x[i], y[i])
|
esac
|
||||||
od;
|
fi
|
||||||
continue
|
|
||||||
else false
|
|
||||||
fi
|
|
||||||
| [#unboxed, #unboxed] -> x == y
|
|
||||||
| [#string, #string] -> compare (x, y) == 0
|
|
||||||
| [#unboxed, #array] -> false
|
|
||||||
| [#array, #unboxed] -> false
|
|
||||||
| _ -> failure ("eq not supported: %s, %s", x.string, y.string)
|
|
||||||
esac
|
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue