Історія, розвиток і сьогоднішні реалії С++

Створений там же, де і попередник, мова C, - в Дослідницькому центрі комп'ютерних наук Bell Labs, С++ повною мірою повторив і примножив успіх С. Прічем відразу слід відмітити, що успіхи і C, і C++, грунтувалися виключно на властивостях цих мов як інструментів. Адже по суті ніяким комерційним розкручуванням мов програмування компанія AT&T, до складу якої входила Bell Labs, не займалася. C розповсюджувався як би в навантаження до ОС UNIX, C++ взагалі фактично не мав товарного характеру. Більш того, AT&T своєчасно підтримала політику стандартизації відкритих специфікацій цих мов. Завдяки цій моделі розповсюдження розробок в області мов програмування, прийнятою AT&T, сьогодні доступні не тільки висококласні комерційні компілятори З і С++, але і прекрасний GCC, що став головним інструментом в світі Open Source. Втім, достоїнства моделі розповсюдження ПО - це річ вельми абстрактна.
А у мови C++ все-таки є цілком конкретний автор, якого чудова у всьому модель вільного розповсюдження відкритих стандартних специфікацій в якійсь мірі обділила. Американець данського походження, що здобув освіту в Данії і Англії, Бьярн Страуструп ніяких відрахувань за специфікації C++ не отримує. Благо специфіка будь-якої мови програмування - складність (навіть найпростіша мова насправді дуже складна, що відмінно демонструється хоррор-програмою Тома Даффа). Ну а там, де люди вимушено стикаються з складністю, завжди є потреба в єдиному універсальному засобі боротьби з нею - в документації. Видані в безлічі країн світу сумарним легальним тиражем понад мільйон екземплярів складні книги Бьярна Страуструпа про складну мову C++ - краще тому підтвердження. У технологічному аспекті створення C++, в принципі, досить звичайна історія. Бьярн Страуструп для створення першого компілятора використовував поширений прийом, відомий під назвою "Методу розкручування".
На мові C Страуструп написав препроцесор, що перетворює підмножину нової мови в звичайну мову C. На підмножині C++ і був розроблений перший транслятор з C++ і потім розкручений в C-код, придатний до компіляції у виконувану програму. Цільовою машиною для першого C++ транслятора була будь-яка машина, здатна виконувати будь-який C-компілятор, тому що результатом трансляції був C-код. Найцікавішим в C++, мабуть, є задум Страуструпа створити одночасно високорівневу мову, несумірно більш високорівневу в порівнянні з C, і в той же час як максимально наближений по низькорівневих можливостях до C, так і в розумному ступені сумісний з C. Можливо, саме завдяки такій затії сучасний C++ - зовсім не "C з класами" і навіть не "об'єктно-орієнтована мова". C++ - це так звана "поліпарадігменний мова".
Сам Бьярн Страуструп слово "парадигма" відносно свого дітища вживати не любить і вважає за краще говорити про різні стилі програмування, допустимих при використанні С++. Структурне програмування, програмування із застосуванням абстрактних типів даних, узагальнене і функціональне програмування - в принципі, в умілих руках C++ дозволяє використовувати як кожний із стилів (або парадигм), так і комбінувати їх в одному програмному проекті. Природно, така гнучкість дається чималою ціною. Особливо якщо враховувати, що основні витрати на мову програмування - це зовсім не вартість придбання ліцензійного компілятора, а час на вивчення власне мови. А ось скільки часу потрібно на те, щоб віртуозно опанувати С++, сказати дуже важко.
Якщо несумірно більш простій C свого часу уразив Тома Даффа, C-програміста з десятирічним стажем, великою кількістю "нерозвіданих куточків", то що тоді можна говорити про С++, окремій техніці якого присвячені такі непрості книги, як 550-сторінкове керівництво за шаблонами "C++ Templates: The Complete Guide"? І тим часом, навіть при цьому рівні складності на ювілейній конференції, присвяченій 20-летию С++, Бьярн Страуструп відзначив, що С++ вже почав втрачати, як би це краще сказати, "крутизну": "C++ став могутнім, відпрацьованим інструментом, але використовувати його вже не круто (no cool)". Можливо, позбавлення С++ ореолів "крутизни" і "ковбойства" піде тільки на користь. І на користь не стільки мові, скільки використовуючим його програмістам і організаціям.
Принаймні, період, коли С++ вибирався мовою реалізації виключно тому, що це було "круто", безповоротно пройшов. Адже такий період в історії мови був, і саме завдяки ньому так переконливо звучали голоси тих, що передрікають швидкий відхід C++ з арени популярних інструментальних засобів. Сьогоднішній С++ багатьом здається мовою, пік розвитку якого вже у минулому. І, за великим рахунком, ця думка вірна. 20 років - термін, достатній для досягнення зрілості навіть такою складною розробкою. І все-таки говорити про те, що розвиток мови після стандартизації ISO в 1998 р. повністю припинився, не можна. В майбутньому більш ніж трьохмільйонна армія С++-программистов отримає оновлений інструмент, що відповідає стандарту C++0x, що формується. Говорити про точну дату появи нового стандарту і, тим більше, про час виходу компіляторів, розуміючих C++0x C++, поки дуже важко.
Річ у тому, що C++ використовується в найрізноманітніших областях застосування, і, відповідно, від різноманітності бажаних поліпшень просто рябить в очах. Проте розробники стандартних специфікацій строго слідують найважливішому правилу, закладеному в ідеологію C++ його творцем Бьярном Страуструпом: C++ - це універсальна мова, придатна до використання в багатьох прикладних областях завдяки вдалому компактному набору загальнийвживаних засобів. Якщо пригадати долю мов, в які включалися спеціалізовані засоби (наприклад, мовна підтримка потокового програмування), можна упевнено говорити про безпомилковість вибору Страуструпа. Друга складність у формуванні С++0x криється в специфіці типізації, прийнятої в нинішньому С++. З одного боку, вимога до підвищення надійності програм, що розробляються, вимушує творців специфікацій мови як можна строго відноситися до системи типів і до контролю за ними.
У ідеалі, звичайно, мова із строгою типізацією була б просто чудовою. Але це в ідеалі. У реальному житті програмістам необхідні одночасно і можливість створення абстрактних типів, і можливість, наприклад, доступу до елементів пам'яті або регістрів, розташованих в адресному просторі за відомими адресами. У реальному житті програмісти прагнуть використовувати як можна велику частину раніше написаного коду повторно, і строга типізація в С++0x призвела б до того, що всі початкові тексти, де використовуються масиви, покажчики, об'єднання, явні і неявні приведення типів, довелося б відправити до сміттєвої корзини. І нарешті, до недосконалості реального життя слід віднести і жорсткі вимоги до високої продуктивності отриманого за допомогою компіляції коду. Неважливо, що зараз епоха "дешевих гігагерців" - далеко не у всіх областях застосування ці гигагерци потрібні, далеко не скрізь комп'ютерам дозволена робота "обігрівачем за сумісництвом".
Іншими словами, вимога до мінімальності середовища часу виконання C++0x залишаються в силі. С++0x зберігає мінімальною дистанцію між програмістом і "залізом", відображаючи один в один цільову машину мовними засобами. Машинні слова, байти, регістри - все це в C++0x залишається. Разом з принципами, по яких формується C++0x, вже відомо і про деякі конкретні нововведення. Так, в стандартній бібліотеці з'явиться підтримка кортежів - tuples. Кортежі - це колекції певної кількості (до десяти) об'єктів різних типів. Зазвичай вони підтримуються в мовах, що інтерпретуються, і дозволяють ефективно повертати безліч значень з функцій, проводити множинні порівняння або привласнення і інші групові операції над гетерогенними наборами даних.
Перелік базових операцій з кортежами включає механізми їх створення, визначення числа елементів і типу кожного елементу, а також доступу як до кортежу в цілому, так і до кожного його елементу. Реалізацію кортежів в C++0x можна вважати дуже вдалою, оскільки вона фактично не зажадала модифікацій ядра мови. До корисних модифікацій також слід віднести "облатку" над посиланнями С++. У поточних специфікаціях мови об'єкти типу "посилання" не є рівноправними з іншими об'єктами базових типів. Так, наприклад, посилання не можна використовувати як параметри в шаблонних конструкціях. В деяких випадках таке нерівноправ'я посилань, наприклад з покажчиками, вимушувало програмістів займатися різними хитруваннями.
У С++0x від несправедливості вирішили позбавлятися малою кров'ю і ввели спеціальні класс-облатку (reference_wrapper), що дозволяє приховати в об'єкті класу посилання так, щоб одночасно зберегти її властивості і усунути обмеження. Реалізація "облатки" така, що з посилань на об'єкти різних типів в С++0x можна, наприклад, формувати кортежі. Ще одне нововведення С++0x - повернення в мову старого ключового слова auto, але в абсолютно новій якості. Ідея нового auto дуже проста і полягає відповідає на питання: який ступінь надмірності наступного виразу: const double Salary = 2563.92. Якщо небагато подумати, то майже вся ліва частина, що стосується оголошення змінної, надмірна. Тому як інформація про тип абсолютно явно указується в правій частині, в значенні, використовуваному для ініціалізації змінної.
Відповідно, в С++0x можна буде полінуватися і довірити компілятору дописати очевидне, замінивши його словом auto:const auto Salary = 2563.92. У прикладах, де в правій частині ініціалізацій використовувалися дані в явній формі, цінність auto невелика. Але якщо замість явних даних використовувати виклики функцій, оголошення змінної з auto-визначенням типу може допомогти уникнути тонких помилок, особливо у випадках, коли можуть спрацювати механізми приведення типів за умовчанням, а вони-то якраз і небажані.Загалом, повертаючись до оцінок перспектив розвитку мови, можна упевнено говорити, що революції з появою C++0x не відбудеться. Щось буде зручніший, щось - краще, все зроблене раніше залишиться працездатним. І це не може не радувати.