Алгебра и пакет Mathematica 5



Алгебра и пакет Mathematica 5

         

Что такое число



Что такое число? Однозначного ответа на этот вопрос нет. Например, комплексное число — это число или все-таки вектор? А действительное число — это число или сечение во множестве рациональных чисел? А если комплексные числа все-таки числа, то кватернионы — тоже числа или уже объекты другой природы? Ну а если даже кватернионы — все-таки числа, то разве не следует к числам причислить и октавы Кэли? Иногда очень удобно считать, что числа — это элементы любого кольца. Но тогда и матрицы (элементы кольца матриц) тоже ведь нужно считать числами! Впрочем, это совсем не глупо, как может показаться на первый взгляд: в кольце матриц размера 2x2, элементами которых являются вещественные числа, можно выделить подкольцо, которое на самом деле является полем, изоморфным полю комплексных чисел. Так что не удивительно, что каждая эпоха в истории математики давала свой ответ на вопрос о том, что такое число.

Не удивительно и то, что в системе Mathematica предусмотрено несколько типов чисел. В качестве базовых типов чисел удобно рассматривать целые, рациональные, вещественные и комплексные числа. Все они могут содержать практически любое количество цифр. (Все же количество цифр, конечно, ограничено объемом имеющейся памяти.)

Чтобы разобраться в этом, давайте рассмотрим классический пример — занимательную задачу из многих популярных книг по математике для младших школьников.

Пример 3.1. Наибольшее число, которое можно записать тремя цифрами. Постановка задачи: какое наибольшее число можно записать с помощью трех цифр?

Ну, конечно, 999, почти не задумываясь, отвечают школьники. И знаете, они по-своему правы. Ведь поскольку в условии задачи говорится о цифрах, то их можно только записывать одна за другой. Поскольку их три, значит, число будет трехзначным. А 999 — наибольшее трехзначное число, причем в его записи используется только три девятки. Но оказывается, что не все так просто. Ведь на самом деле постановка задачи нечеткая. Действительно, в условии ведь не указано, как три цифры можно использовать для записи числа. Ведь каждую из трех цифр можно использовать для записи чисел, а затем над этими числами выполнить какие-нибудь операции. Можно, например, с помощью двух цифр записать число 99, а с помощью оставшейся цифры — число 9, а затем возвести 99 в степень 9: 99".

С вычислением этого числа система Mathematica справляется без малейших затруднений.




999= 913517247483640899

Но можно числа 9 и 99 скомбинировать и иначе: 999. Система Mathematica без труда вычислит и это число.
999= 295126654306527521487534802261977363143592725
17043832886063884637676943433478020332709411004889

Мы сразу видим, что 9" гораздо больше, чем 999. Но вот тут-то оказывается, что есть еще и третий вариант: 99'. Это число имеет 369 693 100 цифр, т.е. более трети миллиарда! Понятно, что во многих компьютерах объем памяти меньше количества цифр этого числа, и потому система Mathematica записать его не сможет. (Если вы все же решили вычислить это число и вам надоело ждать, выберите Ядро<=>Прервать вычисление.)

Впрочем, если допустить еще и операцию вычисления факториала, то, так как 9! = 362880, с помощью трех цифр можно записать еще большее число: 9?? . Это число система Mathematica уж точно записать не сможет! Правда, вычислить показатель степени — число 99!, десятичная запись которого содержит 65 269 цифр, системе Mathematica вполне под силу!

Наконец, замечу, что авторы популярных книжек упустили еще одну возможность: использование скобок. С их помощью (и факториала), даже одной девятки (или любой другой цифры, большей 2), можно выписать бесконечно возрастающую последовательность чисел.

9, 9! = 362880, (9!)!, ((9!)!)!, (((9!)!)!)!, ((((9!)!)!)!)!, ...

Уже число (9!)! содержит 4 282 655 цифр, но система Mathematica справляется и с ним! Но вот предложить ей вычислить следующее число в этой последовательности даже и не пытайтесь!

Разобравшись немного с числами, давайте изучим операции над ними. Как видно из примера, арифметические операции над целыми и рациональными числами, как и во многих других системах компьютерной алгебры, выполняются точно (все цифры результата верные). Вот, например, результат возведения в сотую степень числа пять, найденный системой Mathematica.
5100 = 7888609052210118054117285652827862
29673206435109023004770278930640625

Однако при таком представлении целых или рациональных чисел иногда трудно судить о величине результата. Кроме того, поскольку система Mathematica стремится сохранить точность, она оставляет фактически невычисленными такие выражения, как

Поэтому вполне логично задать вопрос: как же сделать так, чтобы система Mathematica производила вычисления над вещественными числами, представляя результаты в виде десятичных дробей с заданным количеством разрядов?

Представление вещественных чисел систематическими дробями: функция N. Разрядность и точность вещественных чисел: функции Precision и Accuracy .



Оказывается, что если вместо целого числа указать равное ему вещественное (для этого достаточно поставить десятичную точку в записи числа), то в результате также будет записано вещественное число с десятичной точкой.

Более того, существует конвертор (преобразователь), который представляет вещественные числа, а также вещественную и мнимую части комплексных чисел в виде десятичной дроби. Таким конвертором является функция N.

При необходимости разрядность можно указать и явно: у функции N имеется второй, необязательно указываемый аргумент, который определяет разрядность чисел, используемую при вычислении результата. Если второй аргумент не задан, то по умолчанию в вычислениях используется $MachinePrecision цифр, причем результат выводится с шестью цифрами. Например, ниже вычисляется 50 десятичных знаков π.

При вычислениях с вещественными числами очень полезны функции Precision и Accuracy, названия которых можно перевести как разрядность и точность. Разрядность вещественного числа — это количество значащих десятичных цифр в нем, а точность — это количество значащих десятичных цифр в его дробной части. При вычислениях система Mathematica считает, что вещественные числа имеют либо машинную (по умолчанию), либо неопределенную (произвольную) разрядность. Для того чтобы узнать машинную разрядность компьютера, достаточно вычислить выражение $MachinePrecision. (В версии 5 системы Mathematica имеется также константа MachinePrecision, которая равна значению выражения $MachinePrecision.) На разных типах компьютеров это выражение, конечно, может принимать разные значения. На современных ПК оно обычно близко к 16.

$MachinePrecision
15.9546

Значения функций Precision и Accuracy для целых и рациональных чисел равны Infinity.

Если вводится менее $MachinePrecision цифр вещественного числа, то считается, что его разрядность равна $MachinePrecision.

Если количество введенных цифр вещественного числа превышает $MachinePrecision, то его разрядность равна количеству введенных цифр.

Ниже показаны способы задания разрядности и точности при внешнем представлении вещественных чисел. Для задания численного значения разрядности и точности используется знак `.

Число с машинной разрядностью: 123.4

Число с произвольной разрядностью (на некоторых машинах): 123.45678901234567890

Число с машинной разрядностью (на всех машинах): 123.45678901234567890`

Число с произвольной разрядностью 200 десятичных знаков: 123. 456`200

Число с произвольной разрядностью и точностью 200 десятичных знаков: 123.456`200

Число с машинной разрядностью в экспоненциальной форме: 1.234*^6

Число в экспоненциальной форме с разрядностью 200: 1.234`200*^6

Число в двоичной системе с разрядностью 200: 2^^101.111`200

