Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

Tr printing, Tr partial trace #1396

Merged
merged 14 commits into from

10 participants

@gdevanla

This PR implements printing operations for Tr operators and partial trace operations. Also cycle permutes are fixed for consistency. Some changes added to Density class to enable partial trace operations. Also, new set of Notebook examples have been provided.

@ellisonbg , @flacjacket, could you please review the design.

@gdevanla

The printing currently does not print out the indices that are provided as part of object creation. We need to figure out a way to output this along with all other arguments to Tr. Should it just be a [list] displayed after all other arguments to Tr or some super-script/subscript?

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYm5seDA

Interpreter: /opt/pym32/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (32-bit)
Cache: yes
Test command: setup.py test
master hash: d136cb7
branch hash: 11bb365255ed727e8bbea2e192c2a4c7235917a8

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYxYseDA

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: d136cb7
branch hash: 11bb365255ed727e8bbea2e192c2a4c7235917a8

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYqJMeDA

Interpreter: /usr/bin/python3 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: d136cb7
branch hash: 11bb365255ed727e8bbea2e192c2a4c7235917a8

Automatic review by SymPy Bot.

@travisbot

This pull request fails (merged 11bb3652 into d136cb7).

@travisbot

This pull request fails (merged ed384052 into d136cb7).

@travisbot

This pull request fails (merged 88eed960 into d136cb7).

@certik
Owner

@gdevanla, there are failures caused by your pull request:

