2011-02-17 40 views
7

Mathematicas NonCommutativeMultiply(**)不簡化了如重新定義非交換乘法數學

a**0=0**a=0 
a**1=1**a=a 

a**a=a^2. 

我想重新定義**做到這一點。我使用NC代數來做到這一點,但我需要ReplaceRepeated(//。)和NCAlgebra,正如他們的文檔所述,它專門在mathematica中打破了這個功能。

有些人可以告訴我如何清除**的屬性,並重新定義這個乘法做同樣的事情,它會正常做加上處理1和0.我真的不需要乘法來處理a**a,但它會是很好,如果它夠簡單。我需要**最主要的處理1和0

+0

請注意,「\ *」在SO上用作[標記元字符](http://stackoverflow.com/editing-help)。通過用反斜槓(「\」)或(如果適用)將文本標記爲代碼,使用反斜槓(「\`」)對於內聯代碼或具有四個空格的縮進行,可以具有文字「\ *」。如果您點擊您的問題的「編輯」鏈接,您可以檢查問題來源,看看它是如何完成的。您可以通過單擊編輯器工具欄中的橙色問號來閱讀有關標記語言(稱爲Markdown)的更多信息。 – outis 2011-02-17 02:18:22

回答

6

以下僅工作,如果您刪除NonCommutativeMultiply 的平屬性(這是一件好事測試...一個新手的錯誤時我做了錯誤!)

最簡單的事情做的是

Unprotect[NonCommutativeMultiply]; 
NonCommutativeMultiply[a___, 1, b___] := a ** b 
NonCommutativeMultiply[___, 0, ___] := 0 
NonCommutativeMultiply[a_] := a 
Protect[NonCommutativeMultiply]; 

需要最終的表達,使a**1簡化爲a,而不是NonCommutativeMultiply[a]。您可能還需要NonCommutativeMultiply[]:=1,以便像1**1這樣的表達式正確簡化(*)。 所有這一切的唯一問題是,對於大型表達式,該模式會針對所有內容進行檢查,並且這會變得非常緩慢。

爲0和1,以上兩個定義可以組合並推廣到

NonCommutativeMultiply[a___, n_?NumericQ, b___] := n a ** b 

哪些因素出表達式內的任何數值的術語。 但是這會在更大的表達式中減慢速度,因爲每一項都被檢查以查看它的數值。

爲了簡化a**aa^2,你需要像

NonCommutativeMultiply[a___, b_, b_, c___] := a ** b^2 ** c 

或者更一般

NonCommutativeMultiply[a___, b_^n_., b_^m_., c___] := a ** b^(n + m) ** c 

(*)請注意,這僅僅是因爲默認的順序是數學看跌期權其DownValues在這種情況下不一定是最好的。更改訂單,以便NonCommutativeMultiply[a_]a___ ** n_?NumericQ ** b___之前,然後NonCommutativeMultiply[]不會由規則生成,並且您不需要最後一個模式(除非您以其他方式生成NonCommutativeMultiply[])。

+0

順便說一句:我的論文和筆記本現在[在arXiv上](http://arxiv.org/abs/1102.3043)。因爲我有非常大的表達式,所以你會看到我必須對如何簡化NonCommutativeMultiply表達式做出艱難的決定。即使這樣,我不得不抱着媽媽的手進行一些計算,否則他們永遠不會終止。 – Simon 2011-02-17 01:36:25

+0

@Simon,優化對我來說絕對是一個問題。我想知道,如果我只需要將0和1加入**,它將會變慢多少。感謝您的幫助,我現在會檢查論文。我也會嘗試這個代碼並回報任何問題。 – Cantormath 2011-02-17 04:08:02

1

好的,編寫適合NonCommutativeMultiply屬性的規則有時是一件麻煩事。這裏有一個替代方法,它引入了一個幫助程序NCM,它沒有與其關聯的規則和屬性NonCommutativeMultiply

以下代碼還包含了最後幾個問題。 (1)(2)

Unprotect[NonCommutativeMultiply]; 
Clear[NonCommutativeMultiply] 
(* Factor out numerics -- could generalize to some ScalarQ *) 
nc:NonCommutativeMultiply[a__]/;MemberQ[{a},_?NumericQ]:=NCMFactorNumericQ[NCM[a]]/.NCM->NonCommutativeMultiply 
(* Simplify Powers *) 
b___**a_^n_.**a_^m_.**c___:=NCM[b,a^(n+m),c]/.NCM->NonCommutativeMultiply 
(* Expand Brackets *) 
nc:NonCommutativeMultiply[a___,b_Plus,c___]:=Distribute[NCM[a,b,c]]/.NCM->NonCommutativeMultiply 
(* Sort Subscripts *) 
c___**Subscript[a_, i_]**Subscript[b_, j_]**d___/;i>j:=c**Subscript[b, j]**Subscript[a, i]**d 
Protect[NonCommutativeMultiply]; 

Unprotect[NCM]; 
Clear[NCM] 
NCMFactorNumericQ[nc_NCM]:=With[{pos=Position[nc,_?NumericQ,1]},[email protected]@Extract[nc,pos] Delete[nc,pos]] 
NCM[a_]:=a 
NCM[]:=1 
Protect[NCM]; 

注意NCMFactorNumericQ是快,因爲它在一個單一的傳球,但與之相關的規則nc:NonCommutativeMultiply[a__]/;MemberQ[{a},_?NumericQ]是緩慢的,因爲平屬性意味着它使用NumericQ檢查的一個愚蠢的數量。 如果你真的想要更快的速度和大的表達式,那麼你應該手動應用SortFactor例程,以便Mathematica減少模式檢查。

1

訣竅與

Unprotect[NonCommutativeMultiply]; 
.... 
Protect[NonCommutativeMultiply]; 

非常好!我花了10個小時試圖解決NonCommutativeMultiply問題(如何平坦化涉及n.c.和正常乘法的表達式,如a**b**(c*d*(e**f)),但更復雜),但我沒有想到自己修改NonCommutativeMultiply本身。謝謝!