Android studio математические функции

Класс Math и пакет java.math

Класс Math содержит методы, связанные с геометрией и тригонометрией и прочей математики. Методы реализованы как static, поэтому можно сразу вызывать через Math.methodName() без создания экземпляра класса.

В классе определены две константы типа double: E и PI.

Популярные методы для тригонометрических функций принимают параметр типа double, выражающий угол в радианах.

  • sin(double d)
  • cos(double d)
  • tan(double d)
  • asin(double d)
  • acos(double d)
  • atan(double d)
  • atan2(double y, double x)

Существуют также гиперболические функции: sinh(), cosh(), tanh().

Из них хорошо знакомы возведение в степень — pow(2.0, 3.0) вернёт 8.0.

Также популярен метод для извлечения квадратного корня — sqrt(4.0). Если аргумент меньше нуля, то возвращается NaN. Похожий метод cbrt() извлекает кубический корень. Если аргумент отрицательный, то и возвращаемое значение будет отрицательным: -27.0-> -3.0.

  • abs() — возвращает абсолютное значение аргумента
  • ceil() — возвращает наименьшее целое число, которое больше аргумента
  • floor() — возвращает наибольшее целое число, которое меньше или равно аргументу
  • max() — возвращает большее из двух чисел
  • min() — возвращает меньшее из двух чисел
  • nextAfter() — возвращает следующее значение после аргумента в заданном направлении
  • nextUp() — возвращает следующее значение в положительном направлении
  • rint() — возвращает ближайшее целое к аргументу
  • round() — возвращает аргумент, округлённый вверх до ближайшего числа
  • ulp() — возвращает дистанцию между значением и ближайшим большим значением
  • copySign() — возвращает аргумент с тем же знаком, что у второго аргумента
  • getExponent() — возвращает экспоненту
  • IEEEremainder() — возвращает остаток от деления
  • hypot() — возвращает длину гипотенузы
  • random() — возвращает случайное число между 0 и 1 (единица в диапазон не входит)
  • signum() — возвращает знак значения
  • toDegrees() — преобразует радианы в градусы
  • toRadians() — преобразует градусы в радианы

Вычислим наибольшее и наименьшее числа из двух заданных значений.

Большие числа

Если вам не хватает точности основных типов для представления целых и вещественных чисел, то можно использовать классы BigInteger и BigDecimal из пакета java.math, которые предназначены для выполнения действий с числами, состоящими из произвольного количества цифр.

Для преобразования обычного числа в число с произвольной точностью (называемое большим числом) вызывается статический метод valueOf():

При работе с большими числами нельзя использовать привычные математические операции с помощью + или * и т.п. Вместо них следует использовать специальные методы add() (сложение), multiply() (умножение), divide() (деление) и т.д.

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

Источник

Дополнительные классы

Математические вычисления и класс Math

Для выполнения различных математических операций в Java в пакете java.lang определен класс Math . Рассмотрим его основные методы:

abs(double value) : возвращает абсолютное значение для аргумента value

acos(double value) : возвращает арккосинус value. Параметр value должен иметь значение от -1 до 1

asin(double value) : возвращает арксинус value. Параметр value должен иметь значение от -1 до 1

atan(double value) : возвращает арктангенс value

cbrt(double value) : возвращает кубический корень числа value

ceil(double value) : возвращает наименьшее целое число с плавающей точкой, которое не меньше value

cos(double d) : возвращает косинус угла d

cosh(double d) : возвращает гиперболический косинус угла d

exp(double d) : возвращает основание натурального логарифма, возведенное в степень d

floor(double d) : возвращает наибольшее целое число, которое не больше d

floorDiv(int a, int b) : возвращает целочисленный результат деления a на b

log(double a) : возвращает натуральный логарифм числа a

log1p(double d) : возвращает натуральный логарифм числа (d + 1)

log10(double d) : возвращает десятичный логарифм числа d

max(double a, double b) : возвращает максимальное число из a и b

min(double a, double b) : возвращает минимальное число из a и b