________________________________________________________________________________
2575____________ sympy/physics/quantum/tests/test_density.py:test_doit _____________
2576  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/physics/quantum/tests/test_density.py", line 49, in test_doit
2577    assert d.doit() == (1.0*A*C*Dagger(C)*Dagger(A) +
2578  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/physics/quantum/density.py", line 167, in doit
2579    for arg in itertools.product(state.args, repeat=2):
2580AttributeError: 'module' object has no attribute 'product'
2581________________________________________________________________________________
2582______ sympy/physics/quantum/tests/test_tensorproduct.py:test_eval_trace _______
2583  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/physics/quantum/tests/test_tensorproduct.py", line 94, in test_eval_trace
2584    assert t.doit() == ( 1.0*Tr(A*Dagger(A))*Tr(B*Dagger(B)) +
2585  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/core/trace.py", line 146, in doit
2586    return self.args[0]._eval_trace(indices=self.args[1])
2587  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/physics/quantum/density.py", line 193, in _eval_trace
2588    return Tr(self.doit(), indices).doit()
2589  File "/home/vagrant/virtualenv/python2.5/lib/python2.5/site-packages/sympy/physics/quantum/density.py", line 167, in doit
2590    for arg in itertools.product(state.args, repeat=2):
2591AttributeError: 'module' object has no attribute 'product'

Only the last failure was already in master, and the pull request #1398 fixes that one.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYnJseDA

Interpreter: /opt/pym32/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (32-bit)
Cache: yes
Test command: setup.py test
master hash: 9ba3cb3
branch hash: 88eed960ae243f780460bfa9d3bccb7cad83260f

Automatic review by SymPy Bot.

@gdevanla

Ok, the error message is since itertools.product is not supported in Python 2.5 Will fix that soon.

@asmeurer
Owner

There's probably a replacement in the compatibility file.

@asmeurer
Owner

I'm curious why the trace stuff is in the core.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY8fsdDA

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 9ba3cb3
branch hash: 88eed960ae243f780460bfa9d3bccb7cad83260f

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYlekeDA

Interpreter: /usr/bin/python3 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 0930232
branch hash: 88eed960ae243f780460bfa9d3bccb7cad83260f

Automatic review by SymPy Bot.

@gdevanla

@asmeurer The Tr module implemented currently is generic and does not have to belong to the physics module. The module in turn calls _eval_trace() methods in objects passed as 'args' to Tr. For now, yes _eval_trace() methods are defined for objects under physics/quantum module, but that need not be true always.

@travisbot

This pull request passes (merged b01f7e5 into 0930232).

@Krastanov
Collaborator

SymPy Bot Summary: :eight_spoked_asterisk: All tests have passed.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY8_sdDA

Interpreter: /opt/pym32/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (32-bit)
Cache: yes
Test command: setup.py test
master hash: 0930232
branch hash: b01f7e5

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYruwdDA

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 0930232
branch hash: b01f7e5

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY2NwdDA

Interpreter: /usr/bin/python3 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 0930232
branch hash: b01f7e5

Automatic review by SymPy Bot.

@asmeurer
Owner

I agree it is general enough to not be in the physics module, but that doesn't mean it belongs in the core. Only very basic stuff that is used by everything should be in the core. Trace I think belongs somewhere else.

@gdevanla

Yes, one could say it is not a core operation. Do you have any suggestion on where it should go?

@ellisonbg Do you have any suggestion, based how the Tr operator would be used in the future?

@flacjacket
Collaborator

functions.elementary might be a good place for it.

@asmeurer
Owner

I'd put it somewhere other than elementary. That's supposed to be only elementary functions. See http://code.google.com/p/sympy/issues/detail?id=2149.

@flacjacket flacjacket commented on the diff
examples/notebooks/density.ipynb
((16 lines not shown))
+ "source": [
+ "## Density operators with Tensor Products as args"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "from sympy.core.trace import Tr",
+ "",
+ "A, B, C, D = symbols('A B C D',commutative=False)",
+ "",
+ "t1 = TensorProduct(A,B,C)",
+ "",
+ "d = Density([t1, 1.0])",
+ "d.doit()",
@flacjacket Collaborator

To display this result, you'll either need to split the cell here or use display() from IPython.core.display

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@flacjacket
Collaborator

The rest of the changes seem alright to me, once we figure out a better place for trace to go.

@gdevanla

I have other changes siting in the follow up branch. I will move the discussion on where Tr should go to the mailing list. I can submit a separate PR with just the re-factored changes. Will that work?

Alternatively, the one place I can think of after looking at existing folder structures is at : sympy/matrices/expressions. This folder already has modules for matadd, matmul, matpow, inverse and transpose.

@travisbot

This pull request passes (merged e1a3a01 into 0930232).

@Krastanov
Collaborator

SymPy Bot Summary: :eight_spoked_asterisk: All tests have passed.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY6YMeDA

Interpreter: /opt/pym32/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (32-bit)
Cache: yes
Test command: setup.py test
master hash: 424160a
branch hash: e1a3a01

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY6oMeDA

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 424160a
branch hash: e1a3a01

Automatic review by SymPy Bot.

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYuewdDA

Interpreter: /usr/bin/python3 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes
Test command: setup.py test
master hash: 424160a
branch hash: e1a3a01

Automatic review by SymPy Bot.

@flacjacket
Collaborator

Guru, have you sent a message to the list? I feel like since the damage was done and trace.py was put in core in the last PR, it should be alright to merge this and fix it in a later PR when a good spot is found. @asmeurer: what do you think about that?

@ellisonbg have you taken a look at this yet?

@asmeurer
Owner

That should be fine.

@gdevanla

Ok, once @ellisonbg is fine with these changes, this can go.

I will start the mailing thread to discuss the where the Tr module should go.

@ellisonbg
Owner
@ellisonbg
Owner

I think this looks good. I will give some feedback on individual lines. My broad comment is that all your tests and notebook examples use symbols instead of bras/kets. Please include some tests with actual bras/kets and use bras/kets in the notebook examples.

sympy/core/trace.py
((23 lines not shown))
expr = args[0]
- indices = args[1] if len(args) == 2 else -1 #-1 indicates full trace
+ indices = args[1] if len(args) == 2 else []
@ellisonbg Owner

@flacjacket do you think we should wrap indices here in a sympy Tuple?

@flacjacket Collaborator

Yes, we should. I'm not sure why this doesn't trip the test_args test.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@ellisonbg ellisonbg commented on the diff
sympy/core/trace.py
((5 lines not shown))
return True
+
+
+ #TODO: Review if the permute method is needed
+ # and if it needs to return a new instance
+ #def permute(self, pos):
@ellisonbg Owner

I would like to have the permute method and it should return a new instance.

@ellisonbg Actually, I had started a discussion on this on the mailing list. http://bit.ly/M7D9wF

I can work on this and see how we can achieve this. I will add to my TODO. In the subsequent PR, I will update this method based on how we decide to do it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@ellisonbg ellisonbg commented on the diff
sympy/physics/quantum/density.py
((5 lines not shown))
terms = []
for (state, prob) in self.args:
- terms.append(prob*(state*Dagger(state)))
+ state = state.expand() # needed to break up (a+b)*c
+ if (isinstance(state, Add)):
+ for arg in product(state.args, repeat=2):
+ terms.append(prob *
+ self._generate_outer_prod(arg[0], arg[1]))
@ellisonbg Owner

The _generate_outer_product method should be called _generate_tensor_product to be consistent with our naming. Also, can you summarize what this method does and why it is needed?

@ellisonbg I am guessing you were commenting on the _generate_outer_prod in tensor_product. I plan to remove that function.

The function here is just to reuse code needed within the for and if constructs. Am I in sync?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
sympy/physics/quantum/tensorproduct.py
@@ -196,6 +197,18 @@ def expand(self, **hints):
tp = TensorProduct(*[sympify(item).expand(**hints) for item in self.args])
return Expr.expand(tp, **hints)
+ def _generate_outer_prod(self,arg):
@ellisonbg Owner

Minimally we need docs to describe why this is needed. Why can we just call tensor_product_simp directly?

Agreed, the redirection is not needed. I will invoke tensor_product_simp directly.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@ellisonbg
Owner

This can come in a later PR, but I would like to see some tests with Traces of density matrices of tensor products of spin states to make sure the logic works when the representations are matrices.

@travisbot

This pull request fails (merged bcd53e1 into 0930232).

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test command: setup.py test
master hash: 387547b
branch hash: bcd53e1

Interpreter 1: :red_circle: There were test failures.

Interpreter: /usr/local/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYya8fDA

Interpreter 2: :red_circle: There were test failures.

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY8ZwgDA

Interpreter 3: :red_circle: There were test failures.

Interpreter: /usr/bin/python3.2 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY7vUfDA

Build HTML Docs: :red_circle: There were test failures.

Docs build command: make html-errors
Sphinx version: 1.1.3

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYm-YfDA

Automatic review by SymPy Bot.

@travisbot

This pull request fails (merged 4f3405d into 0930232).

@Krastanov
Collaborator

SymPy Bot Summary: :red_circle: There were test failures.

@gdevanla: Please fix the test failures.

Test command: setup.py test
master hash: 0abed0f
branch hash: 4f3405d

Interpreter 1: :red_circle: There were test failures.

Interpreter: /usr/local/bin/python2.5 (2.5.6-final-0)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYn-YfDA

Interpreter 2: :red_circle: There were test failures.

Interpreter: /usr/bin/python2.7 (2.7.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYk_EeDA

Interpreter 3: :red_circle: There were test failures.

Interpreter: /usr/bin/python3.2 (3.2.3-candidate-2)
Architecture: Linux (64-bit)
Cache: yes

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYkJUgDA

Build HTML Docs: :red_circle: There were test failures.

Docs build command: make html-errors
Sphinx version: 1.1.3

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sYzq8fDA

Automatic review by SymPy Bot.

@jrioux
Collaborator

SymPy Bot Summary: :eight_spoked_asterisk: All tests have passed.

Test results html report: http://reviews.sympy.org/report/agZzeW1weTNyDAsSBFRhc2sY66cfDA

Interpreter: /usr/bin/python (2.7.0-final-0)
Architecture: Linux (32-bit)
Cache: yes
Test command: setup.py test
master hash: fb35324
branch hash: 4f3405d

Automatic review by SymPy Bot.

@ellisonbg
Owner

This is ready for merge, and the latest test run seems to pass. But the previous one had lots of failures that seem unrelated to this PR. Do anyone understand those failures?

@jrioux
Collaborator

There was a failure in test_gruntz in the master branch, which has since been fixed. There are still failures related to hash randomization in master, which makes it hard to evaluate whether any failure is introduced by this pull request or not. Judging by the latest test results here, I would say it is safe to merge this pull request.

@ellisonbg ellisonbg merged commit b33c1ed into sympy:master
@amakelov

I'm not sure if this is relevant, but a recent run of travisbot on one of my PRs brought up an error in test_density.py. Here's the pull request: #1406 and the error report: http://travis-ci.org/#!/sympy/sympy/builds/1879684

@jrioux jrioux commented on the diff
sympy/physics/quantum/tests/test_density.py
((22 lines not shown))
+
+ d = Density([t2, 0.5], [t3, 0.5])
+ assert d.doit() == (0.5 * TensorProduct(A*Dagger(A), B*Dagger(B)) +
+ 0.5 * TensorProduct(C*Dagger(C), D*Dagger(D)))
+
+ #Density with mixed states
+ d = Density([t2+t3,1.0])
+ assert d.doit() == (1.0 * TensorProduct(A*Dagger(A), B*Dagger(B)) +
+ 1.0 * TensorProduct(A*Dagger(C), B*Dagger(D)) +
+ 1.0 * TensorProduct(C*Dagger(A), D*Dagger(B)) +
+ 1.0 * TensorProduct(C*Dagger(C), D*Dagger(D)))
+
+
+ #Density operators with spin states
+ tp1 = TensorProduct(JzKet(1,1), JzKet(1,-1))
+ tp2 = TensorProduct(JzKet(1,-1/2), JzKet(1,-1/2))
@jrioux Collaborator
jrioux added a note

To avoid the python 3 problem this could be written tp2 = TensorProduct(JzKet(1,-S(1)/2), JzKet(1,-S(1)/2))

@asmeurer Owner

Note that in Python 2, this is giving 0, because you aren't using future division. Try adding from __future__ import division to the top of file.

I guess the question is if you want this to work with floating point half numbers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@smichr
Collaborator

The problem (according to the error message) is that j and m are not both integer (or both half-integer). The message could be rewritten from "Both j and m must be integer or half-integer" to "j and m must both be integer or both be half-integer"

@gdevanla

I submitted a follow-up pull request to address this issue at #1425

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
This page is out of date. Refresh to see the latest.
View
303 examples/notebooks/density.ipynb
@@ -28,7 +28,7 @@
],
"language": "python",
"outputs": [],
- "prompt_number": 22
+ "prompt_number": 3
},
{
"cell_type": "code",
@@ -38,7 +38,7 @@
],
"language": "python",
"outputs": [],
- "prompt_number": 23
+ "prompt_number": 4
},
{
"cell_type": "markdown",
@@ -55,7 +55,7 @@
],
"language": "python",
"outputs": [],
- "prompt_number": 24
+ "prompt_number": 5
},
{
"cell_type": "code",
@@ -70,13 +70,13 @@
"$$\\rho\\left(\\begin{pmatrix}{\\left|\\psi\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}{\\left|\\phi\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 25,
+ "prompt_number": 6,
"text": [
"\u03c1((\u2758\u03c8\u27e9, 0.5),(\u2758\u03c6\u27e9, 0.5))"
]
}
],
- "prompt_number": 25
+ "prompt_number": 6
},
{
"cell_type": "code",
@@ -93,7 +93,7 @@
]
}
],
- "prompt_number": 26
+ "prompt_number": 7
},
{
"cell_type": "code",
@@ -108,13 +108,13 @@
"$$\\begin{pmatrix}{\\left|\\psi\\right\\rangle }, & {\\left|\\phi\\right\\rangle }\\end{pmatrix}$$"
],
"output_type": "pyout",
- "prompt_number": 27,
+ "prompt_number": 8,
"text": [
"(\u2758\u03c8\u27e9, \u2758\u03c6\u27e9)"
]
}
],
- "prompt_number": 27
+ "prompt_number": 8
},
{
"cell_type": "code",
@@ -129,13 +129,13 @@
"$$\\begin{pmatrix}0.5, & 0.5\\end{pmatrix}$$"
],
"output_type": "pyout",
- "prompt_number": 28,
+ "prompt_number": 9,
"text": [
"(0.5, 0.5)"
]
}
],
- "prompt_number": 28
+ "prompt_number": 9
},
{
"cell_type": "code",
@@ -151,13 +151,13 @@
],
"output_type": "pyout",
"png": "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\n+vgfqAPSYqWMIZsAAAAASUVORK5CYII=\n",
- "prompt_number": 29,
+ "prompt_number": 10,
"text": [
"0.5\u22c5\u2758\u03c6\u27e9\u27e8\u03c6\u2758 + 0.5\u22c5\u2758\u03c8\u27e9\u27e8\u03c8\u2758"
]
}
],
- "prompt_number": 29
+ "prompt_number": 10
},
{
"cell_type": "code",
@@ -172,13 +172,13 @@
"$$\\rho\\left(\\begin{pmatrix}{\\left|\\psi\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}{\\left|\\phi\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 30,
+ "prompt_number": 11,
"text": [
"\u03c1((\u2758\u03c8\u27e9, 0.5),(\u2758\u03c6\u27e9, 0.5))"
]
}
],
- "prompt_number": 30
+ "prompt_number": 11
},
{
"cell_type": "code",
@@ -188,7 +188,7 @@
],
"language": "python",
"outputs": [],
- "prompt_number": 31
+ "prompt_number": 12
},
{
"cell_type": "code",
@@ -203,13 +203,13 @@
"$$\\rho\\left(\\begin{pmatrix}A {\\left|\\psi\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}A {\\left|\\phi\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 32,
+ "prompt_number": 13,
"text": [
"\u03c1((A\u22c5\u2758\u03c8\u27e9, 0.5),(A\u22c5\u2758\u03c6\u27e9, 0.5))"
]
}
],
- "prompt_number": 32
+ "prompt_number": 13
},
{
"cell_type": "markdown",
@@ -226,7 +226,7 @@
],
"language": "python",
"outputs": [],
- "prompt_number": 33
+ "prompt_number": 14
},
{
"cell_type": "code",
@@ -241,13 +241,13 @@
"$$\\rho\\left(\\begin{pmatrix}{\\left|\\frac{1}{2},\\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}{\\left|\\frac{1}{2},- \\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 34,
+ "prompt_number": 15,
"text": [
"\u03c1((\u27581/2,1/2\u27e9, 0.5),(\u27581/2,-1/2\u27e9, 0.5))"
]
}
],
- "prompt_number": 34
+ "prompt_number": 15
},
{
"cell_type": "code",
@@ -262,7 +262,7 @@
"$$\\left[\\begin{smallmatrix}0.5 & 0\\\\0 & 0.5\\end{smallmatrix}\\right]$$"
],
"output_type": "pyout",
- "prompt_number": 35,
+ "prompt_number": 16,
"text": [
"",
"\u23a10.5 0 \u23a4",
@@ -271,7 +271,7 @@
]
}
],
- "prompt_number": 35
+ "prompt_number": 16
},
{
"cell_type": "code",
@@ -286,7 +286,7 @@
"$$\\rho\\left(\\begin{pmatrix}J_z {\\left|\\frac{1}{2},\\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}J_z {\\left|\\frac{1}{2},- \\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 36,
+ "prompt_number": 17,
"text": [
"",
"\u03c1\u239b\u239bJ \u22c5\u27581/2,1/2\u27e9, 0.5\u239e,\u239bJ \u22c5\u27581/2,-1/2\u27e9, 0.5\u239e\u239e",
@@ -294,7 +294,7 @@
]
}
],
- "prompt_number": 36
+ "prompt_number": 17
},
{
"cell_type": "code",
@@ -309,7 +309,7 @@
"$$\\rho\\left(\\begin{pmatrix}\\frac{1}{2} \\hbar {\\left|\\frac{1}{2},\\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}- \\frac{1}{2} \\hbar {\\left|\\frac{1}{2},- \\frac{1}{2}\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
],
"output_type": "pyout",
- "prompt_number": 37,
+ "prompt_number": 18,
"text": [
"",
" \u239b\u239b\u210f\u22c5\u27581/2,1/2\u27e9 \u239e \u239b-\u210f\u22c5\u27581/2,-1/2\u27e9 \u239e\u239e",
@@ -318,7 +318,7 @@
]
}
],
- "prompt_number": 37
+ "prompt_number": 18
},
{
"cell_type": "code",
@@ -334,7 +334,7 @@
],
"output_type": "pyout",
"png": "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\nURRFUZQa8j/bVKmwXxjmUgAAAABJRU5ErkJggg==\n",
- "prompt_number": 38,
+ "prompt_number": 19,
"text": [
"",
"0.5\u22c5J \u22c5\u27581/2,-1/2\u27e9\u27e81/2,-1/2\u2758 + 0.5\u22c5J \u22c5\u27581/2,1/2\u27e9\u27e81/2,1/2\u2758",
@@ -342,12 +342,12 @@
]
}
],
- "prompt_number": 38
+ "prompt_number": 19
},
{
"cell_type": "markdown",
"source": [
- "Evaluate entropy of the density matrices"
+ "## Evaluate entropy of the density matrices"
]
},
{
@@ -364,7 +364,7 @@
],
"output_type": "pyout",
"png": "iVBORw0KGgoAAAANSUhEUgAAAEUAAAAiCAYAAAAJfBTLAAAABHNCSVQICAgIfAhkiAAAA+RJREFU\naIHt2HuIVVUUx/GPw4w5TtmkZTVmNSkRJTlkRVmYGFH0+qOggoygwv8qIaI/sockTERlEVH0/Ksw\nKeglg1lCRlSERJAUNOlYGoWpPaSHPaY/1jncfe/cO9eZ5sytvF+43LP3WfucddZZ+7f2PjT5RxyC\n1kY78W/hACzAZhzbWFfGh5Z9sLkSB6G7YF/+kwxqZsr+SzMoVSi6mszFhZiGt/FawfebiL1J+2Jc\nJKb+BqzBT8PYo/hM2YOfcQvmFXyvI3Bd0l6JhbgPq7BUBObwxOZWEZhRMUFEe7QVaDvuHu3N94EW\nPKaU+YvwcoXNMeIlbUj6ZuOJaherx7V4GhvRKyI+Un4fxZiRcA3W44+sfSk6lFfLrfgQ89GZ9fVj\nG3oK9q8qA4rNlHXKp8HjIrNvrrB7Nus/O+mbgydTo0Yu2+cJEZyIL7AWX1fYtIgsOBNfYjUOxVXY\niXswBW3KBXMZPsCLFdebJYKyKenrF8Vg3BlQnim3iUo0NWvPwrs4I7FpwSvow3Qcj0+zcTOy4zZR\n4Vbtgw8zReBer3JuM9orOwcL+KUMKAXlPPwm3njKAuzCcVl7YXadxYnNA/hFbDtyFgnNq8dTIrtm\nVjm3XrwYlIR2QgG/WizDx/iuov8d8bBXZO08sNsTm+8xSSnD4IcaD5pyCS4TL+SrKuePVL5+GRcG\nRKZMwI94s4bdLiGaORvFVMt5A+9XjDkMW4a590lCs2qtk1qxW1KJx1toB8WDH1zlXKf4ZrMn6XtV\naElv9r9DKZNydohsaRdTK2U6nhElOhfXGaJ0f5u1u0WW/pUPakT1WSfSOV8Q5vQk53M6cL14i9W0\nKud5oUlrk752UYJvUF5tLheZmgdlIZ4b4TOMCQNKQjtbLJgWV9jcJcpomkWfKQnvcEwSAcnXKi14\nCfeK8p3/rhZZkdtNzcYNp4FVaceNWIElRrZXmIv7RWpuEXuNVqH0fXg0c3a5WFNMqRi/En+KKbVb\nBGmNEMxKenBTdrxc7ar4eTJmhaTq5NSLUAsewZ2ZUw/iVJyTOVuPbiF0KX3J2E6ciI8M1YNFYiO5\nWpTSNhyd2S8RwXyhYswMUa1OU77xS9mJ97LjmapXo2GZg0+EYEGXiPZZI73QKOjH6TXOPaT6ImxM\nqLch3CqE79esnW+42opyKGGT8hVuyhRDS/OYMVKBWSrEar7id75H4Q5Mxlv4Rmz/zxfZ22volBt3\nThD7k65xvm8HTsa5mQ+j/ig01nSJjzF5udzvv+1Ow+1KOnIKLmicO8VTT1MOFEK7V2k12SXK5bYC\n/Woo9Zb5k/FwRd+g/3FAmjRp0mSs+Rvvgds8ldAxMgAAAABJRU5ErkJggg==\n",
- "prompt_number": 39,
+ "prompt_number": 20,
"text": [
"",
"log(2)",
@@ -373,7 +373,7 @@
]
}
],
- "prompt_number": 39
+ "prompt_number": 20
},
{
"cell_type": "code",
@@ -389,7 +389,7 @@
],
"output_type": "pyout",
"png": "iVBORw0KGgoAAAANSUhEUgAAAEUAAAAiCAYAAAAJfBTLAAAABHNCSVQICAgIfAhkiAAAA+RJREFU\naIHt2HuIVVUUx/GPw4w5TtmkZTVmNSkRJTlkRVmYGFH0+qOggoygwv8qIaI/sockTERlEVH0/Ksw\nKeglg1lCRlSERJAUNOlYGoWpPaSHPaY/1jncfe/cO9eZ5sytvF+43LP3WfucddZZ+7f2PjT5RxyC\n1kY78W/hACzAZhzbWFfGh5Z9sLkSB6G7YF/+kwxqZsr+SzMoVSi6mszFhZiGt/FawfebiL1J+2Jc\nJKb+BqzBT8PYo/hM2YOfcQvmFXyvI3Bd0l6JhbgPq7BUBObwxOZWEZhRMUFEe7QVaDvuHu3N94EW\nPKaU+YvwcoXNMeIlbUj6ZuOJaherx7V4GhvRKyI+Un4fxZiRcA3W44+sfSk6lFfLrfgQ89GZ9fVj\nG3oK9q8qA4rNlHXKp8HjIrNvrrB7Nus/O+mbgydTo0Yu2+cJEZyIL7AWX1fYtIgsOBNfYjUOxVXY\niXswBW3KBXMZPsCLFdebJYKyKenrF8Vg3BlQnim3iUo0NWvPwrs4I7FpwSvow3Qcj0+zcTOy4zZR\n4Vbtgw8zReBer3JuM9orOwcL+KUMKAXlPPwm3njKAuzCcVl7YXadxYnNA/hFbDtyFgnNq8dTIrtm\nVjm3XrwYlIR2QgG/WizDx/iuov8d8bBXZO08sNsTm+8xSSnD4IcaD5pyCS4TL+SrKuePVL5+GRcG\nRKZMwI94s4bdLiGaORvFVMt5A+9XjDkMW4a590lCs2qtk1qxW1KJx1toB8WDH1zlXKf4ZrMn6XtV\naElv9r9DKZNydohsaRdTK2U6nhElOhfXGaJ0f5u1u0WW/pUPakT1WSfSOV8Q5vQk53M6cL14i9W0\nKud5oUlrk752UYJvUF5tLheZmgdlIZ4b4TOMCQNKQjtbLJgWV9jcJcpomkWfKQnvcEwSAcnXKi14\nCfeK8p3/rhZZkdtNzcYNp4FVaceNWIElRrZXmIv7RWpuEXuNVqH0fXg0c3a5WFNMqRi/En+KKbVb\nBGmNEMxKenBTdrxc7ar4eTJmhaTq5NSLUAsewZ2ZUw/iVJyTOVuPbiF0KX3J2E6ciI8M1YNFYiO5\nWpTSNhyd2S8RwXyhYswMUa1OU77xS9mJ97LjmapXo2GZg0+EYEGXiPZZI73QKOjH6TXOPaT6ImxM\nqLch3CqE79esnW+42opyKGGT8hVuyhRDS/OYMVKBWSrEar7id75H4Q5Mxlv4Rmz/zxfZ22volBt3\nThD7k65xvm8HTsa5mQ+j/ig01nSJjzF5udzvv+1Ow+1KOnIKLmicO8VTT1MOFEK7V2k12SXK5bYC\n/Woo9Zb5k/FwRd+g/3FAmjRp0mSs+Rvvgds8ldAxMgAAAABJRU5ErkJggg==\n",
- "prompt_number": 40,
+ "prompt_number": 21,
"text": [
"",
"log(2)",
@@ -398,7 +398,7 @@
]
}
],
- "prompt_number": 40
+ "prompt_number": 21
},
{
"cell_type": "code",
@@ -410,13 +410,13 @@
"outputs": [
{
"output_type": "pyout",
- "prompt_number": 41,
+ "prompt_number": 22,
"text": [
"(0.69314718056-0j)"
]
}
],
- "prompt_number": 41
+ "prompt_number": 22
},
{
"cell_type": "code",
@@ -428,13 +428,240 @@
"outputs": [
{
"output_type": "pyout",
- "prompt_number": 42,
+ "prompt_number": 23,
"text": [
"(0.69314718056-0j)"
]
}
],
- "prompt_number": 42
+ "prompt_number": 23
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "## Density operators with Tensor Products as args"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "from sympy.core.trace import Tr",
+ "",
+ "A, B, C, D = symbols('A B C D',commutative=False)",
+ "",
+ "t1 = TensorProduct(A,B,C)",
+ "",
+ "d = Density([t1, 1.0])",
+ "d.doit()",
@flacjacket Collaborator

To display this result, you'll either need to split the cell here or use display() from IPython.core.display

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
+ "",
+ "t2 = TensorProduct(A,B)",
+ "t3 = TensorProduct(C,D)",
+ "",
+ "d = Density([t2, 0.5], [t3, 0.5])",
+ "d.doit() "
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$0.5 \\left({A A^{\\dagger}}\\right)\\otimes \\left({B B^{\\dagger}}\\right) + 0.5 \\left({C C^{\\dagger}}\\right)\\otimes \\left({D D^{\\dagger}}\\right)$$"
+ ],
+ "output_type": "pyout",
+ "png": "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\n",
+ "prompt_number": 24,
+ "text": [
+ "",
+ " \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e",
+ "0.5\u22c5\u239dA\u22c5A \u23a0\u2a02 \u239dB\u22c5B \u23a0 + 0.5\u22c5\u239dC\u22c5C \u23a0\u2a02 \u239dD\u22c5D \u23a0"
+ ]
+ }
+ ],
+ "prompt_number": 24
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "#mixed states",
+ "d = Density([t2+t3, 1.0])",
+ "d.doit() "
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$1.0 \\left({A A^{\\dagger}}\\right)\\otimes \\left({B B^{\\dagger}}\\right) + 1.0 \\left({A C^{\\dagger}}\\right)\\otimes \\left({B D^{\\dagger}}\\right) + 1.0 \\left({C A^{\\dagger}}\\right)\\otimes \\left({D B^{\\dagger}}\\right) + 1.0 \\left({C C^{\\dagger}}\\right)\\otimes \\left({D D^{\\dagger}}\\right)$$"
+ ],
+ "output_type": "pyout",
+ "png": "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\n",
+ "prompt_number": 25,
+ "text": [
+ "",
+ " \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b \u2020\u239e \u239b ",
+ "1.0\u22c5\u239dA\u22c5A \u23a0\u2a02 \u239dB\u22c5B \u23a0 + 1.0\u22c5\u239dA\u22c5C \u23a0\u2a02 \u239dB\u22c5D \u23a0 + 1.0\u22c5\u239dC\u22c5A \u23a0\u2a02 \u239dD\u22c5B \u23a0 + 1.0\u22c5\u239dC\u22c5C \u23a0\u2a02 \u239dD\u22c5",
+ "",
+ " \u2020\u239e",
+ "D \u23a0"
+ ]
+ }
+ ],
+ "prompt_number": 25
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "## Trace operators on Density Operators with Spin States"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "from sympy.physics.quantum.density import Density",
+ "from sympy.physics.quantum.spin import (",
+ " Jx, Jy, Jz, Jplus, Jminus, J2,",
+ " JxBra, JyBra, JzBra,",
+ " JxKet, JyKet, JzKet,",
+ ")",
+ "from sympy.core.trace import Tr",
+ "",
+ "d = Density([JzKet(1,1),0.5],[JzKet(1,-1),0.5]);",
+ "t = Tr(d); ",
+ "",
+ "display_pretty(t)",
+ "print t.doit()"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "output_type": "display_data",
+ "text": [
+ "Tr(\u03c1((\u27581,1\u27e9, 0.5),(\u27581,-1\u27e9, 0.5)))"
+ ]
+ },
+ {
+ "output_type": "stream",
+ "stream": "stdout",
+ "text": [
+ "1.00000000000000"
+ ]
+ }
+ ],
+ "prompt_number": 26
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "## Partial Trace on Density Operators with Mixed State"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "#Partial trace on mixed state",
+ "from sympy.core.trace import Tr",
+ "",
+ "A, B, C, D = symbols('A B C D',commutative=False)",
+ "",
+ "t1 = TensorProduct(A,B,C)",
+ "",
+ "d = Density([t1, 1.0])",
+ "d.doit()",
+ "",
+ "t2 = TensorProduct(A,B)",
+ "t3 = TensorProduct(C,D)",
+ "",
+ "d = Density([t2, 0.5], [t3, 0.5])",
+ "",
+ "",
+ "tr = Tr(d,[1])",
+ "tr.doit()"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$0.5 A A^{\\dagger} \\mbox{Tr}\\left(B B^{\\dagger}\\right) + 0.5 C C^{\\dagger} \\mbox{Tr}\\left(D D^{\\dagger}\\right)$$"
+ ],
+ "output_type": "pyout",
+ "prompt_number": 27,
+ "text": [
+ "",
+ " \u2020 \u2020 \u2020 \u2020 ",
+ "0.5\u22c5A\u22c5A \u22c5Tr(B\u22c5B ) + 0.5\u22c5C\u22c5C \u22c5Tr(D\u22c5D )"
+ ]
+ }
+ ],
+ "prompt_number": 27
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "## Partial Trace on Density Operators with Spin states"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "from sympy.physics.quantum.density import Density",
+ "from sympy.physics.quantum.spin import (",
+ " Jx, Jy, Jz, Jplus, Jminus, J2,",
+ " JxBra, JyBra, JzBra,",
+ " JxKet, JyKet, JzKet,",
+ ")",
+ "from sympy.core.trace import Tr",
+ "",
+ "tp1 = TensorProduct(JzKet(1,1), JzKet(1,-1))",
+ "",
+ "#trace out 0 index",
+ "d = Density([tp1,1]);",
+ "t = Tr(d,[0]); ",
+ "",
+ "display_pretty(t)",
+ "display_pretty(t.doit())",
+ "",
+ "#trace out 1 index",
+ "t = Tr(d,[1])",
+ "display_pretty(t)",
+ "t.doit()",
+ ""
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "output_type": "display_data",
+ "text": [
+ "Tr((\u27581,1\u27e9\u2a02 \u27581,-1\u27e9, 1))"
+ ]
+ },
+ {
+ "output_type": "display_data",
+ "text": [
+ "\u27581,-1\u27e9\u27e81,-1\u2758"
+ ]
+ },
+ {
+ "output_type": "display_data",
+ "text": [
+ "Tr((\u27581,1\u27e9\u2a02 \u27581,-1\u27e9, 1))"
+ ]
+ },
+ {
+ "latex": [
+ "$${\\left|1,1\\right\\rangle }{\\left\\langle 1,1\\right|}$$"
+ ],
+ "output_type": "pyout",
+ "png": "iVBORw0KGgoAAAANSUhEUgAAAEwAAAAXCAYAAACh3qkfAAAABHNCSVQICAgIfAhkiAAAAedJREFU\nWIXt2D+I1EAUx/GPB+ohCqIiKqKNFjanveXaKNhaeI2Kglpb2Z2FnYKVgoqNeCDYXecfUgoWgoJy\nCGJhIQhiYWexFtksa8hO/kzYm2K/TSbz8t77zeMxyYQ5UbzYaAGJMq7LQsmwu+Lh/VjHlo7JQv63\nsKdhnHsdc9TRxLeqLiCbGG/DKXzCEIsthTTxX8LNBrFO4EbHHDH6CrJiUO6wgiNYxQA/W4ho6/8B\nx7C5Jt4VPOpRY+z6xmQVcw9067Cm/mexHPDfhzuROWJ9s2IwrcNmyRrOBOxX5YtKghQKNsRbnKyw\nLeIQvsxUUYAUCgZPcKFifhnPZislTCoF+4NfOFyaH+DV7OVMJ5WCwX1cm7gf4M0GaZlKSgUbYtPE\nfUraxqQk6rq8ywpeyrssKfoo2IEeYmyXH5G+leZfy7/GY+lDI5oVbNfourfCdhzf8bijf8FF+Zuy\nzFOcrxNYk6NOYxN9U8lG152j8bp8bxniN97h0sTzB/EVH/2//zT1N/JbDWhawdGK+RiNbfRRfQIK\nG2pY6ehHs6PR3Yj4BTEas2LQ16YfE+ccngfsP7BV3hUx9LLWcpC/HWKcxvuO+ZfwuUHeh7jcMQdx\nGgno29Ey0AJuRwjp6wdiiFiNtK/LnDlzZsM/36lpQdemeFcAAAAASUVORK5CYII=\n",
+ "prompt_number": 28,
+ "text": [
+ "\u27581,1\u27e9\u27e81,1\u2758"
+ ]
+ }
+ ],
+ "prompt_number": 28
},
{
"cell_type": "code",
@@ -442,7 +669,7 @@
"input": [],
"language": "python",
"outputs": [],
- "prompt_number": 42
+ "prompt_number": 28
}
]
}
View
264 examples/notebooks/trace.ipynb
@@ -0,0 +1,264 @@
+{
+ "metadata": {
+ "name": "trace"
+ },
+ "nbformat": 2,
+ "worksheets": [
+ {
+ "cells": [
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [
+ "from sympy import symbols",
+ "from sympy.core.trace import Tr",
+ "from sympy.matrices.matrices import Matrix",
+ "from IPython.core.display import display_pretty",
+ "from sympy.printing.latex import *",
+ "",
+ "%load_ext sympyprinting"
+ ],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 2
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "###Basic Examples"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [
+ "a, b, c, d = symbols('a b c d'); ",
+ "A, B = symbols('A B', commutative=False)",
+ "t = Tr(A*B)"
+ ],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 3
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "t"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$\\mbox{Tr}\\left(A B\\right)$$"
+ ],
+ "output_type": "pyout",
+ "prompt_number": 4,
+ "text": [
+ "Tr(A\u22c5B)"
+ ]
+ }
+ ],
+ "prompt_number": 4
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "latex(t)"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "output_type": "pyout",
+ "prompt_number": 5,
+ "text": [
+ "\\mbox{Tr}\\left(A B\\right)"
+ ]
+ }
+ ],
+ "prompt_number": 5
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "display_pretty(t)"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "output_type": "display_data",
+ "text": [
+ "Tr(\u03c1((\u27581,1\u27e9, 0.5),(\u27581,-1\u27e9, 0.5)))"
+ ]
+ }
+ ],
+ "prompt_number": 14
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "### Using Matrices"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [
+ "t = Tr ( Matrix([ [2,3], [3,4] ]))"
+ ],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 15
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "t"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$6$$"
+ ],
+ "output_type": "pyout",
+ "png": "iVBORw0KGgoAAAANSUhEUgAAAAwAAAASCAYAAABvqT8MAAAABHNCSVQICAgIfAhkiAAAAO5JREFU\nKJHN0r1KQ0EQhuHnhAgBhaiIFpLOxs5O8CIsFG/A1spCL0CwsUtnaat4C7aWNooiCAEJKBb+oMGg\nSCzOHlyWlWDnV+3M7vvN7O7wRxWZXAs7+MIL3rCHXs5gGh0shXgS19isDtQSYB9tnIa4jgZec+5r\n+MD4sHtUOsTlsEP1aL2AeyxiGbNoYgs3KTiqfJVzbET5FTxhLgVmMEAfY1G+FqoepcBIAC4ybZ8p\n/6KoHOATd6F8ql5oeSIG4ARTGaCBLh7TjVW8V05BBZ5xkDECx9j1M2PruIpN0uFrYhvzofcH5ajc\n/lbhH+gb6f4rZTpaz0QAAAAASUVORK5CYII=\n",
+ "prompt_number": 16,
+ "text": [
+ "6"
+ ]
+ }
+ ],
+ "prompt_number": 16
+ },
+ {
+ "cell_type": "markdown",
+ "source": [
+ "### Example using modules in physics.quantum"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [
+ "from sympy.physics.quantum.density import Density",
+ "from sympy.physics.quantum.spin import (",
+ " Jx, Jy, Jz, Jplus, Jminus, J2,",
+ " JxBra, JyBra, JzBra,",
+ " JxKet, JyKet, JzKet,",
+ ")"
+ ],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 7
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "d = Density([JzKet(1,1),0.5],[JzKet(1,-1),0.5]); d"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$\\rho\\left(\\begin{pmatrix}{\\left|1,1\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}{\\left|1,-1\\right\\rangle }, & 0.5\\end{pmatrix}\\right)$$"
+ ],
+ "output_type": "pyout",
+ "prompt_number": 8,
+ "text": [
+ "\u03c1((\u27581,1\u27e9, 0.5),(\u27581,-1\u27e9, 0.5))"
+ ]
+ }
+ ],
+ "prompt_number": 8
+ },
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [
+ "t = Tr(d)"
+ ],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 9
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "t"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$\\mbox{Tr}\\left(\\rho\\left(\\begin{pmatrix}{\\left|1,1\\right\\rangle }, & 0.5\\end{pmatrix},\\begin{pmatrix}{\\left|1,-1\\right\\rangle }, & 0.5\\end{pmatrix}\\right)\\right)$$"
+ ],
+ "output_type": "pyout",
+ "prompt_number": 10,
+ "text": [
+ "Tr(\u03c1((\u27581,1\u27e9, 0.5),(\u27581,-1\u27e9, 0.5)))"
+ ]
+ }
+ ],
+ "prompt_number": 10
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "latex(t)"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "output_type": "pyout",
+ "prompt_number": 11,
+ "text": [
+ "",
+ "\\mbox{Tr}\\left(\\rho\\left(\\begin{pmatrix}{\\left|1,1\\right\\rangle }, & 0.5\\end{p",
+ "matrix},\\begin{pmatrix}{\\left|1,-1\\right\\rangle }, & 0.5\\end{pmatrix}\\right)\\r",
+ "ight)"
+ ]
+ }
+ ],
+ "prompt_number": 11
+ },
+ {
+ "cell_type": "code",
+ "collapsed": false,
+ "input": [
+ "t.doit()"
+ ],
+ "language": "python",
+ "outputs": [
+ {
+ "latex": [
+ "$$1.0$$"
+ ],
+ "output_type": "pyout",
+ "png": "iVBORw0KGgoAAAANSUhEUgAAABsAAAASCAYAAACq26WdAAAABHNCSVQICAgIfAhkiAAAASNJREFU\nOI3t1EErBGEcx/HPimLXgUiU5eKinGxyc8KLkLeDK+WqpChcpJQjBxc33JALsgfFwYrEOsws0za7\nBpOT3+U/z/eZZ77PMzPPwx8mU4P3Yg8DCZ/TjDlkUQzbqziuNyiHSZyinFAEy1iLtMdxja5aAwax\nhVkcfEPWjxdMVPErrCSdaVLZPB4Fry6aJdyioQIa/D4FXOKpip+jA0NpyrrxEMNLYe1JW1aK4RXW\nlqbsGW8xvCmsH31pyE5q8FxYb9KUHaM9hreGtZi2LB/DR3Av+FN/JcujJbw+EqxsNNLfiDEsCr5p\n3WwLNnXccVPAK3bDdgab2PA5+SnBduisJejCPs5CURl3OMR05L4+XGAmwrKCk2QdC9jB8Fcr+s+P\n8g572TfbrLZhHwAAAABJRU5ErkJggg==\n",
+ "prompt_number": 12,
+ "text": [
+ "1.00000000000000"
+ ]
+ }
+ ],
+ "prompt_number": 12
+ },
+ {
+ "cell_type": "code",
+ "collapsed": true,
+ "input": [],
+ "language": "python",
+ "outputs": [],
+ "prompt_number": 12
+ }
+ ]
+ }
+ ]
+}
View
30 sympy/core/tests/test_trace.py
@@ -1,4 +1,4 @@
-from sympy import S, Symbol, symbols, Matrix
+from sympy import S, Symbol, symbols, Matrix, Tuple
from sympy.core.trace import Tr
def test_trace_new():
@@ -19,6 +19,8 @@ def test_trace_new():
assert Tr(a*C*A*D*B*2) == 2*a*Tr(A*D*B*C)
assert Tr(B*A*C*B*A) == Tr(A*C*B*A*B)
assert Tr(A*C*B*A*B) == Tr(A*B*A*C*B)
+ assert Tr(A*A*B*B) == Tr(A**2*B**2)
+ assert Tr(A*B*B*A) == Tr(A**2*B**2)
# since A is symbol and not commutative
assert isinstance(Tr(A), Tr)
@@ -32,14 +34,32 @@ def test_trace_new():
assert Tr(M) == 3
#trace indices test
- t = Tr((A+B), (2))
- assert t.args[0].args[1] == (2) and t.args[1].args[1] == (2)
+ t = Tr((A+B), [2])
+ assert t.args[0].args[1] == Tuple(2) and t.args[1].args[1] == Tuple(2)
- t = Tr(a*A, (2,3))
- assert t.args[1].args[1] == (2,3)
+ t = Tr(a*A, [2,3])
+ assert t.args[1].args[1] == Tuple(2,3)
def test_trace_doit():
a, b, c, d = symbols('a b c d')
A, B, C, D = symbols('A B C D', commutative=False)
#TODO: needed while testing reduced density operations, etc.
+
+#def test_permute():
+# A, B, C, D, E, F, G = symbols('A B C D E F G', commutative=False)
+# t = Tr(A*B*C*D*E*F*G, cycle=False)
+
+# assert t.permute(0).args[0].args == (A, B, C, D, E, F, G)
+# assert t.permute(2).args[0].args == (F, G, A, B, C, D, E)
+# assert t.permute(4).args[0].args == (D, E, F, G, A, B, C)
+# assert t.permute(6).args[0].args == (B, C, D, E, F, G, A)
+# assert t.permute(8).args[0].args == t.permute(1).args[0].args
+
+# assert t.permute(-1).args[0].args == (B, C, D, E, F, G, A)
+# assert t.permute(-3).args[0].args == (D, E, F, G, A, B, C)
+# assert t.permute(-5).args[0].args == (F, G, A, B, C, D, E)
+# assert t.permute(-8).args[0].args == t.permute(-1).args[0].args
+
+# t = Tr((A+B)*(B*B)*C*D,cycle=False)
+# assert t.permute(2).args[0].args == (C, D, (A+B), (B**2))
View
85 sympy/core/trace.py
@@ -1,4 +1,4 @@
-from sympy import Expr, Add, Mul, Matrix, Pow, sympify, Matrix
+from sympy import Expr, Add, Mul, Matrix, Pow, sympify, Matrix, Tuple
def _is_scalar(e):
""" Helper method used in Tr"""
@@ -15,7 +15,17 @@ def _is_scalar(e):
return False
def _cycle_permute(l):
- """ Cyclic permutations based on canonical ordering"""
+ """ Cyclic permutations based on canonical ordering
+
+ This method does the sort based ascii values while
+ a better approach would be to used lexicographic sort.
+ TODO: Handle condition such as symbols have subscripts/superscripts
+ in case of lexicographic sort
+
+ """
+
+ if len(l) == 1:
+ return l
min_item = min(l)
indices = [i for i, x in enumerate(l) if x == min_item]
@@ -39,6 +49,19 @@ def _cycle_permute(l):
return ordered_l
+
+def _rearrange_args(l):
+ """ this just moves the last arg to first position
+ to enable expansion of args
+ A,B,A ==> A**2,B
+ """
+ if len(l) == 1:
+ return l
+
+ x = list(l[-1:])
+ x.extend(l[0:-1])
+ return Mul(*x).args
+
class Tr(Expr):
""" Generic Trace operation than can trace over:
@@ -63,20 +86,24 @@ class Tr(Expr):
>>> from sympy import symbols, Matrix
>>> a, b = symbols('a b', commutative=True)
>>> A, B = symbols('A B', commutative=False)
- >>> Tr(a*A,2)
- a*Tr(A, 2)
+ >>> Tr(a*A,[2])
+ a*Tr(A)
>>> m = Matrix([[1,2],[1,1]])
>>> Tr(m)
2
"""
-
def __new__(cls, *args):
""" Construct a Trace object.
+ Parameters
+ ==========
+ args = sympy expression
+
"""
+
expr = args[0]
- indices = args[1] if len(args) == 2 else -1 #-1 indicates full trace
+ indices = Tuple(*args[1]) if len(args) == 2 else Tuple()
if isinstance(expr, Matrix):
return expr.trace()
elif hasattr(expr, 'trace') and callable(t.x):
@@ -89,10 +116,8 @@ def __new__(cls, *args):
if len(nc_part) == 0:
return Mul(*c_part)
else:
- # cyclic permute nc_part for canonical ordering
- nc_part_ordered = _cycle_permute(nc_part)
- return Mul(*c_part) * Expr.__new__(cls, Mul(*nc_part_ordered),
- indices)
+ nc_part_ordered = _cycle_permute(_rearrange_args(nc_part))
+ return Mul(*c_part) * Expr.__new__(cls, Mul(*nc_part_ordered), indices )
elif isinstance(expr, Pow):
if (_is_scalar(expr.args[0]) and
_is_scalar(expr.args[1])):
@@ -118,7 +143,7 @@ def doit(self,**kwargs):
"""
if hasattr(self.args[0], '_eval_trace'):
- return self.args[0]._eval_trace()
+ return self.args[0]._eval_trace(indices=self.args[1])
return self
@@ -126,5 +151,41 @@ def doit(self,**kwargs):
def is_number(self):
#TODO : This function to be reviewed
# and implementation improved.
-
return True
+
+
+ #TODO: Review if the permute method is needed
+ # and if it needs to return a new instance
+ #def permute(self, pos):
@ellisonbg Owner

I would like to have the permute method and it should return a new instance.

@ellisonbg Actually, I had started a discussion on this on the mailing list. http://bit.ly/M7D9wF

I can work on this and see how we can achieve this. I will add to my TODO. In the subsequent PR, I will update this method based on how we decide to do it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
+ """ Permute the arguments cyclically.
+
+ # Parameters
+ # ==========
+ # pos : integer, if positive, shift-right, else shift-left
+
+ # Examples
+ =========
+
+ # >>> from sympy.core.trace import Tr
+ # >>> t = Tr(A*B*C*D, 2, cycle=False)
+ # >>> t.permute(2)
+ # Tr(C*D*A*B,2)
+
+ # """
+ # if pos > 0:
+ # pos = pos % len(self.args[0].args)
+ # else:
+ # pos = - (abs(pos) % len(self.args[0].args))
+ # #print self.args[0].args[pos:] + self.args[0].args[0:pos]
+
+ # args = list(self.args[0].args[-pos:] + self.args[0].args[0:-pos])
+ # print 'args==' , args, Mul(*(args)), self.args[1], type(self.args[1])
+
+ # x = Tr(Mul(*(args)), 2, cycle=False)
+
+ # print id(x), x
+ # return x
+
+
+ def _hashable_content(self):
+ return self.args[0] + tuple(self.args[1])
View
21 sympy/physics/quantum/density.py
@@ -8,6 +8,8 @@
from sympy.physics.quantum.qubit import Qubit
from sympy.physics.quantum.qapply import qapply
from matrixutils import numpy_ndarray, scipy_sparse_matrix, to_numpy
+from sympy.physics.quantum.tensorproduct import TensorProduct, tensor_product_simp
+from sympy.core.compatibility import product
class Density(HermitianOperator):
"""Density operator for representing mixed states.
@@ -157,12 +159,26 @@ def doit(self, **hints):
0.5*|0><0| + 0.5*|1><1|
"""
+
terms = []
for (state, prob) in self.args:
- terms.append(prob*(state*Dagger(state)))
+ state = state.expand() # needed to break up (a+b)*c
+ if (isinstance(state, Add)):
+ for arg in product(state.args, repeat=2):
+ terms.append(prob *
+ self._generate_outer_prod(arg[0], arg[1]))
@ellisonbg Owner

