As I noted on StackOverflow, if you allow the kbin to return empty
sets, those could represent identities (assuming your operation has
one). Then you would get the matches {a:0, b: 1 + 2 + 3} and {a: 1 +
2 + 3, b: 0}. Depending on what you use this for, it may be desirable
to include those.
Aaron Meurer
On Tue, Oct 30, 2012 at 4:25 PM, Matthew Rocklin <[email protected]> wrote:
> Chris' code now enables unification to produce all possible matches
>
> In [1]: run ../unify/unify_sympy.py
> In [2]: expr = Add(1, 2, 3, evaluate=False)
> In [3]: a, b = map(Wild, 'ab')
> In [4]: pattern = Add(a, b, evaluate=False)
>
> In [5]: for x in unify(expr, pattern, {}): print x
> {a_: 1, b_: 2 + 3}
> {a_: 2, b_: 1 + 3}
> {a_: 3, b_: 1 + 2}
> {a_: 1 + 2, b_: 3}
> {a_: 2 + 3, b_: 1}
> {a_: 1 + 3, b_: 2}
>
> Of course, this quickly leads to computational blowup. Fortunately you can
> ask very efficiently for just the first, second, etc...
>
> Note that, as Aaron pointed out, this doesn't handle mathematical matching.
> Here is an example which matches a very particular structure.
>
> In [8]: from sympy.abc import x
> In [9]: expr = Add(1, 2*x, 3, evaluate=False)
> In [10]: pattern = Add(a, 2*b, evaluate=False)
> In [11]: for x in unify(expr, pattern, {}): print x
> {a_: 1 + 3, b_: x}
>
> Of course, we don't need to match exact structure. Wilds can currently match
> any node.
>
> In [6]: pattern = Add(a, b, evaluate=False)
>
> In [7]: for x in unify(expr, pattern, {}): print x
> {a_: 1, b_: 2*x + 3}
> {a_: 2*x, b_: 1 + 3}
> {a_: 3, b_: 2*x + 1}
> {a_: 2*x + 1, b_: 3}
> {a_: 2*x + 3, b_: 1}
> {a_: 1 + 3, b_: 2*x}
>
> On Tue, Oct 30, 2012 at 5:13 PM, Matthew Rocklin <[email protected]> wrote:
>>
>> Yes, that works quite well. Thanks Chris!
>>
>>
>> On Tue, Oct 30, 2012 at 4:27 PM, Chris Smith <[email protected]> wrote:
>>>
>>> What is said works, I believe...see the docstring
>>>
>>> def kbin(l, k, ordered=True):
>>> """
>>> Return sequence ``l`` partitioned into ``k`` bins.
>>> If ordered is True then the order of the items in the
>>> flattened partition will be the same as the order of the
>>> items in ``l``; if False, all permutations of the items will
>>> be given; if None, only unique permutations for a given
>>> partition will be given.
>>>
>>> Examples
>>> ========
>>>
>>> >>> from sympy.utilities.iterables import kbin
>>> >>> for p in kbin(range(3), 2):
>>> ... print p
>>> ...
>>> [[0], [1, 2]]
>>> [[0, 1], [2]]
>>> >>> for p in kbin(range(3), 2, ordered=False):
>>> ... print p
>>> ...
>>> [(0,), (1, 2)]
>>> [(0,), (2, 1)]
>>> [(1,), (0, 2)]
>>> [(1,), (2, 0)]
>>> [(2,), (0, 1)]
>>> [(2,), (1, 0)]
>>> [(0, 1), (2,)]
>>> [(0, 2), (1,)]
>>> [(1, 0), (2,)]
>>> [(1, 2), (0,)]
>>> [(2, 0), (1,)]
>>> [(2, 1), (0,)]
>>> >>> for p in kbin(range(3), 2, ordered=None):
>>> ... print p
>>> ...
>>> [[0], [1, 2]]
>>> [[1], [2, 0]]
>>> [[2], [0, 1]]
>>> [[0, 1], [2]]
>>> [[1, 2], [0]]
>>> [[2, 0], [1]]
>>>
>>> """
>>> from sympy.utilities.iterables import partitions, permutations
>>> def rotations(seq):
>>> for i in range(len(seq)):
>>> yield seq
>>> seq.append(seq.pop(0))
>>> if ordered is None:
>>> func = rotations
>>> else:
>>> func = permutations
>>> for p in partitions(len(l), k):
>>> if sum(p.values()) != k:
>>> continue
>>> for pe in permutations(p.keys()):
>>> rv = []
>>> i = 0
>>> for part in pe:
>>> for do in range(p[part]):
>>> j = i + part
>>> rv.append(l[i: j])
>>> i = j
>>> if ordered:
>>> yield rv
>>> else:
>>> template = [len(i) for i in rv]
>>> for pp in func(l):
>>> rvp = []
>>> ii = 0
>>> for t in template:
>>> jj = ii + t
>>> rvp.append(pp[ii: jj])
>>> ii = jj
>>> yield rvp
>>>
>>> --
>>> You received this message because you are subscribed to the Google Groups
>>> "sympy" group.
>>> To post to this group, send email to [email protected].
>>> To unsubscribe from this group, send email to
>>> [email protected].
>>> For more options, visit this group at
>>> http://groups.google.com/group/sympy?hl=en.
>>>
>>
>
> --
> You received this message because you are subscribed to the Google Groups
> "sympy" group.
> To post to this group, send email to [email protected].
> To unsubscribe from this group, send email to
> [email protected].
> For more options, visit this group at
> http://groups.google.com/group/sympy?hl=en.
--
You received this message because you are subscribed to the Google Groups
"sympy" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/sympy?hl=en.