test_rules_logarithmic.py 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193
  1. from src.rules.logarithmic import log, match_constant_logarithm, \
  2. base_equals_raised, logarithm_of_one, divide_same_base, \
  3. match_add_logarithms, add_logarithms, expand_negations, \
  4. subtract_logarithms, match_raised_base, raised_base, \
  5. match_factor_out_exponent, split_negative_exponent, \
  6. factor_out_exponent, match_factor_in_multiplicant, \
  7. factor_in_multiplicant, match_expand_terms, \
  8. expand_multiplication_terms, expand_division_terms, \
  9. factor_in_exponent_multiplicant
  10. from src.node import Scope
  11. from src.possibilities import Possibility as P
  12. from tests.rulestestcase import RulesTestCase, tree
  13. class TestRulesLogarithmic(RulesTestCase):
  14. def test_match_constant_logarithm(self):
  15. self.assertRaises(ValueError, match_constant_logarithm,
  16. tree('log_1(a)'))
  17. root = tree('log 1')
  18. self.assertEqualPos(match_constant_logarithm(root),
  19. [P(root, logarithm_of_one)])
  20. root = tree('log 10')
  21. self.assertEqualPos(match_constant_logarithm(root),
  22. [P(root, base_equals_raised),
  23. P(root, divide_same_base)])
  24. root = tree('log(a, a)')
  25. self.assertEqualPos(match_constant_logarithm(root),
  26. [P(root, base_equals_raised),
  27. P(root, divide_same_base)])
  28. root = tree('log(a, b)')
  29. self.assertEqualPos(match_constant_logarithm(root),
  30. [P(root, divide_same_base)])
  31. def test_logarithm_of_one(self):
  32. root = tree('log 1')
  33. self.assertEqual(logarithm_of_one(root, ()), 0)
  34. def test_base_equals_raised(self):
  35. root, expect = tree('log(a, a), 1')
  36. self.assertEqual(base_equals_raised(root, ()), expect)
  37. root, expect = tree('-log(a, a), -1')
  38. self.assertEqual(base_equals_raised(root, ()), expect)
  39. def test_divide_same_base(self):
  40. root, l5, l6 = tree('log(5, 6), 5, 6')
  41. self.assertEqual(divide_same_base(root, ()), log(l5) / log(l6))
  42. def test_match_add_logarithms(self):
  43. root = tree('log a + ln b')
  44. self.assertEqualPos(match_add_logarithms(root), [])
  45. # log(ab) is not desired if ab is not reduceable
  46. root = tree('log a + log b')
  47. self.assertEqualPos(match_add_logarithms(root), [])
  48. log_a, log_b = root = tree('log 2 + log 3')
  49. self.assertEqualPos(match_add_logarithms(root),
  50. [P(root, add_logarithms, (Scope(root), log_a, log_b))])
  51. log_a, log_b = root = tree('-log 2 - log 3')
  52. self.assertEqualPos(match_add_logarithms(root),
  53. [P(root, expand_negations, (Scope(root), log_a, log_b))])
  54. # log(2 / 3) is not desired because 2 / 3 cannot be reduced
  55. log_a, log_b = root = tree('log 2 - log 3')
  56. self.assertEqualPos(match_add_logarithms(root), [])
  57. log_a, log_b = root = tree('log 4 - log 2')
  58. self.assertEqualPos(match_add_logarithms(root),
  59. [P(root, subtract_logarithms, (Scope(root), log_a, log_b))])
  60. log_a, log_b = root = tree('-log 2 + log 4')
  61. self.assertEqualPos(match_add_logarithms(root),
  62. [P(root, subtract_logarithms, (Scope(root), log_b, log_a))])
  63. def test_add_logarithms(self):
  64. root, expect = tree('log a + log b, log(ab)')
  65. log_a, log_b = root
  66. self.assertEqual(add_logarithms(root, (Scope(root), log_a, log_b)),
  67. expect)
  68. def test_expand_negations(self):
  69. root, expect = tree('-log(a) - log(b), -(log(a) + log(b))')
  70. log_a, log_b = root
  71. self.assertEqual(expand_negations(root, (Scope(root), log_a, log_b)),
  72. expect)
  73. def test_subtract_logarithms(self):
  74. root, expect = tree('log(a) - log(b), log(a / b)')
  75. loga, logb = root
  76. self.assertEqual(subtract_logarithms(root, (Scope(root), loga, logb)),
  77. expect)
  78. root, expect = tree('-log(a) + log(b), log(b / a)')
  79. loga, logb = root
  80. self.assertEqual(subtract_logarithms(root, (Scope(root), logb, loga)),
  81. expect)
  82. def test_match_raised_base(self):
  83. root, a = tree('2 ^ log_2(a), a')
  84. self.assertEqualPos(match_raised_base(root),
  85. [P(root, raised_base, (a,))])
  86. root, a = tree('e ^ ln(a), a')
  87. self.assertEqualPos(match_raised_base(root),
  88. [P(root, raised_base, (a,))])
  89. root = tree('2 ^ log_3(a)')
  90. self.assertEqualPos(match_raised_base(root), [])
  91. root = tree('e ^ (2ln x)')
  92. l2, lnx = mul = root[1]
  93. self.assertEqualPos(match_raised_base(root),
  94. [P(root, factor_in_exponent_multiplicant,
  95. (Scope(mul), l2, lnx))])
  96. def test_factor_in_exponent_multiplicant(self):
  97. root, expect = tree('e ^ (2ln x), e ^ ln x ^ 2')
  98. l2, lnx = mul = root[1]
  99. self.assertEqual(factor_in_exponent_multiplicant(root,
  100. (Scope(mul), l2, lnx)), expect)
  101. def test_raised_base(self):
  102. root, a = tree('2 ^ log_2(a), a')
  103. self.assertEqual(raised_base(root, (root[1][0],)), a)
  104. def test_match_factor_out_exponent(self):
  105. for root in tree('log(a ^ 2), log(2 ^ a), log(a ^ a), log(2 ^ 2)'):
  106. self.assertEqualPos(match_factor_out_exponent(root),
  107. [P(root, factor_out_exponent)])
  108. root = tree('log(a ^ -b)')
  109. self.assertEqualPos(match_factor_out_exponent(root),
  110. [P(root, split_negative_exponent),
  111. P(root, factor_out_exponent)])
  112. def test_split_negative_exponent(self):
  113. root, expect = tree('log(a ^ -b), log((a ^ b) ^ -1)')
  114. self.assertEqual(split_negative_exponent(root, ()), expect)
  115. def test_factor_out_exponent(self):
  116. ((a, l2), l10) = root = tree('log(a ^ 2)')
  117. self.assertEqual(factor_out_exponent(root, ()), l2 * log(a))
  118. def test_match_factor_in_multiplicant(self):
  119. (l2, log_3) = root = tree('2log(3)')
  120. self.assertEqualPos(match_factor_in_multiplicant(root),
  121. [P(root, factor_in_multiplicant, (Scope(root), l2, log_3))])
  122. (l2, log_3), l4 = root = tree('2log(3)4')
  123. self.assertEqualPos(match_factor_in_multiplicant(root),
  124. [P(root, factor_in_multiplicant, (Scope(root), l2, log_3)),
  125. P(root, factor_in_multiplicant, (Scope(root), l4, log_3))])
  126. root = tree('2log(a)')
  127. self.assertEqualPos(match_factor_in_multiplicant(root), [])
  128. root = tree('alog(3)')
  129. self.assertEqualPos(match_factor_in_multiplicant(root), [])
  130. def test_factor_in_multiplicant(self):
  131. root, expect = tree('2log(3), log(3 ^ 2)')
  132. l2, log3 = root
  133. self.assertEqual(factor_in_multiplicant(root, (Scope(root), l2, log3)),
  134. expect)
  135. def test_match_expand_terms(self):
  136. ab, base = root = tree('log(2x)')
  137. a, b = ab
  138. self.assertEqualPos(match_expand_terms(root),
  139. [P(root, expand_multiplication_terms, (Scope(ab), b))])
  140. root = tree('log(2 * 3)')
  141. self.assertEqualPos(match_expand_terms(root), [])
  142. root = tree('log(2 / a)')
  143. self.assertEqualPos(match_expand_terms(root),
  144. [P(root, expand_division_terms)])
  145. def test_expand_multiplication_terms(self):
  146. root, expect = tree('log(2x), log x + log 2')
  147. self.assertEqual(expand_multiplication_terms(root,
  148. (Scope(root[0]), root[0][1])), expect)
  149. def test_expand_division_terms(self):
  150. root, expect = tree('log(2 / x), log 2 - log x')
  151. self.assertEqual(expand_division_terms(root, ()), expect)