# Package bubble-operator-upwards

# Description

This package is also nicknamed `bubble-op-up`

.

Simply `(:import-from #:bubble-operator-upwards #:`

from your defpackage. Don't `bubble-operator-upwards`

)`(:use)`

!

`bubble-operator-upwards`

is a function that "bubbles an operator upwards" in a form,

demultiplexing all alternative branches by way of cartesian product.

This operation is notably useful for easy implementation of certain kinds of shorthand notations in macros.

A `cartesian-product`

function is also exported, as it's needed to implement the main function.

Here are a few examples:

`(``bubble-operator-upwards`

'and '(plate (and ham eggs) beans))
=>
(AND (PLATE HAM BEANS)
(PLATE EGGS BEANS))

`(``bubble-operator-upwards`

'alt '(section (alt 1 2 3) - (alt "a" "b"))
:result-kind :branches)
=>
((SECTION 1 - "a") (SECTION 1 - "b")
(SECTION 2 - "a") (SECTION 2 - "b")
(SECTION 3 - "a") (SECTION 3 - "b"))

`(``bubble-operator-upwards`

'or '(>> (or ul ol)
(or (:class (or "important" "urgent"))
(id "first-priority"))))
=>
(OR (>> UL (:CLASS "important"))
(>> UL (:CLASS "urgent"))
(>> UL (ID "first-priority"))
(>> OL (:CLASS "important"))
(>> OL (:CLASS "urgent"))
(>> OL (ID "first-priority")))

This package is also nicknamed `bubble-op-up`

.

Simply `(:import-from #:bubble-operator-upwards #:`

from your defpackage. Don't `bubble-operator-upwards`

)`(:use)`

!

`operator` `form` &key (`result-kind` :abridged) (`if-collapsed` nil) (`collapsed-identity` [...]) => `result`

`operator`-- A symbol.`form`-- A form.`result-kind`-- One of the keywords`:branches`

,`:full`

or`:abridged`

.`if-collapsed`--`:error`

or`nil`

.-
`collapsed-identity`-- An object. The default is:`(ecase`

`result-kind`((:full :abridged) (list`operator`)) (:branches nil))

Bubbles `operator` upwards in `form`, demultiplexing all alternative branches by way of cartesian product.

Hard to describe formally, but the examples above should give some inspiration for the basic effect,

and some experimentation in the REPL is recommended.

`result-kind` is one of `:branches`

, `:full`

or `:abridged`

:

`:branches`

simply returns the demultiplexed branches.`:full`

returns the same`result`as`:branches`

would, except wrapped in a cons whose CAR is`operator`.`:abridged`

returns the same result as`:full`

would, except if there's only one branch, only that branch is returned, without the wrapping.

`if-collapsed` and `collapsed-identity` determine what to do if the number of branches "collapses" to zero.

`if-collapsed` is `:error`

or `nil`

. If it's `nil`

and the result is indeed collapsed, then the value of `collapsed-identity` will be returned.

&rest `possibility-groups` => `cartesian-product`

`possibility-groups`-- A list.

Returns the cartesian-product of all possible combinations from `possibility-groups`, as a list.

This function is inherently needed to implement `bubble-operator-upwards`

, so might as well export it...

`(``bubble-op-up:cartesian-product`

'(1 2) '(a b c))
=>
((1 A) (1 B) (1 C)
(2 A) (2 B) (2 C))