The _generate_outer_product method should be called _generate_tensor_product to be consistent with our naming. Also, can you summarize what this method does and why it is needed?

@ellisonbg I am guessing you were commenting on the _generate_outer_prod in tensor_product. I plan to remove that function.

The function here is just to reuse code needed within the for and if constructs. Am I in sync?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
+ else:
+ terms.append(prob *
+ self._generate_outer_prod(state,state))
return Add(*terms)
+ def _generate_outer_prod(self,arg1,arg2):
+ if (isinstance(arg1, TensorProduct)):
+ return tensor_product_simp(arg1 * Dagger(arg2))
+ else:
+ return (arg1*Dagger(arg2))
+
def _represent(self, **options):
return represent(self.doit(), **options)
@@ -173,7 +189,8 @@ def _print_operator_name_pretty(self, printer, *args):
return prettyForm(u"\u03C1")
def _eval_trace(self, **kwargs):
- return Tr(self.doit()).doit()
+ indices = kwargs.get('indices',[])
+ return Tr(self.doit(), indices).doit()
def entropy(self):
""" Compute the entropy of a density matrix.
View
10 sympy/physics/quantum/tensorproduct.py
@@ -12,6 +12,7 @@
scipy_sparse_matrix,
matrix_tensor_product
)
+from sympy.core.trace import Tr
__all__ = [
'TensorProduct',
@@ -196,6 +197,15 @@ def expand(self, **hints):
tp = TensorProduct(*[sympify(item).expand(**hints) for item in self.args])
return Expr.expand(tp, **hints)
+ def _eval_trace(self, **kwargs):
+ indices = kwargs.get('indices', None)
+ exp = tensor_product_simp(self)
+
+ if indices is None or len(indices) == 0:
+ return Mul(*[Tr(arg).doit() for arg in exp.args])
+ else:
+ return Mul(*[Tr(value).doit() if idx in indices else value
+ for idx, value in enumerate(exp.args)])
def tensor_product_simp_Mul(e):
"""Simplify a Mul with TensorProducts.
View
49 sympy/physics/quantum/tests/test_density.py
@@ -14,6 +14,7 @@
from sympy.functions import sqrt
from sympy.utilities.pytest import raises
from sympy.physics.quantum.matrixutils import scipy_sparse_matrix
+from sympy.physics.quantum.tensorproduct import TensorProduct
def test_eval_args():
@@ -31,7 +32,9 @@ def test_eval_args():
raises(ValueError, lambda: Density([Ket(0)], [Ket(1)]))
def test_doit():
+
x,y = symbols('x y')
+ A, B, C, D, E, F= symbols('A B C D E F', commutative=False)
d = Density([XKet(),0.5], [PxKet(),0.5])
assert (0.5*(PxKet()*Dagger(PxKet())) +
0.5*(XKet()*Dagger(XKet()))) == d.doit()
@@ -41,6 +44,52 @@ def test_doit():
assert (0.5*(PxKet(x*y)*Dagger(PxKet(x*y))) +
0.5*(XKet(x*y)*Dagger(XKet(x*y)))) == d_with_sym.doit()
+
+ d = Density([(A+B)*C, 1.0])
+ assert d.doit() == (1.0*A*C*Dagger(C)*Dagger(A) +
+ 1.0*A*C*Dagger(C)*Dagger(B) +
+ 1.0*B*C*Dagger(C)*Dagger(A) +
+ 1.0*B*C*Dagger(C)*Dagger(B))
+
+
+ # With TensorProducts as args
+
+ # Density with simple tensor products as args
+ t = TensorProduct(A, B, C)
+ d = Density([t, 1.0])
+ assert d.doit() == 1.0 * TensorProduct(A*Dagger(A), B*Dagger(B),C*Dagger(C))
+
+ # Density with multiple Tensorproducts as states
+ t2 = TensorProduct(A,B)
+ t3 = TensorProduct(C,D)
+
+ d = Density([t2, 0.5], [t3, 0.5])
+ assert d.doit() == (0.5 * TensorProduct(A*Dagger(A), B*Dagger(B)) +
+ 0.5 * TensorProduct(C*Dagger(C), D*Dagger(D)))
+
+ #Density with mixed states
+ d = Density([t2+t3,1.0])
+ assert d.doit() == (1.0 * TensorProduct(A*Dagger(A), B*Dagger(B)) +
+ 1.0 * TensorProduct(A*Dagger(C), B*Dagger(D)) +
+ 1.0 * TensorProduct(C*Dagger(A), D*Dagger(B)) +
+ 1.0 * TensorProduct(C*Dagger(C), D*Dagger(D)))
+
+
+ #Density operators with spin states
+ tp1 = TensorProduct(JzKet(1,1), JzKet(1,-1))
+ tp2 = TensorProduct(JzKet(1,-1/2), JzKet(1,-1/2))
@jrioux Collaborator
jrioux added a note

