Заметки о Windows и других программных продуктах Microsoft...

Математические функции в PowerShell

Математические функции в PowerShell

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

базовые математические действия в PowerShell

 

А вот для более сложных математических операций придется задействовать статический класс [math]. В этот класс входит около 30 свойств и методов, с помощью которых можно производить различные математические действия. Для начала выведем эти методы командой:

[math] | Get-Member -Static

свойства и методы класса [math]

Ну а теперь рассмотрим их все по порядку.

Константы

Начнем с двух свойств, E и PI. Как вы наверное догадались, это математические константы. PI равно отношению длины окружности к длине её диаметра, E — основание натурального логарифма. Вывести их значение можно командой:

[math]::PI
[math]::E

константы P и E

Степени, корни и логарифмы

Переходим к методам. Метод ::Pow(x,y) возводит число х в степень у, например:

[math]::Pow(3,2) возвращает 9

Метод ::Sqrt(x) вычисляет квадратный корень из числа x, например:

[math]::Sqrt(9) возвращает 3

возведение в степень и взятие квадратного корня

 

Метод ::Exp(x) служит только для одного —  возведения в степень x числа E. Например так возведем E в квадрат:

[math]::Exp(2)

а так в куб:

[math]::Exp(3)

возведение в степень числа е

 

Продолжая тему числа E, рассмотрим еще парочку методов. Метод ::Log(x) вычисляет натуральный логарифм числа x (логарифм с основанием e), а метод ::Log10(x) — десятичный логарифм  (логарифм с основанием 10). Например:

[math]::Log(2)
[math]::Log10(2)

логарифм натуральный и десятичный

Округление

Округление — довольно часто встречающаяся операция. Метод ::Round(x,y) округляет число x, а y задает нужное количество знаков после запятой. Например:

[math]::Round(1234.5678, 2) возвращает 1234.57
[math]::Round(1234.5678, 0) возвращает 1235

округление числа с заданной точностью

 

Обратите внимание на правила округления:

[math]::Round(12.345, 2) возвращает 12.34
[math]::Round(12.346, 2) возвращает 12.35

правила округления

 

Метод ::Truncate(x) также можно использовать для округления числа x, однако в отличие от предыдущего метода округление производится очень грубо — путем отбрасывания всех знаков после запятой. Например:

[math]::Truncate(1.2) возвращает 1
[math]::Truncate(1.8) возвращает 1
[math]::Truncate(-1.2) возвращает -1
[math]::Truncate(-1.8) возвращает -1

обрезка числа

 

И еще два метода округления. Метод ::Ceiling(x) округляет число х в большую сторону до ближайшего целого значения. Например:

[math]::Ceiling(1.2) возвращает 2
[math]::Ceiling(1.8) возвращает 2
[math]::Ceiling(-1.2) возвращает -1
[math]::Ceiling(-1.8) возвращает -1

округление в большую сторону

 

Метод ::Floor(x) также округляет число до ближайшего целого значения, но в меньшую сторону. Например:

[math]::Floor(1.2) возвращает 1
[math]::Floor(1.8) возвращает 1
[math]::Floor(-1.2) возвращает -2
[math]::Floor(-1.8) возвращает -2

округление в меньшую сторону

Сравнение

Есть в классе [math] пара методов для сравнения. К примеру метод ::Min(x,y) возвращает наименьшее, а метод ::Max(x,y) — наибольшее из двух чисел:

[math]::Min(1,2) возвращает 1
[math]::Max(1,2) возвращает 2
[math]::Min(1,-2) возвращает -2

выбор минимума и максимума

 

А метод ::Equals(x,y) сравнивает числа х и y и возвращает True, если числа ровны и False, если не ровны. Например:

[math]::Equals(1,2) возвращает False
[math]::Equals(2,2) возвращает True

сравнение двух чисел

 

Важно помнить, что для сравнения x и у должны иметь один тип данных. К примерк, для оператора Equals 2 (int32) не равно 2.0 (double) или ″2″ (string):

[math]::Equals(2,2.0) возвращает False
[math]::Equals(2,″2″) возвращает False

сравнение различных типов

Абсолютное значение и знак числа

Метод ::Abs(x) возвращает абсолютное значение числа х, т.е. значение без учета знака. Например:

[math]::Abs(10) возвращает 10
[math]::Abs(-10) возвращает 10

абсолютное значение числа

 

