Как Mathematica определяет, какое правило использовать первым при замене - PullRequest
5 голосов
/ 28 января 2011

Мне интересно, если дано несколько правил подстановки, как mma определяет, что применять в первую очередь в случае коллизии. Пример:

x^3 + x^2*s + x^3*s^2 + s x /. {x -> 0, x^_?OddQ -> 2}

Спасибо.

1 Ответ

12 голосов
/ 28 января 2011

Mathematica имеет механизм, который может определять относительную общность правил в простых случаях, например, он понимает, что ___ (BlankNullSequence) является более общим, чем __ (BlankSequence).Поэтому, когда это возможно, он переупорядочивает глобальные определения в соответствии с ним.Тем не менее, важно понимать, что такой анализ обязательно в основном синтаксический.Поэтому, хотя PatternTest (?) и Condition (/;) с некоторыми простыми встроенными предикатами, такими как EvenQ, иногда можно анализировать, использование их с пользовательскими предикатами обязательно сделает невозможным такое переупорядочение в отношении аналогично определенных правил, так что Mathematicaпридерживайтесь таких правил в том порядке, в котором они были введены.Это связано с тем, что PatternTest и Condition вынуждают средство сопоставления с образцом вызывать средство оценки для определения факта соответствия, и это делает невозможным ответ на вопрос об относительной общности правил при определении - времени.Даже для чисто синтаксических правил не всегда возможно определить их относительную общность.Таким образом, когда это не может быть сделано, или Mathematica не может этого сделать, он сохраняет правила в том порядке, в котором они были введены.

Все это касалось глобальных правил, созданных Set или SetDelayed илидругие операторы присваивания.Для локальных правил, как в вашем примере, нет никакого изменения порядка, они применяются в порядке, который они имеют в списке правил.Все правила в списке правил, кроме первого, примененного к данному (под) выражению, игнорируются для этого подвыражения и конкретного процесса применения правила - выражение (под) переписывается в соответствии с первым правилом соответствия, изатем процесс применения правила продолжается с другими подвыражениями.Даже если новая форма переписанного (под) выражения совпадает с некоторыми правилами, расположенными ниже по списку правил, они не применяются в этом процессе применения правила.Другими словами, для отдельного процесса применения правила для любого конкретного (под) выражения не применяется ни одно правило, или только одно правило.Но и здесь есть несколько тонкостей.Например, ReplaceAll (/.) применяет правила от больших выражений к подвыражениям, в то время как Replace с явной спецификацией уровня делает это противоположным образом.Это может иметь значение в таких случаях:

In[1]:= h[f[x, y]] /. {h[x_f] :> a, f[args__] :> b}

Out[0]= a

In[2]:= Replace[h[f[x, y]], {h[x_f] :> a, f[args__] :> b}, {0, Infinity}]

Out[2]= h[b]

Я упоминал о переупорядочении правил в нескольких местах в моей книге: здесь , здесь и здесь.В редких случаях, когда Mathematica переупорядочивает правила способом, который является неудовлетворительным, вы можете изменить порядок вручную путем прямых манипуляций с DownValues (или другими ... значениями), например, такими как DownValues[f] = Reverse[DownValues[f]].Такие случаи случаются иногда, но довольно редко, и если они случаются, убедитесь, что есть веская причина сохранить существующий дизайн и перейти к ручному переупорядочению правил.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...