Число в двоичной системе в экспоненциальной форме: 2^^101.111`200*^6

Ниже приведены примеры, показывающие, как задание разрядности и точности влияет на представление результатов.

При вычислениях отслеживается точность и разрядность результата. Поэтому функцию N часто вызывают для вычисления численных значений выражений, в частности констант.

Встроенные в систему Mathematica алгоритмы обладают тем свойством, что при вычислении функции N от констант все цифры результата получаются верными. Однако в общем случае не следует ожидать, что все n цифр результата вычисления выражения N[ехрr, n] верные. Справедливо лишь то, что вычисления велись с разрядностью не менее n.

Поскольку комплексные числа можно рассматривать как пары вещественных чисел, аргументами функций N, Precision и Accuracy могут быть и комплексные числа.

Разрядность и точность при выполнении операций над числами.



Давайте теперь посмотрим, что происходит с разрядностью и точностью при выполнении действий.

Как и следовало ожидать, разрядность больше точности, поскольку число больше 1 и, следовательно, некоторые значащие цифры стоят до десятичной точки. Передвинем теперь точку на 3 разряда вправо, для чего умножим число на 1000, и посмотрим, изменится ли точность и разрядность.

Как видим, разрядность не изменилась, точность уменьшилась на 3, поскольку фактически теперь в дробной части на 3 цифры меньше. А что получится, если мы точку передвинем вправо? Для этого исходное число нужно разделить на 1000.

Разрядность, как и прежде, не изменилась, зато точность увеличилась на 3, поскольку добавилось три значащих разряда после точки.

А теперь давайте в исходном числе передвинем десятичную точку на 6 разрядов вправо. Для этого разделим его на 1 000 000. Тогда целая часть числа будет равна 0. Изменится ли при этом разрядность?

Разрядность при этом, как видите, не изменилась, но точность увеличилась и даже превзошла разрядность!

Отсюда можем заключить, что в то время как разрядность (количество значащих цифр) не зависит от положения десятичной точки, точность изменяется при изменении положения точки и может быть как меньше, так и больше разрядности. Кстати, а как система Mathematica определяет разрядность и точность? Почему эти числа не обязательно целые?

Чтобы узнать ответ на этот вопрос, давайте разберемся, как система Mathematica подсчитывает эти величины. Пусть задано приближенное значение вещественного числа х с погрешностью 6. Само число х можно рассматривать как десятичную дробь, для которой известны лишь некоторые разряды. Система Mathematica по заданному приближению числа х может считать, что число х лежит в интервале (х-b/2, х+6/2), длина которого равна погрешности 5. Тогда разрядность числа х определяется как  .

Теперь понятно, почему так часто получаются нецелые числа в качестве значений точности и разрядности. Таким образом, если точность числа х равна а, то его погрешность δ = 10-a. Если же число х# 0 и его разрядность равна р, то его погрешность δ = |x|10-p.

Если прибавить к числу (или отнять от него) величину, меньшую погрешности, визуально это не будет заметно.

Но информация о точности хранится.

10^26*(х-х2)
 О.х10i

Фактически это означает, что точность утеряна — нет ни одной верной значащей цифры результата, так как вычисления велись с недостаточной для этого точностью. Заранее же предвидеть, какая точность потребуется в дальнейшем, можно далеко не всегда. Поэтому ничуть не удивительно, что при вычислениях с вещественными числами иногда возникают ничего не значащие "хвосты", которые не имеют никакого физического смысла. Например, при вычислении выражения Exp[N[2 π I] ], которое равно 1, возникает мнимый "хвостик" -2.44921x10-16I. Такие хвосты можно отсечь.


Отбрасывание малых вещественных чисел: функция Chop



Вещественные числа, меньшие 10-10, можно отбросить с помощью функции Chop.

Задание второго числового аргумента eps функции Chop позволяет отбрасывать вещественные числа, абсолютная величина которых меньше eps.

Таким образом, функция chop заменяет маленькие вещественные числа нулем. Впрочем, иногда вещественное число нужно заменить не нулем, а его приближением к целому или рациональному числу. Для этого предназначены функции, позволяющие вычислить целую и дробную части числа, а также его рациональные приближения.


Целая и дробная части вещественного числа



Всякое вещественное число представляет собой сумму его целой и дробной частей:


Целая часть вещественного числа: функции Floor и IntegerPart



Есть множество способов преобразования вещественных чисел в целые. Но важнейшими из них являются округление к целому числу и отбрасывание дробной части.

Округление к ближайшему целому, не превосходящему х: функция Floor[x]

Функция Floor [х] представляет собой наибольшее целое, не превосходящее х.

{Floor[Pi], Floor[-Pi], Floor[0], Floor [2.99], Floor [-2.0001]} {3,-4,0,2,-3}

Именно функция Floor в математике и называется целой частью числа и обычно обозначается через [х]. Заметьте, что эта функция отсекает дробную часть только неотрицательных чисел. Для отрицательных нецелых чисел ее работа иллюстрируется следующим примером.

Floor[-8.12345678] -9

Поэтому если необходимо просто отбросить дробную часть, лучше воспользоваться функцией IntegerPart.

Отбрасывание дробной части: функция IntegerPart

Функция IntegerPart просто отбрасывает дробную часть.

{IntegerPart[2.4],IntegerPart[2.6],IntegerPart[-2.4],
 IntegerPart[-2.6],IntegerPart[PiA2]}{2,2,-2,-2,9}

"Потолок" вещественного числа — округление к наименьшему целому, не превосходящему х: функция Ceiling

Выражение Ceiling [х] представляет собой наименьшее целое, которое не меньше х.
{Ceiling[Pi],Ceiling[-Pi],Ceiling[0],Ceiling[2.99],
Ceiling[-2.0001]}
(4,-3,0,3,-2}

Округление вещественного Числа: функция Round

Функции Floor и Ceiling позволяют округлить вещественное число к меньшему или большему целому. Иногда же нужно выполнить округление к ближайшему целому. Именно для этого и предназначена функция Round.
{Round[2.4],Round[2.6],Round[-2.4],Round[-2.6],Round[Р1^2]}
 {2,3,-2,-3,10}

Однако числа, дробная часть которых равна .5, имеют два ближайших целых. Такие числа функция Round округляет к ближайшему четному целому.
Round[Range[20]-10.5]
 
{-10,-8,-8,-б,-6,-4,-4,-2,-2, 0, 0,2, 2, 4, 4, 6, б, 8, 8,10}


Дробная часть вещественного числа: функция FractionalPart



Пусть х — вещественное число. Тогда его дробную часть {х} можно определить равенством: {х} = х - [х]. По этому, общепринятому в математике определению дробная часть всегда неотрицательна и меньше единицы: 0<{х}<1. Однако в системе Mathematica используется несколько иное определение:

FractionalPart[х] = х - IntegerPart[х].

Поэтому FractionalPart [х] отрицательна для нецелых отрицательных х.

Чтобы освоиться с функцией FractionalPart, напишем программу, которая распечатывает результат применения функции FractionalPart к каждому элементу списка. Прежде всего нам понадобится определить функцию, которая оформляет вывод следующим образом.

FractionalPart[ х ]- результат применения функции FractionalPart к х

Вот как для этого можно определить функцию f.

f=(Print["FractionalPart[",#1,"]=",FractionalPart[#1]] &)

Теперь можем написать программу, в которой функция f применяется к каждому элементу списка.
f/@{x,2.4,0.3999999999999999',2.6,0.6000000000000001\-2.4,
 -0.3999999999999999",-2.6,Pi,10,-Рi^2,2*Sin[1],Ехр[Pi*Sqrt[163]]}

Вот результат

Давайте теперь вычислим

Неужели число    целое. Давайте повторим вычисления.

О, это уже какая-то загадка. Разные результаты при вычислении одного и того же выражения! А вот и разгадка: мы проводили вычисления с разной разрядностью, притом в обоих случаях точность была недостаточна. Давайте повторим вычисления с большей разрядностью.

Теперь мы видим, что  -13! Между прочим, когда системы компьютерной алгебры не были столь доступны, как сейчас, число е√163π доставляло немало хлопот не только студентам, но и многим вполне серьезным "дядям и тетям", недостаточно знакомым с признаками трансцендентности чисел. Некоторые шутники с вполне серьезным видом заявляли, что все говорит о том, что число е является целым, но никто этого пока не доказал, и что за доказательство обещана кругленькая сумма и т.д. А ведь чтобы прямым вычислением установить ложность этого высказывания, необходимо было провести вычисления более чем с 30 десятичными знаками! Даже вычислить его целую часть на машинах серии JBM/360 или БЭСМ-6 без ухищрений было невозможно! Конечно, на зарубежных машинах были доступны системы компьютерной алгебры, например MACSYMA на IBM/360. Однако на территории СССР доступ к таким системам имели весьма немногие. Кроме того, в советской системе образования следствием застойных явлений были ориентация на идеологические дисциплины (история КПСС, разнообразный марксизм и т.д.), отсутствие свободно выбираемых (студентом, а не деканатом!) курсов и сохранение подчиненной роли курса алгебры (всего три семестра) на уровне прошлого века. В советских университетах даже для студентов-математиков программой не было предусмотрено знакомство с современной алгеброй. О компьютерной алгебре не слышали и многие преподаватели. Поэтому на территории СССР вера в необходимость прямого вычисления с довольно большим количеством значащих цифр была не простым заблуждением обывателя, а подкреплялась советской системой образования. Поэтому именно те, кто был заинтересован в финансировании произвольноразрядной арифметики, и устраивали такие розыгрыши, предварительно тщательно выискивая потенциальных жертв. Фактически из отечественных машин для проверки гипотезы подходили только машины серии МИР. Но машина МИР-1, во входном языке (Алмир) которой была реализована произвольноразрядная арифметика, имела память объемом всего лишь 4 Кбайт, а машина МИР-2 — 8 Кбайт, причем быстродействие машины МИР-2 из-за частой сборки мусора падало подчас до 200 операций в секунду! Тем не менее благодаря встроенному языку Аналитик, в котором была реализована произвольноразрядная арифметика и элементы компьютерной алгебры, она справлялась с задачами, одна лишь постановка которых на БЭСМ-6 была весьма трудоемка, и потому очередь к этой машине стояла в десятки раз больше, чем за колбасой. А поскольку заранее никто не мог сказать, сколько времени потребуется на вычисление, спланировать его не представлялось возможным. Что же касается машины МИР-3 (особенно модели МИР-32), то фактически она была доступна только разработчикам, из числа которых и находились самые злостные шутники'! Кстати, в те годы системы компьютерной алгебры часто не могли определить, является ли заданное число алгебраическим. Начиная с версии 4 в системе Mathematica не составляет труда записать (и вычислить!) нужный предикат.
Ехр[  Pi*Sqrt[163]]sAlgebraics
False

Всякая история имеет мораль, и эта не исключение: вычисляя дробную часть, не забывайте указывать нужную разрядность и, кроме того, не упускайте из виду цель, ради которой вы проводите вычисления, — подумайте, нельзя ли достичь цели более простым способом. (Мы бы, например, могли сразу спросить систему Mathematica, является ли е√163πалгебраическим числом.) Не забывайте также о том, что подчас с помощью систем компьютерной алгебры удается разрешить вопрос, который остается открытым в течение длительного времени. Впрочем, иногда достаточно вспомнить всего лишь несколько теорем.

Упражнение 3.1. Вычислите не менее k десятичных цифр числа я, начиная с n-й после десятичной точки. Можете ли вы провести вычисления, например, для n = 100 000, k = 1000? Иными словами, можете ли вы вычислить сто первую тысячу (после запятой) знаков в представлении этого числа десятичной дробью?

Решение. Вот самое простое решение, которое обычно приходит в голову неискушенному читателю. Сначала нужно вычислить п с разрядностью, которая гарантирует n + k + 1 верную цифру, например n + k + 10, а затем в полученной дроби выбрать нужные десятичные знаки. Что касается вычисления я с разрядностью хотя бы 101001, то оно для системы Mathematica никакого труда не представляет. Но вот что касается отсчитать сто тысяч знаков после запятой... Впрочем, в системе Mathematica и для этого предусмотрены нужные функции! Но если немного поразмыслить, то окажется, что решить поставленную задачу можно с помощью функции FractionalPart, "Ну, я об этом сразу догадался!" — высокомерно воскликнет искушенный читатель. Действительно, чего же можно было еще ожидать, если этот раздел посвящен функции FractionalPart? Ну разве что каких-либо трудностей при составлении программы. Но ее составить как раз совсем нетрудно.

n=100000; k=1000; m= N[FractionalPart[10^ (n-1)*Pi],k+10]

Правда, ее нужно предварительно. проверить. Это совсем просто, достаточно уменьшить значения пик, затем провести вычисления
n=1;   k=5;   m= N[FractionalPart[10^(n-1)*Pi],k+10] 
0.141592653589793
n=2;   k=5;   m= N[FractionalPart [10^(n-1)*Pi],k+10]
0.415926535897932
n=10;   k=5;   m= N[FractionalPart[10^(n-1)*Pi],k+10]
0.589793238462643
и сверить результаты с таблицами. Как легко убедиться, результаты совпадают, так что беспокоиться вроде бы не о чем. Но вот если положить n = 50, появляется предупреждение о недостаточной разрядности.
N::meprec: Internal precision limit $MaxExtraPrecision =50.
reached while evaluating -
31415926535897«21»841971693993751«1» «1» .

А при n = 1000 результат выглядит вообще странно: 0.х1034, да и предупреждений целых два! Давайте разберемся, в чем тут дело. Для этого придется проанализировать ход вычислений. Сначала вычисляется Pi с некоторой точностью, притом с запасом (не более $MaxExtraPrecision десятичных знаков, как следует из предупреждения), а затем это число умножается на степень 10, так что в итоге получается 10^ (n-l) *Pi с некоторой точностью, после чего мы пытаемся взять у этого полученного числа его дробную часть. Но вот теперь и оказывается, что число было вычислено с недостаточной точностью, и система Mathematica предупреждает об этом! Впрочем, выход очевиден: нужно просто увеличить значение $MaxExtraPrecision. Но увеличение будет весьма значительным, и потому лучше всего сделать так, чтобы увеличенное значение $MaxExtraPrecision использовалось системой Mathematica только при вычислении результата, нужного для функции FractionalPart. Иными словами, увеличенное значение $MaxExtraPrecision нужно сделать локальным. Для этого достаточно воспользоваться функцией Block. Тогда можно написать следующую тестовую программу.
Do[Block[{k=10},Block[{$MaxExtraPrecision = n+k+10),
Print[n+1,":",N[FractionalPart[10^n*Рi],k+10]]]],{n,0,2030,5}]

Едва ли стоит полностью приводить распечатку результата, но вот отдельные ее части явно заслуживают обсуждения. Вот банальное начало, подтверждающее правильность задания в программе степеней, умножений и всей подобной тривиальной чепухи, в записи которой так легко допустить ошибку.
1  : 0.14159265358979323846
6 : 0.26535897932384626434
11  0.89793238462643383280
16 0.23846264338327950288
21 0.26433832795028841972
26  0.83279502884197169399 
31  0.50288419716939937511
36 0.41971693993751058210

Правильность цифр можно проверить по таблицам, имеющимся почти в любом солидном справочнике по математике или в какой-нибудь монографии, посвященной арифметике произвольной разрядности, например во втором томе бессмертного труда Дональда Кнута Искусство программирования. Что касается продолжения распечатки, то в ней правильность цифр проверить уже сложнее. Ведь найти книгу с более чем пятидесятые знаками л существенно сложнее. Из опыта знаю, что на территории СССР научному сотруднику, не связанному со спецслужбами вроде КГБ или ГРУ, получить доступ к серьезному фолианту по истории вычисления я практически было невозможно. Тем больше наша благодарность организатору первых математических олимпиад в Ленинграде (и СССР; первые олимпиады в Москве и Киеве проводились только через год) Василию Августовичу Кречмару, который в последних изданиях своего труда Задачник по алгебре (предназначенного для любознательных школьников!) поместил результат вычисления л с 2035 знаками после запятой. Разрабатывая арифметику произвольной разрядности для различных программных комплексов (в том числе и систем компьютерной алгебры), я при проверке получаемых результатов неоднократно пользовался шестым изданием этого бестселлера. Вполне подойдет эта книга и для проверки (хотя бы и выборочной) результатов, выдаваемых нашей программой. Так что можем читать нашу распечатку дальше.
41      0.69399375105820974945
46      0.37510582097494459231
51      0.58209749445923078164
56      0.74944592307816406286
61      0.59230781640628620900
66      0.78164062862089986280
71      0.062862089986280348253
76      0.20899862803482534212
81      0.86280348253421170680
86      0.34825342117067982148
91      0.34211706798214808651
96      0.70679821480865132823
101   :   0.82148086513282306647
106   :   0.086513282306647093845

Вы заметили, что распечатан один "лишний" знак? А знаете, почему? Продолжаем читать дальше.
111   :   0.32823066470938446096
 116   :   0.066470938446095505822
 121   :   0.093844609550582231725

И вот опять появились "лишние" знаки. Правда, и в этом случае после точки стоит сразу 0. Но не случайность ли это?
126   :   0.46095505822317253594
131   :   0.50582231725359408128
136   :   0.23172535940812848112
141   :   0.53594081284811174503
146   :   0.081284811174502841027

И вот опять появился "лишний" знак. И опять после точки стоит сразу 0. Да не закономерность ли это? Давайте пропустим часть распечатки и поищем еще "лишние" знаки (я выделяю их курсивом, знак после точки — полужирным).
286      0.60726024914127372459
291      0.024914127372458700661
296      0.41273724587006606316
301      0.72458700660631558817
306      0.70066063155881748815
311      0.063155881748815209210
316      0.58817488152092096283
356      0.90360011330530548820
361      0.011330530548820466521
366      0.053054882046652138415
371      0.48820466521384146952
416      0.91953092186117381933
421     0.092186117381932611793
426     0.61173819326117931051

О, действительно, это, должно быть, закономерность. Итак, мы полагаем, что если после точки идет нуль, то вычисляется дополнительная цифра. Ну а если нулей несколько? Может быть, количество ведущих нулей равно количеству "лишних" цифр?

Давайте попробуем подтвердить (или опровергнуть) эту гипотезу.
446       0.18548074462379962750
451       0.074462379962749567352
456       0.23799627495673518858
556       0.70277053921717629318
561       0.053921717629317675234
566       0.17176293176752384675
591       0.76694051320005681271
596       0.051320005681271452636
601       0.00056812714526356082773
606       0.81271452635608277858
741       0.47713099605187072113
746       0.099605187072113500000
751       0.51870721134999999837
776       0.49951059731732816096
781       0.059731732816096318595
786       0.17328160963185950245
851       0.71010003137838752887
856       0.0031378387528865875332
861       0.78387528865875332084
991       0.21642019893809525720
996       0.019893809525720106549
1041   0.82303019520353018530
1046   0.01952035301852968995S
1051   0.035301852968995773623
1111   0.45415069595082953312
1116   0.069595082953311686173
1121   0.50829533116861727856
1166   0.19255060400927701671
1171   0.060400927701671139010
 1176  0.092770167113900984882
 1181  0.016711390098488240129
1266   0.68471040475346462080
1271   0.040475346462080466843
 1276  0.53464620804668425907
1331   0.66024058038150193511
 1336  0.058038150193511253382
1386   0.92726042699227967824
1391   0.042699227967823547816
1516   0.75596023648066549912
1521   0.023648066549911988183
1551 0.63698074265425278626
1556 0.074265425278625518184
1601 0.81647060016145249192
1606 0.060016145249192173217
1756 0.67179049460165346680
1761 0.049460165346680498863
1766 0.01653466804988627232S
1831 0.95068006422512520512
1836 0.00642251252051173929S5
1856 0.84896084128488626946
1861 0.084128488626945604242
1896 0.11863067442786220392
1901 0.067442786220391949450
1916 0.94945047123713786961
1921 0.047123713786960956364
1966 0.41389086583264599581
1971 0.08658326459958133904S
2021 0.98352595709825822621
2026 0.59570982582262052249
2031 0.98258226205224894077

Итак, все говорит о том, что эта гипотеза верна! А знаете, почему? Потому что ведущие нули не учитываются при подсчете значащих цифр (а ведь именно их количество и равно разрядности). "Ну, это я знал с шестого класса, если не с пеленок. Давайте лучше решим задачу до конца, раз уж мы столь тщательно проверили предложенный мною вариант программы и убедились в его правильности!" — воскликнет иной искушенный читатель. Что же, не возражаю. Давайте зададим параметры и получим результат.

Полужирным здесь выделены искомая сто первая тысяча цифр в представлении числа к десятичной дробью, причем первая выделенная цифра является стотысячной после запятой. "Ну вот, и все дела. Я сразу говорил, что нужно применить функцию FractionalPart. А автор все сомневался, проверял тривиальную программу, сравнивал десятичные знаки с предварительно вычисленными значениями я, измышлял гипотезы... Да в этой программе Pi можно заменить любым числом, в конце концов, я такие программы пишу с пеленок!" — возмутится тут искушенный читатель. Ой, не торопитесь делать такие выводы. В математике (и в программировании, и в компьютерной алгебре) есть великие идеи, но нет мелочей. А что касается вещественных чисел, то они свои ловушки расставляют не только на страницах учебников по теории функций вещественного переменного (чтобы изловить ленивых студентов), но и в вполне респектабельных программах (чтобы в эти ловушки на сей раз угодили "искушенные" читатели и нерадивые пользователи). Вспомните, что мы в ходе проверки подтвердили гипотезу о том, что количество ведущих нулей равно количеству "лишних" цифр. Но ведь мы заранее не знаем, сколько ведущих нулей может встретиться при вычислении дробной части FractionalPart [10^n*Pi], так что заранее ручаться за правильный выбор разрядности мы не могли! Нам просто повезло, что выбранное значение разрядности обеспечило нужную точность! В принципе заранее неизвестно, работает ли наша программа для всех натуральных значений n и k. Указанного нами значения $MaxExtraPrecision = n+k+10 может ведь и не хватить для вычисления k+10 значащих цифр дробной части, если она будет начинаться более, чем с десяти нулей! Если бы в десятичном приближении я встречались сколь угодно длинные последовательности нулей, то для каждого k нашлось бы такое n, что программа с задачей не справилась бы! К счастью для "искушенного" читателя в настоящий момент это неизвестно. Зато даже шестиклассник (во всяком случае, участник районных математических олимпиад) без труда может придумать примеры вещественных чисел, для которых эта программа и ей подобные не работают. Нужно просто выбрать число, в десятичной записи которого встречаются все более длинные последовательности нулей. В качестве примера подойдет число 0.1234567891011121314151617181920..., в котором после десятичной точки выписаны последовательно все натуральные числа. Есть, конечно, и более экзотические примеры, что-нибудь вроде

Десятичная запись этого числа содержит только нули и единицы, причем и тех, и других там бесконечно много, но единицы встречаются столь редко, что если наудачу выберешь какую-нибудь цифру, почти наверняка попадешь на последовательность нулей. Так что слухи о том, что придуманная нами программа при тривиальных модификациях может быть применена к любому вещественному числу, были несколько преувеличены...

Да, а как же все-таки решить задачу? Ну, в данном случае это совсем несложно.

Почему же все-таки я подчеркиваю, что решить задачу несложно именно в данном случае? Вспомните пример с е '"". Там проблема была в том, что вычисленные десятичные приближения заканчивались девятками. А если бы и в этом примере цифры в конце оказались девятками, мы бы не смогли решить, верные ли они. (Именно для того, чтобы избежать округления и убедиться, что последняя цифра не девятка, мы и распечатываем k+1 цифру — k требуемых по условию задачи и одну запасную. Если бы запасная цифра оказалась девяткой, пришлось бы выводить еще несколько запасных цифр, пока не обнаружили бы отличную от 9.) Конечно, мы могли бы увеличить разрядность, но что если бы мы повстречали участок, сплошь состоящий из нескольких миллионов девяток? Может быть, это верные цифры, а может быть, нам просто не хватило точности, и в каком-то миллионе затерялась та единичка в переносе, добавление которой превращает все эти миллионы девяток в миллионы нулей? Вот оно коварство бесконечных десятичных дробей!

Из этого можно извлечь несколько уроков. Во-первых, выполняя действия над вещественными числами, нужно тщательно следить за точностью. Во-вторых, для применения таких функций, как FractionalPart, иногда необходима существенно более высокая разрядность, чем та, которая обеспечивается системой автоматически. В-третьих, иногда перестановка функций позволяет упростить программу. И, наконец, в-четвертых, вещественные числа иногда способны преподносить сюрпризы вроде девяток в конце вычисленных значений или необъятного количества ведущих нулей в начале дробной части. Тогда даже на простые вопросы вроде целое ли это число или конечная ли эта десятичная дробь ответить бывает чрезвычайно трудно. Ведь чем точнее удается приблизить бесконечную дробь рациональными числами, тем больше шансов на то, что она представляет собой число трансцендентное...

Упражнение 3.2 (число Пизо). Вычислите 5555 десятичных цифр числа Пизо

Сколько у этого числа нулей следует сразу после десятичной точки? Решение. Вот самое простое решение. Сначала вводим определение числа.

Теперь вычисляем число с указанной точностью.

Ну, как? Не думаете ли вы, что это число заслуживает того, чтобы вычислить его целую и дробную части по отдельности? Сначала вычислим целую часть.

"Ну и что?" — возможно, скажете вы. Тогда присмотритесь внимательнее, где начинаются нули. Да, именно с них и начинается дробная часть.

Из этого видно, что после десятичной точки следует 1831 нуль! Чтобы обнаружить, что это число не целое, нужно вычислить его не менее, чем с 5496 десятичными знаками. Вот это можно было бы устроить розыгрыш! 

Упражнение 3.3. Пусть

Сколько у этого числа нулей следует сразу после десятичной точки?

Решение. Вот самое простое решение. Сначала вводим определение дроби fajl.

Теперь нужно вычислить число с такой точностью, чтобы найти хотя бы один ненулевой знак после запятой. Давайте попробуем.
N[FFraction[Sqrt[17]-Sqrt[14],25],50]
 1.0000000000000000000000000000000000000000000000000

Ну и как? А вот еще:

Хотите еще? Пожалуйста.

А пятьдесят тысяч знаков после десятичной точки не хотите ли? Хотите. Тогда пожалуйста, только эффект будет в десять раз сильнее.

Между прочим, если это число целое, то после десятичной точки у него сплошные нули... И все попытки просто приведут к исчерпанию свободной памяти. Ну бывает же, что дроби сокращаются, а радикалы взаимно уничтожаются:

А здесь ведь разность степеней делится на разность степеней... Вот оно, коварство авторов, придумывающих "подленькие" задачи! Возможно, нужно лишь упростить выражение и убедиться, что оно равно какому-нибудь целому числу! Вот если в числителе вычесть и добавить удачно подобранную степень основания:

Конечно, сразу же просится k = 121393, тогда сразу же выделится единица:

Осталось справиться с числом

А ведь разность показателей представляет собой разность последовательных чисел Фибоначчи, и потому опять есть число Фибоначчи! Внимательно следите за моей мыслью? Может, надеетесь на дальнейшие упрощения? Так вот они:

Можно (для удобства исследования) эту дробь обратить и применить к ней тот же прием! И с полученной дробью можно поступить так же! Фактически у нас получатся элементы цепной дроби! После двух десятков (с хвостиком) шагов мы убедимся, что желанного нуля у нас так и не получится. Значит, после десятичной точки все-таки есть цифры, отличные от нуля! Ну вот, а вы говорили о коварстве авторов, придумывающих "подленькие" задачи! Но как же найти эти цифры? Ну, после проделанной работы у вас есть уверенность в наличии таких цифр, и потому вы знаете, что, в конце концов, все время увеличивая точность, вы их найдете. Это важно, ибо вы тем самым убедились в том, что алгоритм, хотя бы теоретически, не зациклится. Но есть и более быстрый способ, ведь мы нашли целую часть и знаем, что дробная не равна нулю. Можем без каких бы то ни было опасений попытаться вычислить логарифм дробной части:

Сразу не получилось... Но можно предпринять и вторую попытку.

Так, оказывается, после запятой 50810 нулей! Убедимся в этом.

Что касается нулей, то, хоть я и вычеркнул подавляющее их число, предварительно я их посчитал в Word! И их оказалось 50810! Между прочим, убедиться в том, что число fa,n не целое, не так-то просто.

Упражнение 3.4. Пусть

Сколько у этого числа нулей следует сразу после десятичной точки?

Решение. Вот самое простое решение. Сначала вводим определение числа.

Теперь нужно вычислить число с такой точностью, чтобы найти хотя бы один ненулевой знак после запятой. Итак, попробуем.

Да это ж предыдущий случай! Мы уже знаем, как с этим справиться.

Видите ли... Как бы вам это популярнее объяснить, пока продолжаются вычисления... Отличие от предыдущего случая состоит в том, что в предыдущем случае мы убедились, что 1 действительно является целой частью исследуемого числа. В данном же случае мы лишь предполагаем, что число -10 является целой частью числа х. дН-10 может ведь оказаться и отрицательным, а тогда логарифм окажется комплексным. Это, впрочем, совсем не страшно, мы лишь должны будем вычислить логарифм х+11. Вот и всего-то... Да, но что-то наши вычисления слишком затянулись... Понимаете, тут я должен сделать еще одно разъяснение. Видите ли, чтобы вычислить логарифм, нужно проделать некоторые вычисления, и в нашем случае с довольно высокой точностью. И успех эти вычисления принесут лишь тогда, когда будет обнаружено, что аргумент логарифма (число х+10) отличен от нуля... А в данном случае для этого недостаточно даже вычисления более чем двух с половиной миллионов знаков. Видите ли, бывает же, что дроби сокращаются, а радикалы взаимно уничтожаются. Вот в данном случае как раз х+10 = 0, потому что х= -10. Данное число целое! Давайте попробуем убедиться в этом.

Возможно, вы подумали, что автор хотел обвести вас вокруг пальца! Число все-таки оказалось нецелым! Просто система Mathematica не смогла вычислить достаточное количество знаков, и автор решил упростить себе задачу. Увы, если вы согласились с тем, что число нецелое, совершили довольно распространенную ошибку. Не потому, что оно целое, а потому, что так проверять нельзя. Предикат IntegerQ[x] может принимать значение False даже для целого аргумента. Он проверяет не само число, а его внутреннее представление. Этот предикат принимает значение True только в том случае, если внутреннее представление числа имеет заголовок Integer. Вот как лучше проверять.

Как видите, все ответы тавтологичны. И в данном случае вопрос так и не прояснился... Да, система Mathematica не всегда может то, с чем справляется даже школьник:

Теперь уж действительно ясно, что число целое. Конечно, придумать таких примеров можно великое множество. И проблема здесь не в коварстве авторов задачников, а в том, что не существует алгоритма (в классическом смысле), который для любого вещественного числа мог бы решить вопрос о том, равно оно нулю или нет. Существует специально разработанный математиками конструктивный анализ, в котором числовой континуум состоит не из обычных вещественных чисел, а из конструктивных. Для конструктивного вещественного числа всегда разрешим вопрос о том, равно ли оно нулю. Конструктивный континуум — та основа, на которой строятся другие объекты конструктивного анализа, например функции. Однако в конструктивном анализе изучаются не любые функции (отображения конструктивного континуума в себя), а только конструктивные. Несмотря на некоторое сходство, свойства конструктивных объектов отличаются подчас радикально.


Приближение вещественных чисел рациональными: функция Rationalize



Что значит найти рациональное приближение вещественного числа? Какое приближение следует считать хорошим? На эти вопросы можно отвечать по-разному.

Mathematica, например, считает, что рациональное число p/q — лежит довольно близко к вещественному х, если существует с, примерно равное 10 -4, такое, что

Вот как можно составить список рациональных приближений числа π с точностью до 0,1; 0,01; 0,001; ... 10 20.

Обратите внимание на то, насколько добросовестно система Mathematica подыскивает рациональные приближения. Хотя знаменатели рациональных чисел невелики, найденные приближения настолько хороши, что повторяются в этом списке дважды. Иными словами, они приближают л на порядок лучше, чем было первоначально "заказано" с помощью второго параметра.


Преобразование в десятичную систему счисления



Хорошо, конечно, что Mathematica, как мы уже видели, действительно умеет многое делать с числами в десятичной системе счисления. Но умеет ли она преобразовывать числа из одной системы счисления в другую? Оказывается, да! Правда, нужно сразу оговориться, что основанием позиционной системы должно быть натуральное число, притом большее 1. Так что никаких комплексных оснований и тем более фибоначчиевых или факториальных систем счисления!

Чтобы ввести число в какой-нибудь системе счисления, сначала нужно указать (в десятичном виде) основание системы счисления n (натуральное число, причем 2<и<36), затем два знака ^^ (крыша), а потом само представление неотрицательного вещественного (или целого) числа без знака в системе счисления с основанием n. Цифры, большие 9, изображаются латинскими буквами от а до z, причем а = 10, b = 11 и т.д., в порядке (латинского) алфавита аж до z = 36. Вот несколько примеров.

{2^^1,2^^10,2^^100,2^^1000,2^^101}
{1,2,4,8,5}
16^^ffffaaOO
42949452.80 2^^1001001010110111.11110
37559.9

Только что мы научились преобразовывать числа из недесятичной системы счисления в десятичную. А как же выполнить обратное преобразование, т.е. преобразовать число из десятичной системы в недесятичную?


Преобразование из десятичной системы счисления в недесятичную



Чтобы преобразовать число из десятичной системы счисления в недесятичную, нужно вызвать функцию BaseForm, причем в качестве первого ее аргумента нужно указать преобразуемое число, а в качестве второго — основание системы счисления, в которую преобразуется число. В качестве основания системы счисления может быть натуральное число и, такое, что 2<n<36. Вот примеры.

BaseForm[377456783746590,2]
10101011101001011100000011000001101100110000111102
BaseForm[377456783746590,16]
1574b8183661е16
BaseForm[377456783746590,60]
BaseForm::basf:Requested base 60 should be between 2 and 36. More...
BaseForm[377456783746590,60]

Как видите, если указать основание системы счисления, большее 36, функция "заругается". Так что шумерам и древним вавилонянам крупно не повезло бы, попытайся они записать какое-нибудь число, например 1000000, в своей любимой шестидесятеричной системе счисления. Впрочем, числа, большего 3600, шумеры долгое время не знали. Дело в том, что они не сразу осилили концепцию числа как последовательности цифр, или списка цифр.


Число как последовательность (список) цифр



В позиционной системе счисления число фактически представляет собой список цифр. Для получения такого списка и работы с ним в системе Mathematica предусмотрено несколько встроенных функций, наиболее важными из которых являются IntegerDigits, DigitCount, RealDigits и FromDigits.

Представление целого числа в виде списка десятичных цифр: функция IntegerDigits

Разговаривая по телефону, иногда приходится передавать какие-нибудь длинные, например двадцатизначные, числа. В этих случаях обычно читают их цифра за цифрой. Число 587999888735555 читают, например, часто так: пять, восемь, семь, девять, девять, девять, восемь, восемь, восемь, семь, три, пять, пять, пять, пять. В программах тоже иногда нужно по числу определить его цифры. Если вы хотите узнать, является ли шестизначное число счастливым, вам придется сравнить сумму первых трех цифр с суммой последних трех. Поэтому не удивительно, что уже в версии 2 системы Mathematica была предусмотрена функция IntegerDigits, которая представляет число в виде списка цифр. Представим, например, число 25! в виде списка цифр.

IntegerDigits[25!]
{1,5,5,1,1,2,1,0,0,4,3,3,3,0,9,8,5,9,8,4,0,0,0,0,0,0}

Представление целого числа в виде списка цифр в системе счисления с произвольным основанием: функция IntegerDigits

Но, оказывается, функция IntegerDigits может использоваться также для получения списка цифр в системе счисления, основание которой нужно указать вторым параметром. Основание в таком случае может быть любым натуральным числом, большим единицы. Представим, например, число 60! (я полагаю, оно бы очень понравилось шумерам, если бы они его знали) в их любимой шестидесятеричной системе.
IntegerDigits[60! , 60]
{1,20,3,4,48,29,10,11,46,47,21,26,45,46,9,29,47,16,37,50,59,
58,0,33, 59,19,31,10,42,35,8,9,36,0,0,0,0,0,0,0,0,0,0,0,0,0,0}

Иногда нужно представить число в системе счисления не только с заданным основанием, но и с заданным количеством цифр, т.е. дополнить его ведущими нулями в таком количестве, чтобы количество цифр равнялось заданному. Тогда количество цифр в числе нужно задать в качестве третьего параметра функции IntegerDigits.

Вот как число 56 представляется в виде байта.
IntegerDigits[56, 2, 8]
 
{0,0,1,1,1,0,0,0}

А вот как число 25! записывается в 32-разрядных машинах.
IntegerDigits[25! ,2,32]
{0,1,1,1,1,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0}

Представление целого числа в виде списка цифр в нега-двоичной системе счисления

Если снование системы счисления b является отрицательным целым числом, меньшим -1, то такую систему называют нега-позиционной. Например, если b = -2, то такая система называется нега-двоичной, а если b = -4 — нега-четверичной, если b = - 10 — нега-десятичной. Основным преимуществом этих систем является отсутствие знака перед отрицательными числами и, следовательно, отсутствие правил знаков. Дело в том, что всякое число любой из нега-позиционных систем с четным числом цифр отрицательно, а число, отличное от 0, с нечетным числом цифр — положительно. Особый интерес для конструкторов вычислительных машин представляет, конечно, нега-двоичная система. Однако если задать отрицательное основание (-2) в качестве второго параметра, функция IntegerDiglts "заругается".

Однако функция IntegerDigits позволяет определить функцию, которая сможет представить число в нега-двоичной системе.

И уж совсем просто определить функцию, которая по представлению числа в нега-двоичной системе находит его представление в десятичной системе:

Вот пример (фактически мини-тест) применения обеих функций.

Представление вещественного числа в виде списка десятичных цифр: функция RealDigits

Функция RealDigits позволяет представить вещественное число в виде списка цифр. В этом она похожа на функцию IntegerDigits для целых чисел. Однако, в отличие от функции IntegerDigits, функция RealDigits выдает список, состоящий из двух элементов: списка цифр и количества цифр до десятичной точки.

Представление вещественных чисел в виде списка цифр в системе счисления с произвольным основанием: функция RealDigits

Как и функция IntegerDigits, функция RealDigits может использоваться для получения списка цифр в системе счисления, основание которой нужно указать вторым параметром. Основание в таком случае может быть любым вещественным числом, большим единицы.
RealDigits[617.2857142857142857142857142857,2.5]
{{1,0,0,0,0,1,0,0,1,1,1,2,0,2,0,1,0,0,2,1,0,
1,1,0,0,0,0,0,0,2,1,0,0,2, 0,1,0,2,0,1,0},8}

Однако при вызове функции RealDigits могут возникнуть осложнения в самых тривиальных, на первый взгляд, случаях. Дело в том, что параметры должны быть такими, чтобы по ним функция RealDigits могла определить разрядность представления. Например, первый параметр должен быть вещественным числом, он не может быть записан даже в виде целого числа, если второй параметр задан как Pi.

В этом случае первый параметр нужно задать как 1.0.
RealDigits[1.0,Pi] 
{{1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0},!}

Вот еще один пример.

А вот сообщение, совсем "дикое" с точки зрения здравого смысла.

Здесь уж точно можно определить, что нужны только две цифры! Правда, для этого нужно вникнуть в смысл выполняемой операции. Правда, функцию можно обмануть, но лишь с определенной точностью.

Второй способ обмана лучше.

При первом же способе получим следующее.

Здесь Indeterminate — это цифра, в которой функция не уверена.

Представление рациональных чисел в виде списка цифр в системе счисления с произвольным основанием: функция RealDigits

Рациональные числа представляют собой конечные или периодические систематические дроби. Поэтому их представление в виде списка цифр в системе счисления с произвольным основанием имеет некоторые особенности. Проиллюстрируем их на примерах. Пусть имеем рациональное число 99/61. Оно представляется в виде периодической десятичной дроби. Вот как можно вычислить ее начало.
nl=  N[99/91,60]
 1.08791208791208791208791208791208791208791208791208791208791

Теперь получим список цифр.
n2=RealDigits[N[99/91,60]]
{{1,0,8,7,9,1,2,0,8,7,9,1,2,0,8,7,9,
1,2,0,8,7,9,1,2,0,8,7,9,1,2,0,8,7,
9,1,2,0,8,7,9,1,2,0,8,7,9,1,2,0,8,7,9,1,2,0,8,7,9,1},!}

Пока ничего удивительного. Но ведь список цифр можно получить и проще.
n3=RealDigits[99/91] {{1,{0,8,7,9,1,2}},!}

Оказывается, в этом случае функция RealDigits соображает, что дробь получается периодическая, и находит ее период!

Интересно выполнить обратное преобразование, оно выполняется с помощью функции FromDigits.

Как видите, если период дроби был выделен явно, обратное преобразование выполняется точно!

Однако период может начинаться не сразу после десятичной точки, как в чисто периодических дробях, а после одной или нескольких цифр. В этом случае количество цифр до периода превышает количество цифр до десятичной точки. Рассмотрим пример.

Как видно из этого примера, других принципиальных отличий нет.

Получение заданного количества цифр вещественного числа в системе счисления с произвольным основанием: функция RealDigits

Мы научились получать список цифр вещественного числа в системе счисления с произвольным основанием. При этом получаются списки цифр определенной длины, которая неявно определяется по параметрам функции RealDigits. Однако количество цифр можно явно указать в качестве третьего параметра функции RealDigits. Вот, например, 300 цифр числа я в системе счисления с основанием е (основание натуральных логарифмов).

Итак, чтобы получить len цифр вещественного числа х в системе счисления с основанием b, вызов функции RealDigits можно записать так: RealDigits [x, b, len]. Если len больше Log [10, b] *Precision[x], то цифры, для которых не хватило точности, представляются как неопределенные (indeterminate).

Получение заданного количества цифр вещественного числа, начиная с цифры определенного разряда в системе счисления с произвольным основанием: функция RealDigits

Если нужно получить len цифр вещественного числа х в системе счисления с основанием 6, начиная с разряда, который в позиционной системе счисления соответствует множителю bn , то вызов функции RealDigits нужно записать так: RealDigits [х, b, len, n]. Например, чтобы вывести только цифры после точки, нужно положить n = -1. Вот еще более "насыщенный" пример.

Однако без дополнительных ухищрений получить вторую после точки тысячу знаков десятичной дроби, приближающей основание натуральных логарифмов, нельзя.

Но даже если увеличить значение $MaxExtraPrecision, все равно ничего не получится (большая часть распечатки пропущена — она заменена троеточием).

Но не думайте, что эта задача неразрешима, просто функцию RealDigits нужно применить к предварительно вычисленному приближению основания натуральных логарифмов.

Честно говоря, запятых здесь слишком много. Возникает соблазн избавиться от них следующим способом.

Обратите внимание на то, что при этом способе теряются ведущие нули! У нас, например, потерялся один нуль.

Реконструкция числа по списку цифр, полученному с помощью функций IntegerDigits и RealDigits, — функция FromDigits

Как мы видели, иногда по списку цифр (и других вспомогательных данных) нужно восстановить число. Это выполняется с помощью функции FromDigits. Если этой функции передать один параметр — список, то при восстановлении числа она считает, что цифры в списке — десятичные. Но при необходимости можно указать и основание системы счисления как второй параметр. Вот как, например, можно получить приближение л в виде десятичной дроби, а затем интерпретировать ее как шестнадцатеричную.

Можете ли вы узнать я? Едва ли!

Но на самом деле восстановить его очень просто.
k=RealDigits[m,16]
{{3,1,4,1,5,9,2,6,5,3,5,8,9,7,9,3,2,3,8,4,6,2,6,4,3,3,8,3,2,7,9,5,0,2,
8,8,4,1,9,7,1,6,9,3,9,9,3,7,5,1,0,5,8,2,0,9,7,4,9,4,4,5,9,2,3,0,7,8,1,
6,4,0,6,2,8,6,2,0,8,9,9,8,6,2,8,0,3,4,8,2,5,3,4,2,1,1,7,0,6,8},!}

Если первый аргумент имеет вид {список, n}, то n рассматривается как показатель степени (основанием степени служит основание системы счисления), на которую умножается число, восстановленное по списку цифр. Если список имеет вид {список-l, (список-2}}, то список-2 рассматривается в качестве периода систематической дроби.

Функция IntegerDigits теряет знак числа, поэтому FromDigits [IntegerDigits [n] ] равно абсолютной величине Abs [n], а' не n.

"Цифромания": как посчитать девятки в десятичном представлении е — функция DigitCount

Система Mathematica позволяет вычислить столько констант! С точки зрения "цифроманов" было просто преступно не воспользоваться этим и не узнать, например, как распределены единицы и нули в числах От 1 до 256, записанных в двоичной системе, или же не посчитать количество девяток в десятичном представлении основания натуральных логарифмов. Именно для этого (и многих других полезных вещей) как раз и предназначена функция DigitCount. Вызов DigitCount [n, b, d] возвращает количество цифр d (предполагается, что это цифра системы счисления с основанием ь) в числе n, записанном в системе счисления с основанием b. Рассмотрим сначала простой пример. Вот как найти"представление числа 175! в системе счисления с основанием 25.

А вот как можно узнать, сколько раз в этом списке встречается цифра 14

Но это еще что! Можно ведь даже построить график зависимости количества единиц в двоичном представлении n от и.

О, это настоящая музыка цифр! Но это еще не все: если третий параметр опущен, функция DigitCount посчитает количество вхождений каждой цифры в представлении числа л в системе счисления с основанием b. (Таким образом, получится список из b чисел.) При этом количество вхождений единицы стоит на 1-м месте в списке, двойки — на 2-м, цифры k (k > 0) — на k-м, а количество вхождений нуля — на последнем, 6-м. Если же опустить и второй параметр — основание системы счисления, то система счисления предполагается десятичной.

Вот как, например, можно сосчитать, сколько раз различные десятичные цифры входят в первые (после запятой) 10 знаков десятичного представления основания натуральных логарифмов.

А вот как узнать, насколько фактически эти цифры отличаются от среднего, 10n.
DigitCount[IntegerPart[10^(10^(n+1))*
FractionalPart[N[E,10^(n+1)+10]]]]-10^n
 {1,1,-1,О,-1,-1,0,3,-!,-!}

А теперь посчитаем относительные отклонения от среднего.
N[(DigitCount[IntegerPart[10^(1СГ (n+1))*
FractionalPart[N[E,10^(n+1)+10]]]]-10^n)/10^n,4]
{1.000,1.000,-1.000,0,-1.000,-1.000,0,3.000,-1.000,-1.000}

Ну а теперь мы можем составить таблицу таких отклонений для n = 0, 1, 2, 3, 4, 5.

Одно время некоторых "цифроманов" очень беспокоили неравномерности в распределении девятки в десятичном представлении основания натуральных логарифмов. Честно говоря, просматривая эту таблицу, особых причин для беспокойства именно по поводу девятки я не вижу. Вы имеете возможность просмотреть таблицу, самостоятельно составить более подробную и сформировать собственное мнение — с помощью функции DigitCount это совсем просто! Если же изучать таблицу лень, можно представить данные в виде графика (обратите внимание на то, что ось, на которой отложены значения отклонений, не проходит через начало координат, которое находится вне графика).

Из графика видно, что наибольшее отклонение от среднего в первом миллионе десятичных знаков не у девятки, а у нуля. Аналогичный график для первых двух миллионов десятичных знаков строится так.

Как видите, если и винить, то скорее нули, а не девятки!

Ну а вот как можно построить график зависимости количества единиц в числе

Наконец, можно заняться изучением двоичного представления числа числителъ (В2n) х знаменателъ(В2n). Вот отклонение количества единиц в представлении от среднего.

А вот и относительное отклонение.

Какие стремительные взлеты и падения!


Экспоненциальное представление чисел: функция MantissaExponent



Функция MantissaExponent [x] представляет число х в виде списка, который содержит мантиссу и экспоненту числа.

В качестве второго аргумента функции MantissaExponent можно задать основание, которое не обязательно дожно быть целым.

Однако комплексными аргументы функции MantissaExponent не могут быть.

Модуль (абсолютная величина) числа: функция Abs



Функция Abs [ z ] возвращает абсолютную величину (модуль) комплексного числа z. Конечно же, ее аргумент может быть и вещественным.


Знак числа: функция Sign



Если аргумент х — вещественное число, то Sign[x] возвращает —1, 0 или 1, в зависимости от того, является аргумент отрицательным, нулем или положительным. Если комплексное число z отлично от нуля, то Sign[z] по определению равно i/Abs [z]. Рассмотрим пример.

Во еще один пример.


Числитель и знаменатель числа: функции Numerator и Denominator



Функция Numerator[ехрг] собирает в ехрг все множители с неотрицательными показателями. В качестве ехрг можно использовать целые числа, дроби, комплексные числа и их произведение. То же самое функция Denominator делает для сомножителей с отрицательными показателями. Вот пример.

Эти функции применимы и к комплексным числам.

Но суммы в качестве аргументов остаются непреобразованными.

Впрочем, как обычно, все вычисления выполняются с учетом значений переменных.

Знаменатель дроби в предыдущем примере получить совсем не сложно, нужно только все привести к общему знаменателю. Проще всего это сделать так.

Аналогично ведет себя и функция Denominator. Вот примеры.


Представление числа непрерывной дробью: функция Continued Fraction



Функция ContinuedFraction [x] преобразует число д: в непрерывную дробь. Количество звеньев определяется точностью числа х. Следующая программа, например, находит представления первых 50 чисел Бернулли в виде цепных дробей.

Do[
Print[2n,":",ContinuedFraction[BernoulliB[2n]]],{n,0,50} ]


Как видно из таблицы, некоторые числа Бернулли представляются цепной дробью с очень небольшим количеством звеньев.

Количество звеньев цепной дроби можно задать явно в качестве второго параметра.

Это позволяет получить наилучшие приближения числа дробями, знаменатели которых не превосходят некоторого числа. Пусть, например, нужно найти первые 20 звеньев цепной дроби, представляющей число

(Разложение этих чисел в цепную дробь при любом натуральном k было найдено Эйлером в 1737 году.) Вот нужная нам программа.
Do[Print[k,":",ContinuedFraction[Е^(2/k), 20]],
{k,1,10}]

Если у цепной дроби количество звеньев меньше заданного, будет сгенерировано предупреждение. Вот как выглядят, например, результаты разложения корней из 2 в цепную дробь с 20-ю звеньями.

Такое предупреждение, как видим, не препятствует работе программы.

Числа Фибоначчи и цепные дроби

Давайте разложим 

Как видите, количество звеньев разложения дроби    никакая другая дробь такого разложения не имеет.

Вообще, выражения, содержащие числа Фибоначчи, доставляют подчас примеры чисел, разложения которых в цепные дроби обладают весьма интересными свойствами.

Пример 3.2. Давайте определим следующую функцию.

А теперь давайте попытаемся представить несколько ее значений в виде цепных дробей. Положим, например, а = 2, k = 15. Вот результаты.

А теперь давайте возьмем логарифмы по основанию 2.

Если и это вам ничего не напоминает, взгляните вот на это.
Table[Fibonacci [n] ,{п,15,2,-1}]
{610,377,233,144,89,55,34,21,13,8,5,3,2,1}

Так что все звенья цепной дроби (кроме последнего), в которую разлагается число 

Фибоначчи Fn, Fn-1, Fn-2,,..., F2, записанные в обратном порядке! То же самое имеем и для а = 3, k = 25.

Последний элемент цепной дроби, как видим, равен n+1. Конечно, фокус основан на тождестве

Хотя тождество справедливо для всех я, таких, что aFk=1 (k = 0, 1, ..., n+1), именно для целых а правая часть будет "настоящей" цепной дробью.

Здесь целая часть выделена полужирным, а остальные элементы курсивом через один, чтобы их было легче отличить. Видно, как быстро убывают элементы дроби. Но вот если основание а не является целым числом, картина может измениться кардинально. Вот, например, разложение, в котором основание а само является дробью того же вида.

Как видите, если не считать целой части, то все элементы цепной дроби являются весьма небольшими числами. Однако так бывает не всегда. Возьмем, например, основание а = 1/3.

Здесь самым большим является второе звено. Все, кроме него и последнего звена, являются степенями тройки, причем показатели степеней — числа Фибоначчи.

Вот еще пример.

Сколько девяток во втором элементе? 13 = 8+5 = Fibonacci [7] — следующее число Фибоначчи. А сколько нулей? 21 = 13+8 = Fibonacci [8] — опять следующее число Фибоначчи! А сколько цифр во втором элементе? 21 + 13+1 = Fibonacci [9]+l — на единицу больше, чем следующее число Фибоначчи! Но эта единица не для того, чтобы портить картину, она как раз служит для того, чтобы утвердить закономерность, потому что благодаря ей второй элемент равен 10F9 + 10F7 -1.

Однако не при всех основаниях картина столь гармонична. Возьмем, например, в качестве основания

Числа вида

могут доставить множество неприятностей при разложении в цепные дроби. Вот первая попытка получить первые десять элементов разложения в цепную дробь.

А вот и вторая

Точность — два с половиной миллиона десятичных цифр! Куда ж еще увеличивать?! Давайте разберемся, в чем тут дело.

Проблема, похоже, в том, что эти числа слишком быстро приближаются к целому числу 1 с возрастанием п, и потому так быстро возрастает второй элемент. Чтобы сделать картину еще более наглядной, придется прибегнуть к хитрости: увеличим количество вычисляемых элементов. Но чтобы не загромождать распечатку, оставим в ней только 5 элементов. Вот начало распечатки.

Как видите, с ростом n второй элемент возрастает катастрофически быстро, а потому катастрофически быстро возрастает и точность, требуемая для его вычисления.

Периодические цепные дроби

Как доказал Лагранж, все квадратичные иррациональности (и только они) разлагаются в периодические цепные дроби. Как учитывает это обстоятельство система Mathematica? Давайте выясним это на примере разложения квадратных корней из чисел начального отрезка натурального ряда, деленных на 1, 2, 3. Вот определение нужных нам функций.
Fn0l[n_]:=Sqrt[n]
Fn02[n_]:=Sqrt[n]/2
Fn03[n_]:=Sqrt[n]/3

Теперь можем написать программу.
Do[Print[n," : ",
ContinuedFraction[FnOl[n]],":",
ContinuedFraction[Fn02[n]],":",
ContinuedFraction[Fn03[n]] ],{n,1,100}]

Результаты отформатируем в виде таблицы.

Эта таблица заслуживает того, чтобы рассмотреть ее более внимательно. Многие приведенные в таблице квадратичные иррациональности имеют вид 2 >q. Во-первых, период цепной дроби, представляющей такую квадратичную иррациональность, начинается сразу после целой части. (Это следует из теоремы о чисто периодических цепных дробях, которую Эварист Галуа опубликовал в 1828 году.)

Во-вторых, последний элемент периода равен удвоенной целой части. (Это следует из доказанной Эваристом Галуа теоремы о том, что в случае чисто периодического разложения сопряженная квадратичная иррациональность имеет те же элементы, но расположены они в обратном порядке.)

Наконец, давайте посмотрим, как в системе Mathematica представляются чисто периодические разложения.
ContinuedFractiont(1+13^(1/2))/3]
{1,{1,1,6,1,1}}

Сюрприз! Целая часть, как видите, выделена отдельно, а период записан только со следующего звена! Во многих учебниках по теории чисел считается, что период начинается с первого звена и потому вся дробь записывается в виде {{1,1,1,6,1}}. Конечно, здесь различие только внешнее, но его следует иметь в виду, сравнивая результаты, полученные с помощью системы Mathematica, с результатами, полученными другими системами. Впрочем, при разложении чисел в цепные дроби могут происходить и более серьезные неожиданности...

Частные случаи разложения чисел в цепные дроби

 Очень"иррациональный" случай: 

Число 

Как видите, ничего не получилось. Система Mathematica говорит, что цепная дробь бесконечна, не имеет периода, и потому советует указать количество необходимых элементов. На самом же деле все эти иррациональности запутали систему Mathematica. Она нуждается в указании упростить выражение. Давайте дадим ей это указание, а заодно и напечатаем числитель и знаменатель нашего очень "иррационального", но на самом деле рационального числа.

Как видите, число оказалось на самом деле рациональным (числители выделены курсивом, а знаменатели — полужирным), а цепная дробь — конечной, но система Mathematica об этом не догадалась. Этот случай говорит о том, что иногда нужно подсказывать, что некоторые выражения можно упрощать. Без этого в данном случае разложение не получить.

Интерес представляют и полученные разложения: все их элементы равны 2, а количество элементов равно п. Никакие другие числа этим свойством не обладают.

Некоторые полезные разложения квадратичных иррациональностей в цепную дробь

В задачниках часто используются разложения в цепную дробь квадратичных иррациональностей вроде

Составим таблицу разложения их в цепные дроби. Сначала определим нужные нам функции.
Fnl[n_]:=  Sqrt[n^2+1]
Fn2[n_]:=  Sqrt[n^2+l]/2 
Fn3[n_]:=  Sqrt[n/42 + l]/n

Вот как выглядит программа для разложения этих иррациональностей.
Do[Print[n,":",
ContinuedFraction[Fnl[n]],":",
ContinuedFraction[Fn2[n]]   ," : ",
ContinuedFraction[Fn3[n]]],{n,1,100} ]

Результаты оформлены в виде таблицы.

Посмотрите внимательно на третий и четвертый столбцы этой таблицы. Вы увидите нечто весьма интересное:    , то несколько удивительно то, что его разложение даже проще: (1, {2n^2,2}}.

Составим таблицу разложения    в цепные дроби. Сначала определим нужные нам функции.
Fn1[n_]:= Sqrt[n^2+2]
Fn2[n_]:= Sqrt[n^2+2]/n
Fn3[n_]:= Sqrt[n^2+2]/Sqrt[n^2+1]

После выполнения программы составляем таблицу .

Из таблицы видно, что период всех дробей, являющихся разложением чисел  , имеет, пожалуй, наиболее сложный период — все его элементы зависят от п. В периодах разложения двух "более сложных" иррациональностей,   лишь первый элемент периода зависит от п. Правда, зависимость эта от n нелинейная, и это как бы "компенсирует" постоянство второго элемента периода. Составим теперь таблицу разложения квадратичных иррациональностей    в цепные дроби. Вот определения нужных нам функций.
Fn1[n_]:=  Sqrt[n^4 + 2n]
Fn2[n_]:=  Sqrt[2n^3+1]/2

Программа может быть такой.
Do[Print[n,":",
ContinuedFraction[Fnl[n]],":",
ContinuedFraction[Fn2[n]]],{n,1,100}]

По результатам выполнения программы составляем таблицу. Обратите внимание на третий столбец этой таблицы. Вы увидите, что длина периода некоторых дробей вида 

Составим теперь таблицу разложения квадратичных иррациональностей 

Программу можно не менять; результат выполнения ее представлен в табл. Б.7.

Интересно отметить, что хотя квадратичная иррациональность    ее период в два раза длиннее.

Более того, в разложении квадратичной иррациональности 

Чтобы составить таблицу разложения квадратичных иррациональностей    в цепные дроби, нужно дать лишь новые определения нужным нам функциям.
Fnl[n_]:=  Sqrt[rr6+2n]
Fn2[n_]:=  Sqrt[2n^5+l]/(n^3)

Обратите внимание на то, что у заурядной иррациональности    в цепную дробь имеет такой длинный период! Квадратный корень сам по .себе, между прочим, в длине периода не виноват, поскольку период разложения 

Составим, наконец, таблицу разложения в цепные дроби квадратичных иррациональностей 
Fnl[n_]:=  Sqrt[nA2+n+l]
Fn2[n_]:=  Sqrt[rr2+n+l]/n

После выполнения программы составляем таблицу . Обратите внимание на второй столбец этой таблицы. Вы увидите, что вполне заурядная иррациональность    отличающаяся всего лишь наличием простенького знаменателя!

Трудные случаи при разложении чисел в цепные дроби

Казалось бы, при разложении чисел в цепные дроби никаких неожиданностей быть не может, поскольку любое вещественное число можно представить в виде цепной дроби (конечной или бесконечной). Ну а при желании такую дробь всегда можно оборвать, и тогда получится приближение разлагаемого числа с помощью цепной дроби. Но мы уже видели, что не все так просто. Давайте попробуем разложить в цепную дробь число Пизо.

Собственно, не хватило точности. Пока ничего удивительного, даже подсказка есть. Последуем совету.

Сейчас уже $MaxExtraPrecision = 10000000, и потому несколько странно выглядит упоминание о точности 3698. Может быть, система Mathematica вообще не может разложить это число в цепную дробь? Это очень досадно! Не может найти даже 10 звеньев! А если мне нужно узнать, чему равно, например, 1947-е звено? Похоже, ничего поделать нельзя.

Зачем было только увеличивать количество звеньев до 1747, если не удается вычислить ни двух, ни десяти? А за тем, чтобы показать вам сюрприз. Второе звено я выделил курсивом, кое-что опустил (поставил многоточие), но все равно будьте внимательны.

В чем сюрприз? Конечно, не в том, что второе звено содержит 1832 цифры — именно этого мы ожидали, зная, что после запятой следует 1831 нуль. Непостижимо другое: найти 2, 3, ..., 1947 звеньев система Mathematica не может, а вот 1948 (и больше) — может!

Давайте обсудим сложившуюся ситуацию. Оказывается, чтобы найти 2-е, 3-е, ..., 1947-е звено, нужно, как минимум, найти 1948 звеньев, причем нужно догадаться, что если система Mathematica ругается и говорит, что ей что-то не под силу, то задачу нужно сделать более трудной, и только тогда система Mathematica справится с ней в мгновение ока и к тому же без труда!

Я предпочитаю систему Mathematica, поскольку она помогает мне справиться со многими задачами быстрее, чем другие системы компьютерной алгебры. Но должен отметить, что поведение ее в данном случае интуитивно непонятно, и учесть такую возможность в программе весьма непросто. Конечно, система Mathematica — пример системы с искусственным интеллектом, а поведение таких систем предсказуемо далеко не всегда, как и поведение человека. Иногда ведь и человек может справиться с очень трудной задачей, но не может найти ключ к решению более простой задачи. Тем не менее в данном случае от компьютера хотелось бы более детерминированного результата.

Ну и еще один вопрос: это исключение, не так ли? Можете считать, что да. (Сам поступаю очень часто именно так.) Но тогда приходится признать, что таких исключений очень много. Например, добавляя к числу Пизо целые числа, вы получите серию (теоретически бесконечную) новых исключений. Если вы считаете, что такие исключения связаны с кубическими корнями из числа три, то я вас разочарую. Вот число, которое с виду в несколько раз проще, но в десятки (а может, сотни или тысячи) раз "подлее" с точки зрения функции ContinuedFraction.
х=1000!+(Sqrt[2]-1)^10000

Система Mathematica не сможет превратить его в цепную дробь, если вы укажете менее 3667 необходимых звеньев. А если все же указать 3667 звеньев, то тут как раз и окажется, что она может вычислить всего лишь 2613 из заданных 3667.

Далее система Mathematica честно выпишет обещанные 2613 звеньев, причем на первом месте, конечно, будет записано десятичное представление 1000!.. Может быть, все дело в факториале — 1000!? Нет, то же самое происходит и с числом 1 + (√2 -1)10000. Но ведь это квадратичные иррациональности, и цепные дроби должны  быть периодическими! Может, просто не нужно указывать период и получить точное представление? Так и поступим.

Система Mathematica справилась! Она может обнаружить, что цепная дробь периодическая, и правильно определяет ее период. Он, кстати, оказался очень коротким: всего лишь два звена! Так что не составило бы труда выписать и десятки тысяч звеньев, ведь для этого необходимо только достаточное число раз повторить период. Но до этого может догадаться пока лишь человек. Я же надеюсь, что в следующей версии сможет это и система Mathematica! Давайте теперь рассмотрим саму цепную дробь. (Недаром же я привожу ее в книге.) Оказывается, здесь тоже есть неожиданности. Во-первых, первое звено цепной дроби равно 2, хотя целая часть числа равна 1.

Это указывает на то, что в системе Mathematica первое звено цепной дроби не всегда равно целой части числа, даже если число положительно. Во-вторых, оба звена в периоде отрицательны. Все это может усложнить восприятие числа и никоим образом не одобряется авторами учебников и задачников по теории чисел. Такое представление не является стандартным, и потому будьте внимательны. А вот пример стандартного представления:

А вот и еще один пример. Попытаемся разложить целое число 40= Sgrt[57-40Sqrt[2]]-Sqrt[57+40Sqrt[2]] В цепную дробь.

Результат вообще абсурдный:

Заметьте, утверждается, что дробь не является ни конечной, ни периодической! Против отсутствия периода я бы не спорил, но звеньев-то всего одно! Если же указать фактическое количество звеньев, результат получить все равно не удастся.

Фокус с увеличением количества звеньев (например, до миллиона) здесь не проходит, поскольку трудности возникают уже при вычислении целой части, т.е. первого звена.

Мы разобрали всего лишь несколько примеров, где поведение системы Mathematica, мягко скажем, слабо предсказуемо. Но, надеюсь, вы понимаете, что аналогичное произойдет и в случае чисел вида 

целых 5, k, n, q, удовлетворяющих неравенствам 1<k<n. Конечно, наверняка можно придумать и другие формулы, доставляющие "плохие" числа. Если все это исключения, то не слишком ли их много?! После всего сказанного, возможно, вы даже подозреваете, что неприятности будут вообще в случае чисел вида 1 +е при очень малых е, например при ε= 1/(1000!). Так вот она, непредсказуемость: при ε= 1/(10000!) все происходит без каких-либо неожиданностей. И вообще, при рациональных е неприятностей не бывает. Недаром рациональный значит "разумный"! И уж если мы заговорили о разумном и рациональном, то не разумно ли было бы научиться рациональным способам проверки правильности полученных разложений в цепную дробь? Для этого нужно всего лишь научиться (с помощью системы Mathematica) находить числа по их представлению в виде цепных дробей. Оказывается, это совсем несложно, и именно к этому мы сейчас и перейдем.


Преобразование непрерывной дроби в число: функция FromContinuedFraction



Функция FromContinuedFraction является обратной к функции Continued-Fraction. Она преобразует цепную дробь в число. Вот пример.

Ну а как функция FromContinuedFraction справляется с периодическими цепными дробями? Оказывается, она вычисляет равную им квадратичную иррациональность.

С этой задачей система Mathematica справляется даже в том случае, если период повторен несколько раз.

Наконец, осталось исследовать случай чисто периодического разложения. Вот пример.

Но что произойдет, если период задать иначе, например начать его с первого звена? Оказывается, система Mathematica справляется и с этим.


Мнимая единица



На специальной панели символов системы Mathematica имеется мнимая единица, но иногда ее удобно ввести просто как букву I или даже как \ [Imaginaryi] или \ [ImaginaryJ]. Вот примеры.

2I + 1
1+2i
2J+5
5+2i
 


Вещественная часть комплексного числа: функция Re



Это совсем незамысловатая функция, возвращающая вещественную часть комплексного числа.

Re[3+4I] 3
Re[a+bI]
-Im[b]+Re[a]

Заметьте, что в последнем примере вещественность а и b не предполагается.


Мнимая часть комплексного числа: функция Im



Тоже совсем незамысловатая функция, возвращающая мнимую часть комплексного числа.

Im[3 + 4I]4
{Im[a+bI],ComplexExpand[Im[a+b  I]])
{Im[a]+Re[b] ,b>

Заметьте, что в случае Im[a+b I] вещественность а и b не предполагается — в отличие от случая, когда используется функция ComplexExpand.


Аргумент комплексного числа: функция Arg



Функция Arg[z] возвращает аргумент комплексного числа z.

Вот как, например, можно получить аргументы корней четвертой степени из 1.

Возвращаемый угол всегда по абсолютной величине не превосходит n.


Сопряженное комплексное число: функция Conjugate



Выражение Conjugate [z] представляет собой сопряженное комплексное число z . Вот как, например, можно получить число, сопряженное к х+I у.

Conjugate[х+Iу]
Conjugate[x]-IConjugate[у]

Заметьте, что х и у предполагаются комплексными.

Мы рассмотрели основные числовые системы,



Мы рассмотрели основные числовые системы, предусмотренные в системе Mathe-matica. Они полностью охватывают классическую математику. Благодаря такому богатству система Mathematica может помочь в решении практически любых математических задач. Но благодаря этому же богатству при решении задач можно столкнуться с теми же проблемами, что и в математике. И потому решение исследовательских задач с помощью системы Mathematica может потребовать основательного знакомства с методологией применения данной системы в конкретной области науки и техники. Конечно, по высказыванию Гаусса, математика — царица всех наук. И потому в первую очередь следует освоить именно методологию применения системы Mathematica к решению математических задач. И начнем мы с царицы математики (по выражению того же Гаусса) — с арифметики.