Skip to content

Add any? and all? predicate combinators#4

Merged
hellerve merged 1 commit into
mainfrom
claude/any-all-predicates
Jun 2, 2026
Merged

Add any? and all? predicate combinators#4
hellerve merged 1 commit into
mainfrom
claude/any-all-predicates

Conversation

@carpentry-agent

Copy link
Copy Markdown

Summary

  • Adds any? and all? to all 10 persistent data structure types (list, queue, trie, deque, ord-map, ord-set, heap, hash-map, hash-set, vector)
  • Both are implemented via reduce with short-circuit-free fold semantics, matching the pattern of existing filter operations
  • Includes 6 tests per type (match, no-match, all-match, not-all-match, empty-any, empty-all)

Notes

  • Hash-map and hash-set tests crash on ARM64 due to pre-existing Carp compiler bug with nested closure captures in reduce (confirmed crash on main as well)
  • Ord-map tests hang on ARM64, also pre-existing
  • All other 7 types (list, queue, trie, deque, ord-set, heap, vector) compile and pass all tests

Test plan

  • Compiled and ran tests for list, queue, deque, trie, ord-set, heap, vector — all pass
  • Confirmed hash-map/hash-set/ord-map failures are pre-existing (same crash on main)
  • Ran carp-fmt -w on all changed files
  • Ran angler — no new findings (all are pre-existing)

@carpentry-reviewer carpentry-reviewer Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Build & Tests

Build: 7 of 10 data structure types compile and pass all tests locally (list: 25/25, queue: 24/24, deque: 22/22, trie: 25/25, ord-set: 20/20, heap: 14/14, vector: 14/14). Hash-map crashes during reduce tests (null Lambda pointer dereference), ord-map hangs on ARM — both confirmed pre-existing on main.

CI: both test (macos-latest) and test (ubuntu-latest) fail. The failure is in the hash-map test file which crashes at the pre-existing reduce test (test 7, line 95 of the test file) before any new any?/all? tests execute. I verified this: checking out main and running the same hash-map test produces the identical crash at the same point. This PR does not introduce any new CI failures.

Findings

  1. Implementation is correct. any? and all? are consistently implemented via reduce across all 10 types, with appropriate type signatures for element-based vs pair-based collections. The pattern matches existing filter implementations.

  2. No short-circuit iteration. reduce traverses all elements even after any? finds a match (or all? finds a non-match). The boolean operators (or/and) short-circuit the predicate evaluation, but not the iteration itself. This is acknowledged in the PR description ("short-circuit-free fold semantics") and is consistent with how filter works in this codebase. For collections of any realistic size in Carp, this is unlikely to matter, but it's worth being aware of.

  3. Gratuitous reformatting in heap and vector test files. carp-fmt -w collapsed several multi-line expressions to single lines (e.g. build-descending-heap, pop-values, heap empty? test). Not harmful, but adds noise to the diff — ~30 lines of formatting changes mixed in with the actual test additions.

Verdict: merge

The code is correct. All 7 locally-testable types pass. The CI failures are pre-existing (hash-map reduce with closures has been crashing on main for months). The formatting churn is minor.

@hellerve hellerve left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Rebase.

@carpentry-agent carpentry-agent Bot force-pushed the claude/any-all-predicates branch from eec28ba to af3e161 Compare June 2, 2026 17:07
@carpentry-agent

Copy link
Copy Markdown
Author

Rebased onto main as requested by @hellerve. Resolved merge conflicts in the hash-map and ord-map test files (both had the new merge/merge-with tests from PR #2 conflicting with the any?/all? tests — kept both). Formatting verified clean with carp-fmt.

@carpentry-reviewer carpentry-reviewer Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Build & Tests

CI: both test (macos-latest) and test (ubuntu-latest) pass.

Local (ARM64): compiled and ran 7 of 10 test files. All pass, including all new any?/all? tests:

  • persistent_list: 26/26
  • persistent_queue: 24/24
  • persistent_deque: 22/22
  • persistent_trie: 25/25
  • persistent_ord_set: 20/20
  • persistent_heap: 14/14
  • persistent_vector: 14/14

Skipped hash-map, hash-set, and ord-map (pre-existing ARM64 crashes/hangs confirmed on main).

Prior feedback

@hellerve requested a rebase (CHANGES_REQUESTED). The rebase was done: branch is now based on current main, merge conflicts in hash-map and ord-map test files (from PR #2's merge/merge-with tests) were resolved correctly — both sets of tests are present.

The previous reviewer noted gratuitous formatting churn in heap and vector test files from carp-fmt. That is still present (~30 lines of whitespace changes), but not worth blocking on.

Findings

Implementation is correct and consistent across all 10 types:

  1. Signatures are right. Element-based types (list, queue, deque, ord-set, heap, hash-set, vector) take (Ref (Fn [(Ref %value-type q)] Bool) r). Pair-based types (trie, ord-map, hash-map) take predicates over their respective Pair types, matching the existing filter signatures exactly.

  2. Bodies are identical. Every any? is (reduce &(fn [acc x] (or acc (~pred &x))) false coll-ref), every all? is (reduce &(fn [acc x] (and acc (~pred &x))) true coll-ref). No copy-paste errors.

  3. Empty collection semantics are correct. any? on empty returns false, all? on empty returns true — standard vacuous truth. Tested for all 10 types.

  4. Placement is consistent. For types with filter, any?/all? follow filter. For types without filter (ord-set, heap, hash-set, vector), they go before str. Both orderings are reasonable and internally consistent.

  5. Test coverage is thorough. 6 tests per type: match, no-match, all-match, not-all-match, empty-any, empty-all. The map/trie tests correctly use Pair accessors.

  6. No short-circuit iteration — reduce traverses all elements even after finding a result. Already noted in prior review and PR description. This is consistent with how filter works in this codebase and is a non-issue for realistic collection sizes.

No new issues found.

Verdict: merge

The rebase was done as requested. Code is correct, well-tested, and consistent with existing patterns.

@hellerve hellerve merged commit e7e5c01 into main Jun 2, 2026
2 checks passed
@hellerve hellerve deleted the claude/any-all-predicates branch June 2, 2026 19:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant