home.social

#функції — Public Fediverse posts

Live and recent posts from across the Fediverse tagged #функції, aggregated by home.social.

  1. CW: Оператор $ у :haskell:

    Через те що у Haskell аргументи функції не вкладаються у дужки при спробі передати результат однієї функції в іншу потрібно використати дужки для групування.

    foo bar x    -- Функції передаються два аргументи bar і x
    foo (bar x)  -- Функції bar передається аргумент x і її результат підставиться як один аргумент функції foo
    

    У цьому простому прикладі все виглядає просто і зрозуміло, але якщо у нас був би складніший вираз з іншими дужками все виглядало б не так зрозуміло.

    Для полегшення додали спеціальний оператор зниження пріоритету. Складається він з одного символу $. Використати його ми можемо тут підставивши між функціями.

    foo $ bar x
    

    Результат буде той же що й з дужками.

    Цей оператор має праву асоціативність і найнижчий пріоритет. Перевірити це ми можемо в інтерпретаторі.

    > :i ($)
    ($) :: (a -> b) -> a -> b 	-- Defined in ‘GHC.Base’
    infixr 0 $
    

    Тако ж у цьому повідомленні ми бачимо тип цього оператора. Він приймає іншу функцію й аргумент цієї функції, а повертає результат цієї функції. Визначення цього оператора таке.

    ($) f x = f x
    

    #ukrhaskell #програмування #haskell #оператор #$ #пріоритет #функції

  2. CW: Створення операторів і стандартні оператори :haskell:.

    У Haskell можна оголошувати свої оператори. Вони можуть складатись з одного або кількох символів. Дозволяються наступні символи ~!?.@#$%^&*-<=>+\|/. Також можна використовувати символ :, але він повинен розташовуватись у середині або кінці, не на початку.

    Оголошуються оператори в синтаксисі схожому на виклик

    x *+* y = x^2 + y^2
    

    або можна використати префіксну форму

    (*+*) x y = x^2 + y^2
    

    Примітка: Функції можна оголошувати в інфіксній формі.


    ЗВЕРНІТЬ УВАГУ!: Усі оператори є бінарні окрім унарного мінуса який обовʼязково обгортають в круглі дужки.

    Усі оператори мають пріоритети для правильної роботи, саме за їхньої допомоги вираз 2 + 2 * 2 вичислюється правильно й результат дорівнюватиме 6, а не 8. Є десять рівнів пріоритету від нуля до девʼяти.

    Але що робити з кількома операторами якщо у них один пріоритет, це може бути кілька викликів одного оператора. Тут потрібно використати асоціативність. Є два види асоціативності ліва і права. Ліва асоціативність це коли оператори застосовуються по черзі зліва на право, а права навпаки.

    (2 + 1) - 5 -- ліва
    2 + (1 - 5) -- права
    

    Оголошується асоціативність оператора за допомоги ключових слів:

    • infixl - ліва
    • infixr - права
    • infix - відсутня

    Якщо асоціативність відсутня, то такий оператор не можна викликати кілька раз або з іншими операторами того ж пріоритету в одному виразі.

    Вказується асоціація і пріоритет у такому синтаксисі infix[rl] <prio> <operator>. Вказується це, або до, або після оголошення самого оператора, але в інтерпретаторі це мусе бути одним рядком, тому їх потрібно розділити крапкою з комою.

    infixl 7 +**
    a +** b = a^2 + b^2
    

    Якщо цього не вказати, то оператор матиме ліву асоціативність і девʼятий, найвищий, пріоритет.

    Дізнатись цю інформацію про оператор можна за допомоги команди інтерпретатора info.

    ghci> infixl 7 +**; (+**) a b = a^2 + b^2
    ghci> 5 +** 4
    41
    ghci> :i (+**)
    (+**) :: Num a => a -> a -> a 	-- Defined at <interactive>:1:15
    infixl 7 +**
    

    Якщо явно не вказати infix, то й у виводі цієї команди не буде такої інформації.

    У Haskell немає вбудованих операторів. Всі стандартні оператори оголошені в стандартній бібліотеці. Є такі стандартні оператори.

    infixr 8   ^, ``
    infixl 7   *, /, `div`, `mod`
    infixl 6   +, -
    infix  4   ==, /=, <, <=, >=, >
    

    Це не всі, але інші ми розглянемо пізніше. Оператор `` це оператор виклику функції в інфіксному форматі. Виклик функції у префіксному вигляді має праву асоціативність і девʼятий пріоритет.

    /= це оператор не рівності, в інших мовах зазвичай він виглядає !=. Оператори порівняння не мають асоціативності, тому їх не можна обʼєднувати в ланцюжок.

    #програмування #haskell #hs #оператори #створення #оголошення #асоціативність #пріоритети #стандартні #стандартна #бібліотека #інтерпретатор #ghci #infix #infixl #infixr #виклик #функції #функцій #префіксна #інфіксна #форми

  3. CW: Створення операторів і стандартні оператори :haskell:.

    У Haskell можна оголошувати свої оператори. Вони можуть складатись з одного або кількох символів. Дозволяються наступні символи ~!?.@#$%^&*-<=>+\|/. Також можна використовувати символ :, але він повинен розташовуватись у середині або кінці, не на початку.

    Оголошуються оператори в синтаксисі схожому на виклик

    x *+* y = x^2 + y^2
    

    або можна використати префіксну форму

    (*+*) x y = x^2 + y^2
    

    Примітка: Функції можна оголошувати в інфіксній формі.


    ЗВЕРНІТЬ УВАГУ!: Усі оператори є бінарні окрім унарного мінуса який обовʼязково обгортають в круглі дужки.

    Усі оператори мають пріоритети для правильної роботи, саме за їхньої допомоги вираз 2 + 2 * 2 вичислюється правильно й результат дорівнюватиме 6, а не 8. Є десять рівнів пріоритету від нуля до девʼяти.

    Але що робити з кількома операторами якщо у них один пріоритет, це може бути кілька викликів одного оператора. Тут потрібно використати асоціативність. Є два види асоціативності ліва і права. Ліва асоціативність це коли оператори застосовуються по черзі зліва на право, а права навпаки.

    (2 + 1) - 5 -- ліва
    2 + (1 - 5) -- права
    

    Оголошується асоціативність оператора за допомоги ключових слів:

    • infixl - ліва
    • infixr - права
    • infix - відсутня

    Якщо асоціативність відсутня, то такий оператор не можна викликати кілька раз або з іншими операторами того ж пріоритету в одному виразі.

    Вказується асоціація і пріоритет у такому синтаксисі infix[rl] <prio> <operator>. Вказується це, або до, або після оголошення самого оператора, але в інтерпретаторі це мусе бути одним рядком, тому їх потрібно розділити крапкою з комою.

    infixl 7 +**
    a +** b = a^2 + b^2
    

    Якщо цього не вказати, то оператор матиме ліву асоціативність і девʼятий, найвищий, пріоритет.

    Дізнатись цю інформацію про оператор можна за допомоги команди інтерпретатора info.

    ghci> infixl 7 +**; (+**) a b = a^2 + b^2
    ghci> 5 +** 4
    41
    ghci> :i (+**)
    (+**) :: Num a => a -> a -> a 	-- Defined at <interactive>:1:15
    infixl 7 +**
    

    Якщо явно не вказати infix, то й у виводі цієї команди не буде такої інформації.

    У Haskell немає вбудованих операторів. Всі стандартні оператори оголошені в стандартній бібліотеці. Є такі стандартні оператори.

    infixr 8   ^, ``
    infixl 7   *, /, `div`, `mod`
    infixl 6   +, -
    infix  4   ==, /=, <, <=, >=, >
    

    Це не всі, але інші ми розглянемо пізніше. Оператор `` це оператор виклику функції в інфіксному форматі. Виклик функції у префіксному вигляді має праву асоціативність і девʼятий пріоритет.

    /= це оператор не рівності, в інших мовах зазвичай він виглядає !=. Оператори порівняння не мають асоціативності, тому їх не можна обʼєднувати в ланцюжок.

    #програмування #haskell #hs #оператори #створення #оголошення #асоціативність #пріоритети #стандартні #стандартна #бібліотека #інтерпретатор #ghci #infix #infixl #infixr #виклик #функції #функцій #префіксна #інфіксна #форми

  4. CW: Друга програма на Haskell

    Зазвичай друга програма кожного програміста який починає вивчати мову програмування це hello {name}.

    Спочатку треба трохи розʼяснити про ghc, ghci і функцію main.

    • ghc - це компілятор мови програмування Haskell.

    • ghci - це інтерпретатор мови програмування.

    • функція main - це головна функція яка автоматично викликається при запуску бінарного файлу зібраного за допомогою ghc. Вона не обовʼязкова для запуску в режимі інтерпретації.

    • У функціональних мовах, до яких належить Haskell, немає змінних. Є тільки функції та константи. Константа це функція яка повертає завжди одне значення не залежачи від жодних обставин.

    • Всі файли з джерельним кодом називаються модулями. Є спеціальне оголошення модулів, але про це пізніше.

    • Також є різниця між написанням коду в файлі й виконанням в інтерактивному режимі інтерпретатора. В інтерпретаторі ми можемо виконати будь-яку інструкцію, наприклад putStrLn "Hi!", а в модулі ні. У модулі можна тільки створювати функції.

    • Однорядкові коментарі починаються з двох мінусів -- Comment.

    Тепер перейдемо до нашої програми. У єдиній попередній нашій функції в нас була одна команда. Виклик функції putStrLn з передаванням аргументу. Тепер нам потрібно вписати кілька команд, і щоб це зробити потрібно використати ключове слово do. Після нього можна вписати кілька команд розділені ;, або новим рядком. Але кожний новий рядок повинен починатися з певного відступу. Відступ може бути або пробілом, або табуляцією. Кількість символів може бути різною, але кожний наступний рядок повинен мати, або ту ж кількість пробілів, або більше. Якщо буде менше, то це вважатиметься новим оголошенням. Також один символ табуляції буде розглядатись як вісім пробілів, не залежно від налаштувань редактора.

    main = do
      putStr "Введіть ваше ім'я: " -- Вивід тексту в stdout
      name <- getLine -- зчитування з клавіатури одного рядка з stdin
      putStrLn ("Привіт, " ++ name ++ "!") -- Вивід привітання в stdout
    

    Оператор ++ обʼєднує рядки в один. У інших мовах для цього використовується оператор, який складається з одного символу +.

    Все було б добре, якби не одна проблема. Коли ми запустимо цю програму, то отримаємо не зовсім очікуваний результат.

    Мертвий Демон
    Введіть ваше ім'я: Привіт, Мертвий Демон!
    

    Ця програма спочатку буде очікувати на ввід, а потім виведе на екран весь текст. Це відбувається через буферизацію. Вивід відбувається при вписуванні символу нового рядка. Але ми можемо змусити його вивести тоді коли нам це потрібно. Ця функція називається flush. У Haskell вона знаходиться у модулі System.IO, який нам потрібно імпортувати.

    import System.IO
    
    main = do
      putStr "Введіть ваше ім'я: "
      hFlush stdout
      name <- getLine
      putStrLn ("Привіт, " ++ name ++ "!")
    

    Ця програма буде працювати вірно.

    #haskell #hello-name #programing #програмування #друга #програма #stdout #stdin #функції #вивід #ввід #екран #клавіатура #зчитування #flush

  5. CW: Друга програма на Haskell

    Зазвичай друга програма кожного програміста який починає вивчати мову програмування це hello {name}.

    Спочатку треба трохи розʼяснити про ghc, ghci і функцію main.

    • ghc - це компілятор мови програмування Haskell.

    • ghci - це інтерпретатор мови програмування.

    • функція main - це головна функція яка автоматично викликається при запуску бінарного файлу зібраного за допомогою ghc. Вона не обовʼязкова для запуску в режимі інтерпретації.

    • У функціональних мовах, до яких належить Haskell, немає змінних. Є тільки функції та константи. Константа це функція яка повертає завжди одне значення не залежачи від жодних обставин.

    • Всі файли з джерельним кодом називаються модулями. Є спеціальне оголошення модулів, але про це пізніше.

    • Також є різниця між написанням коду в файлі й виконанням в інтерактивному режимі інтерпретатора. В інтерпретаторі ми можемо виконати будь-яку інструкцію, наприклад putStrLn "Hi!", а в модулі ні. У модулі можна тільки створювати функції.

    • Однорядкові коментарі починаються з двох мінусів -- Comment.

    Тепер перейдемо до нашої програми. У єдиній попередній нашій функції в нас була одна команда. Виклик функції putStrLn з передаванням аргументу. Тепер нам потрібно вписати кілька команд, і щоб це зробити потрібно використати ключове слово do. Після нього можна вписати кілька команд розділені ;, або новим рядком. Але кожний новий рядок повинен починатися з певного відступу. Відступ може бути або пробілом, або табуляцією. Кількість символів може бути різною, але кожний наступний рядок повинен мати, або ту ж кількість пробілів, або більше. Якщо буде менше, то це вважатиметься новим оголошенням. Також один символ табуляції буде розглядатись як вісім пробілів, не залежно від налаштувань редактора.

    main = do
      putStr "Введіть ваше ім'я: " -- Вивід тексту в stdout
      name <- getLine -- зчитування з клавіатури одного рядка з stdin
      putStrLn ("Привіт, " ++ name ++ "!") -- Вивід привітання в stdout
    

    Оператор ++ обʼєднує рядки в один. У інших мовах для цього використовується оператор, який складається з одного символу +.

    Все було б добре, якби не одна проблема. Коли ми запустимо цю програму, то отримаємо не зовсім очікуваний результат.

    Мертвий Демон
    Введіть ваше ім'я: Привіт, Мертвий Демон!
    

    Ця програма спочатку буде очікувати на ввід, а потім виведе на екран весь текст. Це відбувається через буферизацію. Вивід відбувається при вписуванні символу нового рядка. Але ми можемо змусити його вивести тоді коли нам це потрібно. Ця функція називається flush. У Haskell вона знаходиться у модулі System.IO, який нам потрібно імпортувати.

    import System.IO
    
    main = do
      putStr "Введіть ваше ім'я: "
      hFlush stdout
      name <- getLine
      putStrLn ("Привіт, " ++ name ++ "!")
    

    Ця програма буде працювати вірно.

    #haskell #hello-name #programing #програмування #друга #програма #stdout #stdin #функції #вивід #ввід #екран #клавіатура #зчитування #flush

  6. CW: Друга програма на Haskell

    Зазвичай друга програма кожного програміста який починає вивчати мову програмування це hello {name}.

    Спочатку треба трохи розʼяснити про ghc, ghci і функцію main.

    • ghc - це компілятор мови програмування Haskell.

    • ghci - це інтерпретатор мови програмування.

    • функція main - це головна функція яка автоматично викликається при запуску бінарного файлу зібраного за допомогою ghc. Вона не обовʼязкова для запуску в режимі інтерпретації.

    • У функціональних мовах, до яких належить Haskell, немає змінних. Є тільки функції та константи. Константа це функція яка повертає завжди одне значення не залежачи від жодних обставин.

    • Всі файли з джерельним кодом називаються модулями. Є спеціальне оголошення модулів, але про це пізніше.

    • Також є різниця між написанням коду в файлі й виконанням в інтерактивному режимі інтерпретатора. В інтерпретаторі ми можемо виконати будь-яку інструкцію, наприклад putStrLn "Hi!", а в модулі ні. У модулі можна тільки створювати функції.

    • Однорядкові коментарі починаються з двох мінусів -- Comment.

    Тепер перейдемо до нашої програми. У єдиній попередній нашій функції в нас була одна команда. Виклик функції putStrLn з передаванням аргументу. Тепер нам потрібно вписати кілька команд, і щоб це зробити потрібно використати ключове слово do. Після нього можна вписати кілька команд розділені ;, або новим рядком. Але кожний новий рядок повинен починатися з певного відступу. Відступ може бути або пробілом, або табуляцією. Кількість символів може бути різною, але кожний наступний рядок повинен мати, або ту ж кількість пробілів, або більше. Якщо буде менше, то це вважатиметься новим оголошенням. Також один символ табуляції буде розглядатись як вісім пробілів, не залежно від налаштувань редактора.

    main = do
      putStr "Введіть ваше ім'я: " -- Вивід тексту в stdout
      name <- getLine -- зчитування з клавіатури одного рядка з stdin
      putStrLn ("Привіт, " ++ name ++ "!") -- Вивід привітання в stdout
    

    Оператор ++ обʼєднує рядки в один. У інших мовах для цього використовується оператор, який складається з одного символу +.

    Все було б добре, якби не одна проблема. Коли ми запустимо цю програму, то отримаємо не зовсім очікуваний результат.

    Мертвий Демон
    Введіть ваше ім'я: Привіт, Мертвий Демон!
    

    Ця програма спочатку буде очікувати на ввід, а потім виведе на екран весь текст. Це відбувається через буферизацію. Вивід відбувається при вписуванні символу нового рядка. Але ми можемо змусити його вивести тоді коли нам це потрібно. Ця функція називається flush. У Haskell вона знаходиться у модулі System.IO, який нам потрібно імпортувати.

    import System.IO
    
    main = do
      putStr "Введіть ваше ім'я: "
      hFlush stdout
      name <- getLine
      putStrLn ("Привіт, " ++ name ++ "!")
    

    Ця програма буде працювати вірно.

    #haskell #hello-name #programing #програмування #друга #програма #stdout #stdin #функції #вивід #ввід #екран #клавіатура #зчитування #flush