This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2021-07-07
Channels
- # announcements (1)
- # babashka (31)
- # beginners (54)
- # biff (3)
- # calva (22)
- # cider (13)
- # circleci (1)
- # clj-kondo (6)
- # cljsrn (2)
- # clojure (113)
- # clojure-europe (58)
- # clojure-mexico (5)
- # clojure-nl (3)
- # clojure-uk (7)
- # clojurescript (81)
- # cursive (20)
- # datomic (33)
- # events (3)
- # fulcro (29)
- # introduce-yourself (1)
- # meander (78)
- # off-topic (60)
- # om-next (2)
- # podcasts-discuss (1)
- # re-frame (8)
- # reagent (5)
- # reitit (20)
- # remote-jobs (1)
- # shadow-cljs (24)
- # spacemacs (10)
- # sql (8)
- # tools-deps (22)
- # xtdb (16)
Not a problem. I wouldn’t want anyone to suffer fixing it anyway because IIRC the way the dissoc is put there is a bit of a hack.
I’m pretty sure the problem is due to meander.match.syntax.epsilon/expand-map
. This function tries to rewrite the :map
node such that certain keys are prioritized, :as
is desugared, etc.
{:a ?x}
should not cause a dissoc
to be compiled but {:a ?x & ?rest}
definitely should.
it seems not, because after adding the print inside meander.match.syntax.epsilon/expand-map
nothing happens :thinking_face:
Line 726 of meander.match.epsilon
rest-rhs (r.ir/op-bind rest_target (r.ir/op-eval `(dissoc ~target ~@local-literal-key-codes))
rest-ir)
Seems like I can get rid of the dissoc by changing that line to check if the :rest-map
is set.
(let [x {:a 1}]
(m/match x
{:a ?x, :b ?y, :c ?z}
?x))
;; =>
(let*
[R__12612
(let*
[T__12607 x]
(if (map? T__12607)
(let* [T__12610 (. T__12607 valAt :c)
T__12609 (. T__12607 valAt :b)
T__12608 (. T__12607 valAt :a)]
(let* [?x T__12608]
(let* [?y T__12609] (let* [?z T__12610] ?x))))
meander.match.runtime.epsilon/FAIL))]
(if (meander.match.runtime.epsilon/fail? R__12612)
(throw (ex-info "non exhaustive pattern match" {}))
R__12612))
No dissoc.I'm trying to catch up with datascript speed with my naive implementation of datalog using meander
Yeah, lemme think about it for a moment. I doubt it would break anyone to make this is the implementation of unsafe
.
I did because I was under the impression that using get
without type checks was “fast enough”.
in case of a large map and many lookups, the benefit of not checking if the object is a map is negated due that the get
is much slower
@jimmy do you foresee/have any objections to having unsafe do what the fast flag is doing? IOW should the patch @huxley be the implementation of unsafe?
Because if skipping the type checks and using get
is slower than having type checks and using .valAt
, etc. it doesn’t really make a lot of sense for the unsafe option, as it is implemented now, to exist.
I don't think so. Though I personally think depending on ILookup (.valAt) instead of APersistentMap (.get) gives us more flexibility. We don't want to only work on APersistentMaps for that. Anything implementing ILookup should be allowed (in my view). Maybe for non-unsafe where we know map? is true we could use .get if it is truly faster. For example, one thing we might want to support in unsafe mode is transients, but transients are not APersistentMaps.
+-------------+----------------+----------------------------+
| type-check? | native-method? | result |
+-------------+----------------+----------------------------+
| true | false | (f object ,,,) | < Slow
+-------------+----------------+----------------------------+
| true | true | (.method ^Type object ,,,) | < Safe (Default)
+-------------+----------------+----------------------------+
| false | false | (f object ,,,) | < Unsafe
+-------------+----------------+----------------------------+
| false | true | (.method ^Type object ,,,) | < Dangerous
+-------------+----------------+----------------------------+
> Maybe for non-unsafe where we know map? is true we could use .get if it is truly faster.
Note, that I’m throwing bounds-check?
into the same basket as type-check?
since it has a similar effect.
I recently updated to meander 0.0.626 and I get the following warnings when I start the REPL:
Performance warning, meander/util/epsilon.cljc:123:3 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:157:3 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:191:3 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:221:3 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:314:6 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:291:4 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:374:6 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:348:4 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:435:3 - case has int tests, but tested expression is not primitive.
Performance warning, meander/util/epsilon.cljc:630:3 - case has int tests, but tested expression is not primitive.
Reflection warning, meander/util/epsilon.cljc:714:24 - reference to field val can't be resolved.
I doubt it's a problem but wanted to call it out just in case@markaddleman I recently fixed those errors and all but the last of those should go away with the next release.
I’m hoping that we come to an agreement/patch on some of the new flag stuff and I can release that in addition to the update to &
patterns.
BTW in case anyone is interested, the algorithm I used to generate the space for map patterns like
{&1 ?m1 &2 ?m2 &3 ?m3}
came from the Art of Computer Programming Volume 4A on the topic of partitions.On a related topic, I just discovered a pattern that compiled in 0.0.602 but does not compile in 626:
(comment
; does not compile
(m/rewrites {}
{:group-defaults (m/scan {:attribute {:alias (m/some ?alias)}
:from-expression (m/some ?expression)})
:group-by (m/scan {:alias ?alias :as ?group-by})}
{:group-by [{:default {:from-expression ?expression} & ?group-by}]}
{:group-by (m/scan {(m/some :alias) ?a :as ?group-by})
:group-defaults (m/scan {:attribute {:alias (m/not ?a)}})}
{:group-by [?group-by]}))
Meander complains Unable to resolve symbol: ?a in this context
Oddly, this pattern compiles on .626:
(m/rewrites {}
{:group-by (m/scan {(m/some :alias) ?a :as ?group-by})
:group-defaults (m/scan {:attribute {:alias (m/not ?a)}})}
{:group-by [?group-by]})
Both patterns compile successfully on 602
whoopsie: My previous version of meander was 602 (not 606). Edited previous messages to make that clear