Рядок (програмування): відмінності між версіями

[неперевірена версія][неперевірена версія]
Вилучено вміст Додано вміст
Немає опису редагування
Немає опису редагування
Рядок 11:
 
=== Подання масивом символів ===
У цьому підході рядки представляються [[Масив|масивом]] символів; при цьому розмір масиву зберігається в окремій (службової) області. Від назви мови Pascal, де цей метод був вперше реалізований, даний метод отримав назву [[Pascal]] strings.
 
Злегка оптимізованим варіантом цього методу є т.так Н.званий формат c-addr -u (від англ. character-aligned address + unsigned number), застосовуваний в Форте. На відміну від Pascal strings, тут розмір масиву зберігається не спільно із строковими даними, а є частиною покажчика на рядок.
 
==== Переваги ====
Рядок 31:
Другий метод полягає в використанні «завершального байту»<ref>http://queue.acm.org/detail.cfm?id=2010365</ref><ref>http://russian.joelonsoftware.com/Articles/BacktoBasics.html</ref>. Одне з можливих значень символів алфавіту (як правило, це символ з кодом 0) вибирається як ознака кінця рядка, і рядок зберігається як послідовність байтів від початку до кінця. Є системи, в яких в якості ознаки кінця рядка використовується не символ 0, а байт 0xFF (255) або код символу «$».
 
Метод має три назви - ASCIIZ (або asciz, символи в кодуванні [[ASCII]] з нульовим завершальним байтом), C-strings (найбільшого поширення метод отримав саме в мові [[C (мова програмування)|Сі]]).
 
==== Переваги ====
Рядок 37:
* можливість подання рядки без створення окремого типу даних;
* відсутність обмеження на максимальний розмір рядка;
* економне використання [[Пам'ять|пам'яті]];
* простота отримання суфікса рядки;
* простота передачі рядків у функції (передається покажчик на перший символ);
Рядок 51:
 
=== Подання у вигляді списку ===
Мови [[Erlang]]<ref>Simon St. Laurent. Introducing Erlang. — O’Reilly Media, Inc., 2013. — P. 62. — 185 p. — ISBN 978-1-449-33176-4.</ref>, [[Haskell]]<ref>http://book.realworldhaskell.org/read/characters-strings-and-escaping-rules.html</ref>, [[Пролог (мова програмування)|Пролог]]<ref>http://www.swi-prolog.org/pldoc/man?section=text-representation</ref> використовують для строкового типу список символів. Цей метод робить мову більш «теоретично елегантним» за рахунок дотримання ортогональности в системі типів, але приносить суттєві втрати швидкодії.
 
== Реалізація в мовах програмування ==
Рядок 58:
* У Сі використовуються нуль-терминировать рядки з повним ручним контролем з боку програміста.
 
* У стандартному Паскалі рядок виглядає як масив з 256 байтів; перший байт зберігав довжину рядка, в інших зберігається її тіло. Таким чином, довжина рядка не може перевищувати 255 символів. У Borland Pascal 7.0 також з'явилися рядки «а-ляпо типу [[C++|Сі]]<nowiki/>» - очевидно, через те, що в число підтримуваних платформ увійшла [[Microsoft Windows|Windows]].
 
* У [[Object Pascal]] іта [[C ++]] STL рядок є «чорним ящиком», в якому виділення / вивільнення пам'яті відбувається автоматично - без участі програміста. При створенні рядка пам'ять виділяється автоматично; як тільки на рядок не залишиться жодного посилання, пам'ять повертається системі. Перевага цього методу в тому, що програміст не замислюється над роботою рядків. З іншого боку, програміст має недостатній контроль над роботою програми в критичних до швидкості ділянках; також важко реалізується передача таких рядків як параметр в DLL. Також [[Object Pascal]] автоматично стежить, щоб в кінці рядка був символ з кодом 0. Тому якщо функція вимагає на вході нуль-терминировать рядок, для конвертації треба просто написати PAnsiChar (строковая_переменнаярядкова_змінна) або PWideChar (строковая_переменная) (для Pascal), переменная.змінна c_str ( ) (для Builder / STL).
 
* У C # та іншими мовами із збіркою сміття рядок є незмінним об'єктом; якщо рядок потрібно модифікувати, створюється інший об'єкт. Цей метод повільний і витрачає чимало тимчасової пам'яті, але добре поєднується з концепцією збірки сміття. Перевага цього методу в тому, що присвоювання відбувається швидко і без дублювання рядків. Також є деякий ручний контроль над конструюванням рядків (в [[Java]], наприклад, через класи StringBuffer і StringBuilder) - це дозволяє зменшити кількість виділень і вивільнень пам'яті і, відповідно, збільшити швидкість.
 
* У деяких мовах (наприклад, Standard ML) крім цього, є додатковий модуль для забезпечення ще більшої ефективності - «подстрокапідрядок» (SubString). Його використання дозволяє виконувати операції над рядками без копіювання їхніх тіл за допомогою маніпулювання індексами початку і кінця підстроками; фізичне копіювання відбувається лише при необхідності перетворення подстрок в рядки.
 
== Операції ==
Рядок 83:
* Відображення одного списку на інший;
 
* [[Фільтрація]] списку за [[Критерій|критерієм]].
 
=== Більш складні операції ===
* Знаходження мінімальноїмінімального надстрокінадрядку, що містить всі зазначені рядки;
* Пошук в двох масивах рядків збігаються послідовностей (завдання про [[плагіат]]).
 
=== Можливі завдання для рядків на природній мові ===
* Порівняння на близькість зазначених рядків по заданому [[Критерій|критерію]];
 
* Визначення мови і [[кодування]] тексту на підставі ймовірностей символів і складів.
 
== Подання символів рядка ==
До останнього часу один символ завжди кодувався одним байтом (8 двійкових бітів; застосовувалися також кодування з 7 битамибітами на символ), що дозволяло представляти 256 (128 при семібітнойсемібітному кодуванні) можливих значень. Однак для повноцінного представлення символів алфавітів кількох мов (багатомовних документів, друкарських символів - кілька видів лапок, тире, кількох видів прогалин і для написання текстів на ієрогліфічних мовах - китайською, японською та корейською) 256 символів недостатньо. Для вирішення цієї проблеми існує кілька методів:
* Перемикання мови керуючими кодами. Метод не стандартизований і позбавляє текст самостійності (тобто послідовність символів без керуючого коду на початку втрачає сенс); використовувався в деяких ранніх русифікації [[ZX Spectrum|ZX-Spectrum]] і БК.
 
* Використання двох або більше байт для представлення кожного символу ([[UTF-16]], UTF-32). Головним недоліком цього методу є втрата сумісності з попередніми бібліотеками для роботи з текстом при поданні рядка як ASCIIZ. Наприклад, кінцем рядка повинен вважатися вже не байт із значенням 0, а два або чотири поспіль нульових байта, в той час як одиночний байт «0» може зустрічатися в середині рядка, що збиває бібліотеку «з пантелику».
 
* Використання кодування зі змінним розміром символу. Наприклад, в [[UTF-8]] частина символів представляється одним байтом, частина двома, трьома або чотирма. Цей метод дозволяє зберегти часткову сумісність зі старими бібліотеками (немає символів 0 всередині рядка і тому 0 можна використовувати як ознака кінця рядка), але призводить до неможливості прямої адресації символу в пам'яті за номером його позиції в рядку.
 
== Див. також ==