Метод ::Sign(x) возвращает значение, определяющее знак числа х — 1 если число положительное, -1 если число отрицательное и 0, если x равен 0. Например:

[math]::Sign(20) возвращает 1
[math]::Sign(0) возвращает 0
[math]::Sign(-10) возвращает -1

определение знака числа

 

В качестве x можно передавать не только отдельные числа, но и выражения:

[math]::Sign(10-15) возвращает -1
[math]::Sign(-1*2+2) возвращает 0

определение знака выражения

Разное

Теперь рассмотрим некоторые специфические функции, которые скорее всего вам никогда не понадобятся 🙂

Функция ::IEEERemainder(x,y) возвращает остаток от деления X / Y, однако делает это несколько необычным образом. Так при делении X / Y остаток вычисляется по формуле X — (Y * Q), где Q является частным от деления X / Y, округленным до ближайшего целого числа. Если X / Y находятся на равном расстоянии от двух целых чисел, то выбирается четное. Поскольку значение Y * Q может быть больше чем X, остаток может принимать как положительные, так и отрицательные значения. Например:

[math]::IEEERemainder(19,6) возвращает 1
[math]::IEEERemainder(18,6) возвращает 0
[math]::IEEERemainder(17,6) возвращает -1

Другими словами, IEEERemainder возвращает минимальное число, которое необходимо добавит или вычесть из делимого X, чтобы сделать его кратным делителю Y.

получение остатка от деления

 

Метод ::BigMul предназначен для умножения двух 32-битных чисел. Результат умножения возвращается в виде 64-битного числа. Использовать этот метод стоит в том случае, если для результата вам не хватает 32-битов.

умножение двух чисел

 

Метод ::DivRem(x,y,[ref]$R) вычисляет результат деления X/Y и возвращает остаток от деления в выходном параметре ($R). Обратите внимание, что переменная $R должна быть определена заранее:

$R = 0
[math]::DivRem(20,3,[ref]$R) возвращает частное 6
$R возвращает остаток от деления 2

получение частного и остатка от деления

Тригонометрические функции

Ну и в завершение тригонометрические функции. Наврядли вы будете использовать их в своих скриптах, поэтому привожу их исключительно для общего развития. Напомню, что по умолчанию эти функции вычисляются в радианах, поэтому для перевода в градусы необходимо использовать конструкцию (x/180*Pi). Например вычислим синус 90º:

$Pi = [math]::PI
[math]::Sin(90/180 * $Pi)

косинус 180º:

[math]::Sin(180/180 * $Pi)

или тангенс 45º:

[math]::Tan(45/180 * $Pi)

тригонометрические функции

 

Обратные тригонометрические функции. Они также вычисляются в радианах, для преобразования в градусы результат надо умножить на 180/Pi. Для примера вычислим арксинус 1 (угол, синус которого равен 1):

[math]::Asin(1)*180/$Pi

арктангенс 0:

[math]::Atan(0)*180/$Pi

и арккосинус -1:

[math]::Acos(-1)*180/$Pi

обратные тригонометрические функции

 

Ну вот, основные математические функции PowerShell мы рассмотрели. А более подробно познакомится со свойствами и методами класса [math] можно на MSDN.

 
 
Комментарии

Поправьте, пожалуйста:
должно быть IEEERemainder вместо IEEEReminder

Спасибо. Поправил.

Леколь

Кирилл, салют!

Имеем файл содержащий строки с формулами.
Например первая строка файла имет вид: «3+4»

Какой системной или [math].функции передать эту строку
в качестве аргумента, чтобы она вернула результат?

Естественно, в строке консоли всё катит нормально,
то есть при вводе 3+4 энтер, получаем результат = 7.

Естественно, в скрипте: $x=3+4 тоже аккуратно даёт «7».

Так какая же функция вроде «calculate($x)» из API
или «eval($x)» из JavaScript занимается этим в PowerShell?

Леколь

Эврика! После пробы по списку командлетов.

Один из возможных ответов таков:

командлет: Invoke-Expression
алиас: iex

Пример: $expr = «(2+3)*4»; $answ = iex $expr

Вадим

Поправьте, пожалуйста в Round:

[math]::Round(1234.5678, 2) возвращает 1234.56 — должно быть 1234.57
[math]::Round(1234.5678, 0) возвращает 1234 — должно быть 1235

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

Поправил. Спасибо.

Leave a Reply to Kirill