pow(double a, double b) : возвращает число a, возведенное в степень b

random() : возвращает случайное число от 0.0 до 1.0

rint(double value) : возвращает число double, которое представляет ближайшее к числу value целое число

round(double d) : возвращает число d, округленное до ближайшего целого числа

scalb(double value, int factor) : возвращает произведение числа value на 2 в степени factor

signum(double value) : возвращает число 1, если число value положительное, и -1, если значение value отрицательное. Если value равно 0, то возвращает 0

sin(double value) : возвращает синус угла value

sinh(double value) : возвращает гиперболический синус угла value

sqrt(double value) : возвращает квадратный корень числа value

tan(double value) : возвращает тангенс угла value

tanh(double value) : возвращает гиперболический тангенс угла value

toDegrees(double value) переводит радианы в градусы и toRadians(double value) — градусы в радианы

Источник

Математический пакет для Android своими руками

Мне понравилась дискуссия, развернувшаяся по поводу этой статьи. Однако мне более интересен немного иной аспект дискутируемой проблемы, а именно: нужна ли система компьютерной алгебры на смартфоне или планшете, или это такой странный таракан в голове околоайтишного инженера?

Читайте также:  Котлин с нуля android studio

Постановка проблемы

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

Каких-то особых ограничений не было, за свою научную карьеру я успел попользовать и Mathcad с MATLAB, и Математику, и FEM-системы (Ansys). Поэтому для начала стал смотреть все подряд.

Сложилась такая картина (я не буду приводить ссылки, желающие легко могут найти это на Play-маркете):

  • Matlab Mobile, как расширение лицензионной копии десктопного варианта. У меня таковой дома не оказалось, поэтому этот вариант, к сожалению, отпал;
  • Сервис Wolfram Alpha и туча обучалок от Wolfram Group — не совсем то, что у меня ассоциируется со словами «посчитать самостоятельно»;
  • Клоны «Матлаба» и «Октавы» под Android — уже теплей, но писать код на экране в 5 дюймов не очень-то удобно;
  • Огромное количество научных калькуляторов разной степени навороченности. Их всех объединяет одно — ввод и представление результатов организованы как в классическом (хардверном) графическом калькуляторе. Основной минус такой идеи — это отсутствие «документа», который можно сохранять, изменять и пересчитывать вновь и вновь;
  • Ничего, что походило бы на Маткад, тогда найти не удалось.

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

  • На небольшом экране устройства с пальце-ориентированным интерфейсом все-же удобней работать с формулой, если она записана в естественном математическом виде, а не в виде кода на скриптовом языке;
  • Мобильное устройство хорошо подходит для того, чтобы что-то быстро попробовать. Поэтому от мобильной математической системы требуется удобный интерфейс, но не требуется серьезных вычислительных возможностей;
  • В идеале, в такой системе нужна функция «Я пиарюсь». То есть не только быстро записать сложную формулу и построить пару графиков, но и удобно опубликовать это во всех своих социальных сетях. Формулы в естественной математической нотации здесь тоже более удобны, чем скрипт.

То есть я бы с удовольствием установил бы Mathcad mobile на свой смартфон. Но вот его-то (в смысле «Маткада», а не смартфона) на Play-маркете и не оказалось. Отсюда и родилась идея разработать нечто подобное самостоятельно.

Формулировка задачи

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

Требования к приложению я сформулировал так:

  • Максимально широкий охват поддерживаемых устройств. Отсюда минимальный API level 8;
  • Поддержка экранов различных разрешений и ландшафтной/портретной ориентации;
  • Формат хранения документов — свой на основе XML;
  • Подробная документация. Чтобы не плодить сущностей, для документирования используется тот же самый формат, в котором хранятся сами документы;
  • Для создания печатной документации предусмотреть экспорт в LaTeX, так как он удобен для записи формул и дает возможность сгенерировать PDF;
  • Математика безгранична. Все не реализовать. Поэтому начальный функционал включает в себя функции многих переменных, графики (2D и 3D), численное интегрирование и дифференцирование, логический оператор. Далее в зависимости от хотелок пользователей;
  • Возможность вставки текста и изображений, но функционал редактирования текста для начала минимальный;
  • Удобность использования и качество имеют приоритет над функционалом;
  • Языки только те, что знаю сам и смогу развивать и поддерживать без обращения к переводчику.