To avoid the python 3 problem this could be written tp2 = TensorProduct(JzKet(1,-S(1)/2), JzKet(1,-S(1)/2))

@asmeurer Owner

Note that in Python 2, this is giving 0, because you aren't using future division. Try adding from __future__ import division to the top of file.

I guess the question is if you want this to work with floating point half numbers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
+
+ d = Density([tp1, 1])
+ t = Tr(d);
+ assert t.doit() == 1
+
+ #Partial trace on density operators with spin states
+ t = Tr(d, [0])
+ assert t.doit() == JzKet(1,-1) * Dagger(JzKet(1,-1))
+
+ t = Tr(d, [1])
+ assert t.doit() == JzKet(1,1) * Dagger(JzKet(1,1))
+
def test_apply_op():
d = Density([Ket(0), 0.5], [Ket(1), 0.5])
assert d.apply_op(XOp()) == Density([XOp()*Ket(0), 0.5],
View
52 sympy/physics/quantum/tests/test_tensorproduct.py
@@ -7,7 +7,8 @@
from sympy.physics.quantum.dagger import Dagger
from sympy.physics.quantum.qubit import Qubit, QubitBra
from sympy.physics.quantum.operator import OuterProduct
-
+from sympy.physics.quantum.density import Density
+from sympy.core.trace import Tr
A,B,C = symbols('A,B,C', commutative=False)
x = symbols('x')
@@ -51,3 +52,52 @@ def test_issue_2824():
# module, but the following is a test from the issue that used to raise.
assert TensorProduct(1, Qubit('1')*Qubit('1').dual) == \
TensorProduct(1, OuterProduct(Qubit(1), QubitBra(1)))
+
+def test_eval_trace():
+ # This test includes tests with dependencies between TensorProducts
+ #and density operators. Since, the test is more to test the behavior of
+ #TensorProducts it remains here
+
+ A, B, C, D, E, F= symbols('A B C D E F', commutative=False)
+
+ # Density with simple tensor products as args
+ t = TensorProduct(A, B)
+ d = Density([t, 1.0])
+ tr = Tr(d)
+ assert tr.doit() == 1.0*Tr(A*Dagger(A))*Tr(B*Dagger(B))
+
+ ## partial trace with simple tensor products as args
+ t = TensorProduct(A, B, C)
+ d = Density([t, 1.0])
+ tr = Tr(d,[1])
+ assert tr.doit() == 1.0*A*Dagger(A)*Tr(B*Dagger(B))*C*Dagger(C)
+
+ tr = Tr(d, [0, 2])
+ assert tr.doit() == 1.0*Tr(A*Dagger(A))*B*Dagger(B)*Tr(C*Dagger(C))
+
+ # Density with multiple Tensorproducts as states
+ t2 = TensorProduct(A, B)
+ t3 = TensorProduct(C, D)
+
+ d = Density([t2, 0.5], [t3, 0.5])
+ t = Tr(d)
+ assert t.doit() == (0.5*Tr(A*Dagger(A))*Tr(B*Dagger(B)) +
+ 0.5*Tr(C*Dagger(C))*Tr(D*Dagger(D)))
+
+ t = Tr(d, [0])
+ assert t.doit() == (0.5*Tr(A*Dagger(A))*B*Dagger(B) +
+ 0.5*Tr(C*Dagger(C))*D*Dagger(D))
+
+ #Density with mixed states
+ d = Density([t2+t3, 1.0])
+ t = Tr(d)
+ assert t.doit() == ( 1.0*Tr(A*Dagger(A))*Tr(B*Dagger(B)) +
+ 1.0*Tr(A*Dagger(C))*Tr(B*Dagger(D)) +
+ 1.0*Tr(C*Dagger(A))*Tr(D*Dagger(B)) +
+ 1.0*Tr(C*Dagger(C))*Tr(D*Dagger(D)))
+
+ t = Tr(d, [1] )
+ assert t.doit() == ( 1.0*A*Dagger(A)*Tr(B*Dagger(B)) +
+ 1.0*A*Dagger(C)*Tr(B*Dagger(D)) +
+ 1.0*C*Dagger(A)*Tr(D*Dagger(B)) +
+ 1.0*C*Dagger(C)*Tr(D*Dagger(D)))
View
5 sympy/printing/latex.py
@@ -1264,6 +1264,11 @@ def _print_MatrixHomomorphism(self, h):
return r"{%s} : {%s} \to {%s}" % (self._print(h._sympy_matrix()),
self._print(h.domain), self._print(h.codomain))
+ def _print_Tr(self, p):
+ #Todo: Handle indices
+ contents = self._print(p.args[0])
+ return r'\mbox{Tr}\left(%s\right)' % (contents)
+
def latex(expr, **settings):
r"""
View
8 sympy/printing/pretty/pretty.py
@@ -1544,6 +1544,14 @@ def _print_MatrixHomomorphism(self, h):
' %s> ' % hobj('-', 2), self._print(h.codomain)))
return pform
+ def _print_Tr(self, p):
+ #TODO: Handle indices
+ pform = self._print(p.args[0])
+ pform = prettyForm(*pform.left('%s(' % (p.__class__.__name__)))
+ pform = prettyForm(*pform.right(')'))
+ return pform
+
+
def pretty(expr, **settings):
"""Returns a string containing the prettified form of expr.
View
7 sympy/printing/pretty/tests/test_pretty.py
@@ -15,6 +15,7 @@
from sympy.physics.units import joule
from sympy.utilities.pytest import raises, XFAIL
+from sympy.core.trace import Tr
a, b, x, y, z, k = symbols('a,b,x,y,z,k')
th = Symbol('theta')
@@ -3935,3 +3936,9 @@ def test_Homomorphism():
assert upretty(expr) == ucode_str
assert pretty(expr) == ascii_str
+
+def test_Tr():
+ A, B = symbols('A B', commutative=False)
+ t = Tr(A*B)
+ assert pretty(t) == r'Tr(A*B)'
+ assert upretty(t) == u'Tr(A\u22c5B)'
View
3  sympy/printing/str.py
@@ -540,6 +540,9 @@ def _print_NamedMorphism(self, morphism):
def _print_Category(self, category):
return 'Category("%s")' % category.name
+ def _print_Tr(self, expr):
+ #TODO : Handle indices
+ return "%s(%s)" % ("Tr", self._print(expr.args[0]))
def sstr(expr, **settings):
"""Returns the expression as a string.
View
7 sympy/printing/tests/test_latex.py
@@ -15,6 +15,7 @@
from sympy.utilities.pytest import XFAIL, raises
from sympy.functions import DiracDelta
from sympy.logic import Implies
+from sympy.core.trace import Tr
x, y, z, t = symbols('x y z t')
k, n = symbols('k n', integer=True)
@@ -642,3 +643,9 @@ def test_QuotientRing():
assert latex(R) == r"\frac{\mathbb{Q}\left[x\right]}{\left< {x^{2} + 1} \right>}"
assert latex(R.one) == r"{1} + {\left< {x^{2} + 1} \right>}"
+
+def test_Tr():
+ #TODO: Handle indices
+ A, B = symbols('A B', commutative=False)
+ t = Tr(A*B)
+ assert latex(t) == r'\mbox{Tr}\left(A B\right)'
View
6 sympy/printing/tests/test_str.py
@@ -14,6 +14,7 @@
from sympy.utilities.pytest import raises
from sympy.printing import sstr, sstrrepr, StrPrinter
+from sympy.core.trace import Tr
x, y, z, w = symbols('x,y,z,w')
d = Dummy('d')
@@ -489,3 +490,8 @@ def test_categories():
assert str(id_A) == 'IdentityMorphism(Object("A"))'
assert str(K) == 'Category("K")'
+
+def test_Tr():
+ A, B = symbols('A B', commutative=False)
+ t = Tr(A*B)
+ assert str(t) == 'Tr(A*B)'
Something went wrong with that request. Please try again.