Я хочу на низькому рівні зрозуміти, що буде, якщо структура даних не буде стійкою?
Давайте розглянемо генератор псевдовипадкових чисел з величезним простором стану (на кшталт " Мерсенн твістер " зі станом 2450 байт) як структуру даних. Ми насправді не хочемо використовувати будь-яке випадкове число більше одного разу, тому, мабуть, є мало причин реалізувати це як незмінну стійку структуру даних. Тепер давайте запитаємо, що може піти не так у наступному коді:
mt_gen = CreateMersenneTwisterPRNGen(seed)
integral = MonteCarloIntegral_Bulk(mt_gen) + MonteCarloIntegral_Boundary(mt_gen)
Більшість мов програмування не вказують порядок, в якому MonteCarloIntegral_Bulk
і MonteCarloIntegral_Boundary
буде оцінюватися. Якщо обидва беруть посилання на змінний mt_gen як аргумент, результат цього обчислення може залежати від платформи. Що ще гірше, можуть бути платформи, де результат взагалі не відтворюється між різними пробіжками.
Можна створити ефективну структуру даних, що змінюється, для mt_gen таким чином, що будь-яке переплетення виконання MonteCarloIntegral_Bulk
і MonteCarloIntegral_Boundary
дасть "правильний" результат, але інше переплетення взагалі призведе до іншого "правильного" результату. Ця невідтворюваність робить відповідну функцію "нечистою", а також призводить до деяких інших проблем.
Невідтворюваності можна уникнути, застосувавши фіксований порядок послідовного виконання. Але в цьому випадку код може бути впорядкований таким чином, що в будь-який момент часу доступна лише одна посилання на mt_gen. У введеній функціональній мові програмування для забезпечення цього обмеження можна використовувати типи унікальності, тим самим забезпечуючи безпечні оновлення, що змінюються, також у контексті чистої функціональної мови програмування. Все це може звучати приємно і безглуздо, але, принаймні, теоретично моделювання Монте-Карло незручно паралельне, і наше "рішення" просто знищило цю власність. Це не просто теоретична проблема, а цілком реальна практична проблема. Однак ми маємо змінити (функціонал, який пропонує) наш генератор псевдовипадкових чисел та послідовність випадкових чисел, які він виробляє, і жодна мова програмування не може зробити це автоматично для нас. (Звичайно, ми можемо використовувати іншу бібліотеку псевдовипадкових чисел, яка вже пропонує необхідну функціональність.)
На низькому рівні структури даних, що змінюються, легко призводять до невідтворюваності (а отже, і домішок), якщо порядок виконання не є послідовним та фіксованим. Типовою імперативною стратегією вирішення цих проблем є наявність послідовних фаз із фіксованим порядком виконання, під час яких змінюються змінні структури даних, і паралельні фази з довільним порядком виконання, під час яких всі спільні структури даних, що змінюються, залишаються постійними.
Андрій Бауер порушив питання про підрахунок змінних змінних структур. Цікаво, що різні імперативні мови, такі як Fortran і C, мають різні припущення щодо дозволеного псевдонімування аргументів функції, і більшість програмістів зовсім не знають, що в їхній мові взагалі є модель псевдоніму.
Семантика незмінності та значення може бути дещо завищеною. Що ще важливіше, це те, що система типу та логічний каркас (як, наприклад, абстрактна модель машини, модель псевдоніму, паралельна модель чи модель управління пам'яттю) вашої мови програмування надають достатню підтримку для роботи "безпечно" з "ефективними" даними споруди. Введення "переміщення семантики" в C ++ 11 може виглядати як гігантський крок назад з точки зору чистоти та "безпеки" з теоретичної точки зору, але на практиці це навпаки. Система типів та логічна основа мови були розширені, щоб усунути величезні частини небезпеки, пов'язані з новою семантикою. (І навіть якщо залишаються шорсткі краї, це не означає, що це не вдалося поліпшити "кращим"
Удей Редді порушив питання про те, що математика ніколи не працювала з об'єктами даних, що змінюються, і що типові системи для функціональних програм добре розроблені для незмінних об'єктів даних. Це нагадало мені пояснення Жана-Іва Жирара, що математика не використовується для роботи зі змінними об'єктами, коли він намагається мотивувати лінійну логіку.
Можна запитати, як розширити тип системи та логічні рамки функціональних мов програмування, щоб дозволити «безпечно працювати» з «ефективними» змінними непостійними структурами даних. Одна з проблем тут може полягати в тому, що класична логіка та булеві алгебри можуть бути не найкращою логічною основою для роботи зі змінними структурами даних. Можливо, лінійна логіка та комутативні моноїди можуть бути краще підходять для цього завдання? Можливо, я повинен прочитати, що Філіп Вадлер повинен сказати про лінійну логіку як систему типів для функціональних мов програмування? Але навіть якщо лінійна логіка не зможе вирішити цю проблему, це не означає, що типову систему та логічні рамки функціональної мови програмування не можна було б розширити, щоб забезпечити "безпечний" та "ефективний"