И, наверное, самое главное. Это — хобби. Поэтому важно оставаться реалистом и не замахиваться на то, что невозможно реализовать одному человеку за разумное время в режиме 5-6 дней в неделю по 2 часа.

Так как проект получил статус «любимое хобби на ближайший год», то отсюда два важных следствия:

  • Я решил не ограничивать себя в разумных тратах на технику/продвижение/услуги, если таковые потребуются;
  • Такие цели, как «Заработать любой ценой» и «Оказаться в топе» не ставятся, поэтому я решил не добавлять рекламу в приложения и отказаться от продвижения через мотивированные загрузки.

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

  • Само приложение является платным и распространяется только через Play-маркет;
  • Имеется бесплатная версия с идентичным внешним видом и интерфейсом, но с урезанной математикой. Причем этот функционал не деактиварован, а отсутствует на уровне кода. То есть бесплатную версию физически нельзя переключить в полный режим и она распространяется везде, где только можно.

Такая модель легко реализуется с использованием системы контроля версий (в моем случае SVN), где основная ветка предназначена для экспериментов и разработки, а две дочерние — для релизов платной и бесплатной версий соответственно.

Читайте также:  Андроид полностью заполнена память

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

Метод решения

На мой взгляд, самый главный вопрос такой — как организовать на смартфоне ввод и редактирование формул, которые можно вычислять (для начала только численно), но при этом они представлены в естественном математическом виде? Как скомпоновать из этих формул, графиков, текста и загружаемых из файла картинок единый документ, способный самовычисляться?

Многие из вас наверняка использовали вордовский редактор формул. На большом экране, да с клавиатурой и мышкой под рукой все очень просто. На экране видны различные математические палитры (или легко доступны из меню), мышкой позиционируется курсор, а далее либо с клавиатуры, либо мышкой из палитры вводится нужный символ. Часть формулы можно легко выделить мышкой, скопировать, заменить или перетащить в другое место. Сами формулы как плавающие объекты можно перетащить мышкой в любую часть документа. Знакомо, да?

А теперь то же самое на сенсорном экране, без мышки, без хардверной клавиатуры, где виртуальная клавиатура перекрывает треть (в ландшафтной ориентации половину) экрана?

Начну с компоновки объектов в документе. Вариантов, на самом деле, не очень много:

  • Каждый объект имеет свои координаты и объекты могут располагаться относительно друг друга произвольно, как в векторном графическом редакторе. Именно этот вариант реализован в самом Маткаде. Под Андроидом можно использовать для этого устаревший AbsoluteLayout, но при этом необходимо реализовать выравнивание/распределение объектов и групп объектов. То есть в этом варианте нужен дополнительный пользовательский интерфейс, не относящийся к основной задаче. Для настольного компьютера это не критично, однако юзабилити мобильного приложения, на мой взгляд, от этого будет хуже;
  • Расположение в ячейках таблицы, как в MS Excel. Этот вариант я отмел сразу, так как математический документ — это все что угодно, но только не таблица;
  • Простой список, где каждый объект в своей строке. Именно так устроены большинство научных калькуляторов. Именно это я и реализовал в первой версии приложения. Дешево и сердито. На что получил вполне резонные замечания пользователей, что такой метод очень неудобен, так как есть объективная потребность группировать некоторые формулы по строкам;
  • В результате получилась упрощенная версия RelativeLayout, этакий двумерный список, где по умолчанию объекты добавляются вертикально (снизу выделенного объекта), но с помощью одного единственного окна можно добавить объект как справа, так и слева от выделенного:

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

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

