| 724 | Class for free modules with a named basis |
| 725 | |
| 726 | INPUT: |
| 727 | |
| 728 | - ``R`` - base ring |
| 729 | |
| 730 | - ``basis_keys`` - list, tuple, family, set, etc. defining the |
| 731 | indexing set for the basis of this module |
| 732 | |
| 733 | - ``element_class`` - the class of which elements of this module |
| 734 | should be instances (optional, default None, in which case the |
| 735 | elements are instances of |
| 736 | :class:`CombinatorialFreeModuleElement`) |
| 737 | |
| 738 | - ``category`` - the category in which this module lies (optional, |
| 739 | default None, in which case use the "category of modules with |
| 740 | basis" over the base ring ``R``) |
| 741 | |
| 742 | Options controlling the printing of elements: |
| 743 | |
| 744 | - ``prefix`` - string, prefix used for printing elements of this |
| 745 | module (optional, default 'B'). With the default, a monomial |
| 746 | indexed by 'a' would be printed as ``B['a']``. |
| 747 | |
| 748 | - ``latex_prefix`` - string, prefix used in the LaTeX |
| 749 | representation of elements (optional, default same value as |
| 750 | ``prefix``). With the default, a monomial indexed by 'a' would |
| 751 | be printed as ``B_{a}``. If this is the empty string, then |
| 752 | don't print monomials as subscripts: the monomial indexed by 'a' |
| 753 | would be printed as ``a``, or as ``[a]`` if ``latex_bracket`` is |
| 754 | True. |
| 755 | |
| 756 | - ``bracket`` - None, bool, string, or list or tuple of |
| 757 | strings (optional, default None): if None, use the value of the |
| 758 | attribute ``self._repr_option_bracket``, which has default value |
| 759 | True. (``self._repr_option_bracket`` is available for backwards |
| 760 | compatibility. Users should set ``bracket`` instead. If |
| 761 | ``bracket`` is set to anything except None, it overrides |
| 762 | the value of ``self._repr_option_bracket``.) If False, do not |
| 763 | include brackets when printing elements: a monomial indexed by |
| 764 | 'a' would be printed as ``B'a'``, and a monomial indexed by |
| 765 | (1,2,3) would be printed as ``B(1,2,3)``. If True, use "[" and |
| 766 | "]" as brackets. If it is one of "[", "(", or "{", use it and |
| 767 | its partner as brackets. If it is any other string, use it as |
| 768 | both brackets. If it is a list or tuple of strings, use the |
| 769 | first entry as the left bracket and the second entry as the |
| 770 | right bracket. |
| 771 | |
| 772 | - ``latex_bracket`` - bool, string, or list or tuple of strings |
| 773 | (optional, default False): if False, do not include brackets in |
| 774 | the LaTeX representation of elements. This option is only |
| 775 | relevant if ``latex_prefix`` is the empty string; otherwise, |
| 776 | brackets are not used regardless. If True, use "\\left[" and |
| 777 | "\\right]" as brackets. If this is one of "[", "(", "\\{", "|", |
| 778 | or "||", use it and its partner, prepended with "\\left" and |
| 779 | "\\right", as brackets. If this is any other string, use it as |
| 780 | both brackets. If this is a list or tuple of strings, use the |
| 781 | first entry as the left bracket and the second entry as the |
| 782 | right bracket. |
| 783 | |
| 784 | - ``scalar_mult`` - string to use for scalar multiplication in |
| 785 | the print representation (optional, default "*") |
| 786 | |
| 787 | These print options may also be accessed and modified using the |
| 788 | :meth:`print_options` method, after the module has been defined. |
| 789 | |
| 845 | sage: F2 = CombinatorialFreeModule(QQ, [1,2,3,4], prefix='F') |
| 846 | sage: F2 == F |
| 847 | False |
| 848 | |
| 849 | Because of this, if you create a free module with certain |
| 850 | parameters and then modify its prefix or other print options, this |
| 851 | affects all modules which were defined using the same parameters:: |
| 852 | |
| 853 | sage: F2.print_options(prefix='x') |
| 854 | sage: F2.prefix() |
| 855 | 'x' |
| 856 | sage: F3 = CombinatorialFreeModule(QQ, [1,2,3,4], prefix='F') |
| 857 | sage: F3 is F2 # F3 was defined just like F2 |
| 858 | True |
| 859 | sage: F3.prefix() |
| 860 | 'x' |
| 861 | sage: F4 = CombinatorialFreeModule(QQ, [1,2,3,4], prefix='F', bracket=True) |
| 862 | sage: F4 == F2 # F4 was NOT defined just like F2 |
| 863 | False |
| 864 | sage: F4.prefix() |
| 865 | 'F' |
| 866 | |
| 867 | The default category is the category of modules with basis over |
| 868 | the base ring:: |
| 869 | |
| 870 | sage: CombinatorialFreeModule(GF(3), ((1,2), (3,4))).category() |
| 871 | Category of modules with basis over Finite Field of size 3 |
| 872 | |
| 873 | See :mod:`sage.categories.examples.algebras_with_basis` and |
| 874 | :mod:`sage.categories.examples.hopf_algebras_with_basis` for |
| 875 | illustrations of the use of the ``category`` keyword, and see |
| 876 | :class:`sage.combinat.root_system.weight_space.WeightSpace` for an |
| 877 | example of the use of ``element_class``. |
| 878 | |
| 879 | Customizing print and LaTeX representations of elements:: |
| 880 | |
| 881 | sage: F = CombinatorialFreeModule(QQ, ['a','b'], prefix='x') |
| 882 | sage: e = F.basis() |
| 883 | sage: e['a'] - 3 * e['b'] |
| 884 | x['a'] - 3*x['b'] |
| 885 | |
| 886 | sage: F.print_options(prefix='x', scalar_mult=' ', bracket='{') |
| 887 | sage: e['a'] - 3 * e['b'] |
| 888 | x{'a'} - 3 x{'b'} |
| 889 | sage: latex(e['a'] - 3 * e['b']) |
| 890 | x_{a} + \left(-3\right)x_{b} |
| 891 | |
| 892 | sage: F.print_options(latex_prefix='y') |
| 893 | sage: latex(e['a'] - 3 * e['b']) |
| 894 | y_{a} + \left(-3\right)y_{b} |
| 895 | |
| 896 | sage: F = CombinatorialFreeModule(QQ, [(1,2), (3,4)]) |
| 897 | sage: e = F.basis() |
| 898 | sage: e[(1,2)] - 3 * e[(3,4)] |
| 899 | B[(1, 2)] - 3*B[(3, 4)] |
| 900 | |
| 901 | sage: F.print_options(bracket=['_{', '}']) |
| 902 | sage: e[(1,2)] - 3 * e[(3,4)] |
| 903 | B_{(1, 2)} - 3*B_{(3, 4)} |
| 904 | |
| 905 | sage: F.print_options(prefix='', bracket=False) |
| 906 | sage: e[(1,2)] - 3 * e[(3,4)] |
| 907 | (1, 2) - 3*(3, 4) |
| 996 | # printing options for elements. These include self._prefix |
| 997 | # (set when initializing self) and self._repr_option_bracket |
| 998 | # (declared to be True by default, needs to be overridden |
| 999 | # explicitly). |
| 1000 | self._print_options = {} |
| 1001 | self._print_options['prefix'] = self._prefix |
| 1002 | # 'bracket': its default value here is None, meaning that |
| 1003 | # the value of self._repr_option_bracket is used; the default |
| 1004 | # value of that attribute is True -- see immediately before |
| 1005 | # the method _repr_term. If 'bracket' is any value |
| 1006 | # except None, then it overrides the value of |
| 1007 | # self._repr_option_bracket. Future users might consider |
| 1008 | # using 'bracket' instead of _repr_option_bracket. |
| 1009 | self._print_options['bracket'] = kwds.get('bracket', None) |
| 1010 | self._print_options['latex_bracket'] = kwds.get('latex_bracket', False) |
| 1011 | self._print_options['latex_prefix'] = kwds.get('latex_prefix', self._prefix) |
| 1012 | self._print_options['scalar_mult'] = kwds.get('scalar_mult', "*") |
| 1013 | |
| 1372 | def print_options(self, **kwds): |
| 1373 | """ |
| 1374 | Return the current print options, or set an option. |
| 1375 | |
| 1376 | INPUT: all of the input is optional; if present, it should be |
| 1377 | in the form of keyword pairs, such as |
| 1378 | ``latex_bracket='('``. The allowable keywords are: |
| 1379 | |
| 1380 | - ``prefix`` |
| 1381 | - ``latex_prefix`` |
| 1382 | - ``bracket`` |
| 1383 | - ``latex_bracket`` |
| 1384 | - ``scalar_mult`` |
| 1385 | - ``tensor_symbol`` |
| 1386 | |
| 1387 | See the documentation for :class:`CombinatorialFreeModule` for |
| 1388 | descriptions of the effects of setting each of these options. |
| 1389 | |
| 1390 | OUTPUT: if the user provides any input, set the appropriate |
| 1391 | option(s) and return nothing. Otherwise, return the |
| 1392 | dictionary of settings for print and LaTeX representations. |
| 1393 | |
| 1394 | EXAMPLES:: |
| 1395 | |
| 1396 | sage: F = CombinatorialFreeModule(ZZ, [1,2,3], prefix='x') |
| 1397 | sage: F.print_options() |
| 1398 | {'latex_bracket': False, 'prefix': 'x', 'bracket': None, 'scalar_mult': '*', 'latex_prefix': 'x'} |
| 1399 | sage: F.print_options(bracket='(') |
| 1400 | sage: F.print_options() |
| 1401 | {'latex_bracket': False, 'prefix': 'x', 'bracket': '(', 'scalar_mult': '*', 'latex_prefix': 'x'} |
| 1402 | """ |
| 1403 | # don't just use kwds.get(...) because I want to distinguish |
| 1404 | # between an argument like "option=None" and the option not |
| 1405 | # being there altogether. |
| 1406 | args = False |
| 1407 | if 'prefix' in kwds: |
| 1408 | args = True |
| 1409 | prefix = kwds['prefix'] |
| 1410 | self._prefix = prefix |
| 1411 | self._print_options['prefix'] = prefix |
| 1412 | if 'latex_prefix' not in kwds: |
| 1413 | self._print_options['latex_prefix'] = prefix |
| 1414 | |
| 1415 | for option in ['latex_prefix', 'bracket', 'latex_bracket', |
| 1416 | 'scalar_mult', 'tensor_symbol']: |
| 1417 | if option in kwds: |
| 1418 | args = True |
| 1419 | self._print_options[option] = kwds[option] |
| 1420 | |
| 1421 | if not args: |
| 1422 | return self._print_options |
| 1423 | return |
| 1424 | |
1205 | | The output can be customized by mean of: |
1206 | | - self.prefix() |
1207 | | - self._repr_option_bracket # TODO: find a good name |
1208 | | (suggestions: _repr_with_bracket or _repr_add_bracket) |
| 1431 | The output can be customized by setting any of the following |
| 1432 | options when initializing the module: |
| 1433 | |
| 1434 | - prefix |
| 1435 | - bracket |
| 1436 | - scalar_mult |
| 1437 | |
| 1438 | Alternatively, one can use the :meth:`print_options` method |
| 1439 | to achieve the same effect. To modify the bracket setting, |
| 1440 | one can also set ``self._repr_option_bracket`` as long as one |
| 1441 | has *not* set the ``bracket`` option: if the |
| 1442 | ``bracket`` option is anything but ``None``, it overrides |
| 1443 | the value of ``self._repr_option_bracket``. |
| 1444 | |
| 1445 | See the documentation for :class:`CombinatorialFreeModule` for |
| 1446 | details on the initialization options. |
| 1505 | def _latex_term(self, m): |
| 1506 | """ |
| 1507 | Returns a string for the LaTeX code for the basis element |
| 1508 | indexed by m. |
| 1509 | |
| 1510 | The output can be customized by setting any of the following |
| 1511 | options when initializing the module: |
| 1512 | |
| 1513 | - prefix |
| 1514 | - latex_prefix |
| 1515 | - latex_bracket |
| 1516 | |
| 1517 | (Alternatively, one can use the :meth:`print_options` method |
| 1518 | to achieve the same effect.) |
| 1519 | |
| 1520 | See the documentation for :class:`CombinatorialFreeModule` for |
| 1521 | details on the initialization options. |
| 1522 | |
| 1523 | EXAMPLES:: |
| 1524 | |
| 1525 | sage: F = CombinatorialFreeModule(QQ, ['a', 'b', 'c']) |
| 1526 | sage: e = F.basis() |
| 1527 | sage: latex(e['a'] + 2*e['b']) # indirect doctest |
| 1528 | B_{a} + 2B_{b} |
| 1529 | |
| 1530 | sage: F = CombinatorialFreeModule(QQ, ['a', 'b', 'c'], prefix="C") |
| 1531 | sage: e = F.basis() |
| 1532 | sage: latex(e['a'] + 2*e['b']) # indirect doctest |
| 1533 | C_{a} + 2C_{b} |
| 1534 | |
| 1535 | sage: QS3 = CombinatorialFreeModule(QQ, Permutations(3), prefix="") |
| 1536 | sage: a = 2*QS3([1,2,3])+4*QS3([3,2,1]) |
| 1537 | sage: latex(a) # indirect doctest |
| 1538 | 2[1, 2, 3] + 4[3, 2, 1] |
| 1539 | sage: QS3.print_options(latex_bracket=True) |
| 1540 | sage: latex(a) # indirect doctest |
| 1541 | 2\left[[1, 2, 3]\right] + 4\left[[3, 2, 1]\right] |
| 1542 | sage: QS3.print_options(latex_bracket="(") |
| 1543 | sage: latex(a) # indirect doctest |
| 1544 | 2\left([1, 2, 3]\right) + 4\left([3, 2, 1]\right) |
| 1545 | sage: QS3.print_options(latex_bracket=('\\myleftbracket', '\\myrightbracket')) |
| 1546 | sage: latex(a) # indirect doctest |
| 1547 | 2\myleftbracket[1, 2, 3]\myrightbracket + 4\myleftbracket[3, 2, 1]\myrightbracket |
| 1548 | |
| 1549 | TESTS:: |
| 1550 | |
| 1551 | sage: F = CombinatorialFreeModule(QQ, [('a', 'b'), (0,1,2)]) |
| 1552 | sage: e = F.basis() |
| 1553 | sage: latex(e[('a','b')]) # indirect doctest |
| 1554 | B_{\left(a, b\right)} |
| 1555 | sage: latex(2*e[(0,1,2)]) # indirect doctest |
| 1556 | 2B_{\left(0, 1, 2\right)} |
| 1557 | sage: F = CombinatorialFreeModule(QQ, [('a', 'b'), (0,1,2)], prefix="") |
| 1558 | sage: e = F.basis() |
| 1559 | sage: latex(2*e[(0,1,2)]) # indirect doctest |
| 1560 | 2\left(0, 1, 2\right) |
| 1561 | """ |
| 1562 | from sage.misc.latex import latex |
| 1563 | import re |
| 1564 | s = latex(m) |
| 1565 | s = re.sub("\\\\texttt{([^}]*)}", "\\1", s) |
| 1566 | # dictionary with left-right pairs of "brackets". put pairs |
| 1567 | # in here accept \\left and \\right as prefixes. |
| 1568 | bracket_d = {"{": "\\}", "[": "]", "(": ")", "\\{": "\\}", |
| 1569 | "|": "|", "||": "||"} |
| 1570 | bracket = self._print_options.get('latex_bracket', False) |
| 1571 | if bracket is True: |
| 1572 | left = "\\left[" |
| 1573 | right = "\\right]" |
| 1574 | elif bracket is False: |
| 1575 | left = "" |
| 1576 | right = "" |
| 1577 | elif isinstance(bracket, (tuple, list)): |
| 1578 | left = bracket[0] |
| 1579 | right = bracket[1] |
| 1580 | elif bracket in bracket_d: |
| 1581 | left = bracket |
| 1582 | right = bracket_d[bracket] |
| 1583 | if left == "{": |
| 1584 | left = "\\{" |
| 1585 | left = "\\left" + left |
| 1586 | right = "\\right" + right |
| 1587 | else: |
| 1588 | left = bracket |
| 1589 | right = bracket |
| 1590 | prefix = self._print_options.get('latex_prefix', self.prefix()) |
| 1591 | if prefix == "": |
| 1592 | return left + s + right |
| 1593 | return "%s_{%s}" % (prefix, s) |
| 1962 | This is customizable by setting |
| 1963 | ``self.print_options('tensor_symbol'=...)``. |
| 1964 | |
| 1965 | TESTS:: |
| 1966 | |
| 1967 | sage: F = CombinatorialFreeModule(ZZ, [1,2,3]) |
| 1968 | sage: G = CombinatorialFreeModule(ZZ, [1,2,3,8]) |
| 1969 | sage: F.rename("F") |
| 1970 | sage: G.rename("G") |
| 1971 | sage: T = tensor([F, G]) |
| 1972 | sage: T # indirect doctest |
| 1973 | F # G |
| 1974 | sage: T.print_options(tensor_symbol= ' @ ') # note the spaces |
| 1975 | sage: T # indirect doctest |
| 1976 | F @ G |
| 1977 | """ |
| 1978 | from sage.categories.tensor import tensor |
| 1979 | if hasattr(self, "_print_options"): |
| 1980 | symb = self._print_options['tensor_symbol'] |
| 1981 | else: |
| 1982 | symb = tensor.symbol |
| 1983 | return symb.join(["%s"%module for module in self._sets]) |
| 1984 | # TODO: make this overridable by setting _name |
| 1985 | |
| 1986 | def _latex_(self): |
| 1987 | """ |