Однако вынуждать пользователя запоминать все коды — не есть хорошая идея. Поэтому внизу экрана, вне зависимости от ориентации, расположена вторая панель инструментов, по оформлению и размерам идентичная верхней основной. Все математические символы, коих сейчас около 50-ти, расположены в одну линию на этой панели, а сама она прокручивается вправо и влево. При коротком нажатии символ вводится. При долгом нажатии на символ всплывает подсказка, что это и какой код ему соответствует:

В подтверждение этой идеи хочу процитировать отзыв одного из пользователей: «Beeing able to use shortcuts instead of symbolic buttons (but not beeing forced to do so) makes the app perfect».

А куда вводятся коды или символы? Здесь опять все похоже на Маткад. При добавлении объекта появляются пустые поля ввода. В них можно вводить текст, числа или символы. При вводе, например, символа деления вместо поля ввода появляется дробь с двумя полями, в одно из которых перекочует текст, введенный ранее в удаленном поле. Это основной режим ввода, который хорош, когда точно знаешь последовательность набора нужной формулы:

А если не знаешь или нужно что-то изменить в формуле? Контекстное меню в помощь. Оно активируется при долгом нажатии на часть формулы и предоставляет доступ к буферу обмена. Кроме этого, там есть кнопка расширения области выделения. С нижней панели инструментов можно ввести символ, который будет применен к выделенному блоку:

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

Таким образом, каждая формула имеет два аспекта:

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

  • Во-вторых, это иерархическая структура примитивных математических токенов, каждый из которых умеет вычисляться. Каждый токен связан с соответствующим ему лайаутом и является его владельцем.
  • Читайте также:  Android downloading and building

    Подводные камни

    И вот здесь меня поджидала серьезная засада. Де-факто в Андроиде есть ограничение на количество вложенных лайаутов, связанное с размером стека вызова процедур. Компилятор в этом случае ничего не скажет, но во время работы (в методе android.view.View.draw одного из вложенных лайаутов) приложение валится с исключением типа StackOverflowErrors. Подробнее об этом здесь.

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

    Экспериментально я подобрал следующие значения предельной глубины, считая от корневого RelativeLayout фрагмента:

    • если API level 17 (4.3.x и выше), то 15 уровней.

    Вторая проблема — отсутствие стандартной компоненты, которая бы сочетала в себе горизонтально-вертикальный скроллинг и масштабирование. Эти действия вроде как поддерживаются WebView, но вот сама WebView мне никак не подходит. Решение топорное, но работает — я взял исходники стандартных ScrollView и HorizontalScrollView, объединил их в одну компоненту и прикрутил детектирование и обработку изменения масштаба. Что я при этом так и не смог довести до ума — это корректное позиционирование в документе после изменения масштаба.

    Документация и локализация

    Читая отзывы пользователей на Play-маркете про различные научные калькуляторы, я обнаружил, что одним из слабых мест большинства калькуляторов является отсутствие документации. Иногда полное. Поэтому я решил уделить документации достаточно много внимания. И добавил ее как в само приложение (для этой цели удобным оказалось боковое меню NavigationDraver), так и выложил в сети в виде PDF и добавил в приложение ссылки для прямой загрузки.

    В приложении разделы документации хранятся в XML и открываются как отдельные фреймы. Имеется функция конвертации документа в LaTeX. Утилита pdfletx на рабочем месте довершает дело. Результат не стыдно выставить на всеобщее обозрение.

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

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


    То есть Россия, Украина и Казахстан вместе обеспечивают более 40% загрузок. Платная версия дает другую картину: загрузки из России доминируют лишь с незначительным отрывом.

    Заключение

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

    Что касается ближайших задач, то пока основные пожелания пользователей касаются наращивания экспортных возможностей. К примеру, один из последних комментариев: «Интересует такой вопрос, есть хоть какая нибудь возможность связать документ с маткадом? Что бы была возможность доработать документ на ПК». По поводу Маткада лично я сомневаюсь, так как формат проприетарный, но такие вещи, как экспорт в HTML (буквально сегодня обнаружил фреймворк MathJax), в PDF, или какой-нибудь открытый офисный формат можно реализовать.

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

    Источник

    Оцените статью