Яка різниця між синтаксисом і семантикою?


87

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



6
"Безбарвні зелені ідеї люто сплять" синтаксично добре, але не має сенсу. Дивіться en.wikipedia.org/wiki/Colorless_green_ideas_sleep_furiously
CesarGon

+1, щоб задати це питання. Я дивувався такому ж, було лінь шукати це в Інтернеті і, очевидно, ніколи не питав.
КК.

Більше чи менш, я б сказав ... Семантика - це типи примірників, їх зв'язки з іншими екземплярами та гарантії, які існують між ними. Синтаксис - це спосіб оголосити ці речі за допомогою рядків символів. Більш-менш.
Дехбоп

Відповіді:


106

Семантика ~ Значення

Синтаксис ~ Символічне подання

Тож дві програми, написані різними мовами, могли б робити те саме (семантика), але символи, які використовуються для написання програми, були б різними (синтаксис).

Компілятор перевірить ваш синтаксис (помилки часу компіляції) та виведе семантику з мовних правил (відображення синтаксису в машинних інструкціях), але не знайде всіх семантичних помилок (помилки під час виконання, наприклад обчислення неправильний результат, оскільки в коді написано додати 1, а не 2).


2
Перевірка помилок не є критерієм для розмежування синтаксису та семантики. Компілятор може і повинен діагностувати як синтаксичні помилки (як, наприклад, відсутня крапка з комою), так і семантичні помилки (наприклад, x + yякщо +для цих операндів немає відповідного оператора). Додавання 1, а не 2 - це те, що я б назвав логічною помилкою.
Кіт Томпсон

3
@Keith - але логіка (як у "логічній помилці") - це семантика. Деякі семантичні перевірки можуть зробити компілятор - особливо перевірка типу - тому я погоджуюся, що компілятори не знаходять лише синтаксичні помилки, але Кріс сказав лише, що " не знайде всіх семантичних помилок", що не означає "не може знайти будь-який ".
Steve314

1
@ Steve314: Погоджено. Але якщо ви хочете зробити різке розмежування між помилками, які повинен виявити компілятор, та помилками, які йому не потрібно виявляти, то я думаю, що "семантичний" проти "логічний" - це хороший спосіб висловити цю відмінність.
Кіт Томпсон

4
@KeithThompson Насправді, теоретично, компілятор або інтерпретатор для мови з достатньо сильною та потужною (тобто залежною ) системою типу може перевірити будь-яке довільне властивість вашого коду (за модулем Проблема зупинки, якщо це застосовується), тому розбиваючи семантичні помилки на "перевіряється" та "не перевіряється" взагалі не має сенсу.
Полум’я Птарієна

@ Ptharien's Flame Я просто збираюся на секунду витягнути цю дискусію з хмар, виділивши частину вашої заяви «теоретично». На практиці застосування семантики в коді вимагає додаткового синтаксису, щоб дати компіляторам підказки щодо функціональності. Додаткова семантична перевірка походить як вартість (тобто складність / читабельність). Заявляти, що мова може бути достатньо потужною для перевірки всіх смислових помилок - це як би сказати, що правова система може бути достатньо досконалою для запобігання будь-яких злочинів. Особисто я віддаю перевагу свободі над безпекою, але саме це робить це "релігійною" темою.
Еван Плейс

35

Насправді існує не два рівні, а три:

  • лексичний рівень: як символи об'єднуються для отримання мовних елементів ( iі fвиробляє if)
  • синтаксичний рівень: як елементи мови об'єднуються для отримання мовних виразів ( if, (, 42, ==, answerі )виробляють умовний оператор)
  • семантичний рівень: як мовні вирази перетворюються на інструкції CPU, щоб сформувати значення (умовне твердження дозволяє виконувати одну або іншу гілку залежно від результату булевого виразу)

10
Розмежування між стадіями лексингу та розбору цілком штучне, це не що інше, як оптимізація. І є деякі мови, де не визначений кінцевий плоский набір лексем - але все ж є чітко визначений синтаксис. Отже, я вважаю за краще визначити лексеми частиною синтаксису, це не окрема сутність.
SK-логіка

@ SK-логіка: У багатьох мовах вказується список дозволених або заборонених лексем, що утворюють назву змінної. Тож розділення має сенс.
mouviciel

5
@mouviciel, це має сенс як оптимізація - інакше у вас просто буде ValidIdentifierтермінал, який можна визначити як щось на зразок ![AnyKeyword] [Identifier](тут я використовую PEG-подібні позначення). Вам не потрібен окремий лексичний пропуск для такої мови. Дивіться, наприклад, партери C ++ на базі GLR.
SK-логіка

2
@EvanPlaice, про що ти говориш? Моя думка полягає в тому, що лексика не потрібна (і фактично обмежує вашу мову), а не розбір .
SK-логіка

1
@ SK-логіка, я думаю, я читаю ваш коментар, щоб означати протилежне тому, що ви задумали. Я подумав, що ви говорите про випадки, коли потрібен лише лексер - як, наприклад, в чисто "регулярних" або "без контекстних" мовах. У мовах вищого рівня лексеру може не знадобитися, але він забезпечує швидкий спосіб запустити перевірку синтаксису одного проходу. Я повністю погоджуюся, що є багато випадків, коли було б вигідно вимкнути або повністю усунути стадію лексеру.
Еван Плейс

18

Я поясню це вам простим прикладом мовою ENGLISH:

The glass drank Ben

Є синтаксично правильним твердженням. У ньому є іменник, дієслово тощо.

Але семантично це неправильно, оскільки це твердження не має жодного мислимого чи правильного значення.


15

Семантика описує логічні сутності мови програмування та їх взаємодії. Синтаксис визначає, як вони виражаються символами.

Наприклад, поняття арифметики вказівника є частиною семантики С; те, як +і -оператори можуть бути використані для вираження операцій вказівника, є частиною його синтаксису.

Іноді дві мови поділяють частину своєї семантики, але синтаксис сильно відрізняється (наприклад, C # і VB.NET - обидва використовують значення значень і типи посилань, але символи, які ви вводите для їх визначення, відрізняються); в інших випадках дві мови синтаксично схожі, але семантика не збігається (розгляньте Java проти JavaScript, де подібності часто плутають початківців).


Отже, "Парадигми" пов'язані з семантикою? Я маю на увазі парадигма - це сукупність взаємопов'язаних семантик?
Гульшань

1
@Gulshan, парадигма - це набагато ширше поняття, ніж така формалізована річ, як семантика. Парадигма може включати семантику, але це скоріше методологія або, навіть ширше, філософія.
SK-логіка


5

Ви не вказали, чи посилаєтесь ви лише на мови програмування або на загальні мови, які використовуються в програмуванні, тому моя відповідь стосується мов даних (таких як XML, RDF, системи типів даних тощо):

Брайан Л. Мек у своїх семи золотих правилах створення стандартів, незалежних від мови (1995) пише, що «синтаксис однієї мови може бути семантикою іншого» . Він посилається на слова "синтаксис" і "семантичний", що використовуються в описі даних: тому якщо ви натрапите на ці слова в специфікації якогось формату даних, вам краще замінити обидва слова на "Potrzebie", щоб зрозуміти, що ви повинні працювати значення для себе.

Співвідношення між синтаксисом і семантикою, принаймні в точно вказаних даних, можна краще описати терміном "кодування" . Семантичний зашифрований у синтаксисі. Оскільки записи можуть бути вкладені, синтаксис однієї мови є семантикою іншого. Якщо виходити за межі сфери даних, це гніздування може бути практично нескінченним, як описано Умберто Еко як "необмежений семіоз".

Щоб навести приклад:

  • Синтаксис XML (матеріал із усіма цими дужками) - це синтаксис із інформаційним набором XML (абстрактним деревом) як семантичним.
  • Інформаційний набір XML як синтаксис може виражати запис у деякому форматі XML як семантичний, наприклад документ RDF / XML, що кодує графік RDF.
  • Графік RDF (матеріал із посиланнями URI) як синтаксис кодує графік абстрактних ресурсів як семантичний.
  • Графік абстрактних ресурсів як синтаксис кодує концептуальну модель як семантичну.

Люди зазвичай зупиняються на якомусь рівні і сприймають це як семантичне, але врешті-решт немає остаточної семантики, якщо якась людина не інтерпретує дані у своєму розумі. Як тільки людина намагається виразити семантичне у формі даних, він стає синтаксисом.


4

Якщо його можна описати в BNF (Backus-Naur Form) або щось подібне, це синтаксис. Якщо не може, це не так.

З іншого боку, семантика - це значення програми (або іншого фрагмента вихідного коду).

І іноді лінія між ними може бути розмитою.

Один із способів зрозуміти відмінність - це переглянути види помилок, які ви отримуєте, коли синтаксис або семантика вашої програми неправильні.

Помилка синтаксису - це невідповідність вихідного коду граматиці мови, наприклад, відсутність крапки з комою, де потрібна.

Семантична помилка - це невиконання інших вимог до мови (те, що C, наприклад, називає "обмеження"); прикладом може бути написання, x + yде xі yє несумісні типи. Граматика мови говорить про те, що додаток виглядає так something + something, але воно недостатньо потужне, щоб висловити вимоги щодо типів лівого та правого операндів.

(Логічні помилки, такі як використання 1, де було б правильно, компілятор, як правило, не виявляють - хоча в деяких випадках компілятор може попереджати про сумнівний код.)


0

Синтаксис - це те, про що говорять (лексичні) символи. Семантика - це те, що вони означають.

Поміркуйте:

C #: condition ? true_value : false_value
VB.NET: If(condition, true_value, false_value)
- Різний синтаксис, однакова семантика.

C #: left_value / right_value
VB.NET: left_value / right_value
- Один і той же синтаксис, різна семантика (для цілих чисел).


0

Синтаксис - це граматичне розташування слів у реченні, тобто порядок слів.

(Англ.) ' Cat dog boy ' та (програмування) ' hi.5 ' не є синтаксично правильним.

(Англійська) ' cat hugs boy ' та (програмування) '* 3.2 * 5 *' є синтаксично дійсним.

Статична семантика - це чи мають синтаксично достовірні твердження якесь значення.

(Англійська) " Я великий " (програмування) (python) " 3 +" привіт " синтаксично правильний, але має статичну семантичну помилку.

Семантика - це значення, пов'язане з синтаксично правильним рядком символів без статичної смислової помилки, тобто речення є синтаксично і семантично правильним, але його значення може бути не таким, як було призначено.

(Англійська) " Літаючі літаки можуть бути небезпечними " можуть мати два значення, тобто політ літаків може бути небезпечним або літаки, що літають, можуть бути небезпечними.

(Програмування) 'комп'ютер не генерує жодних повідомлень про помилки, але він не буде робити те, що ви йому сказали; це зробить щось інше ».

Джерело : MIT 6.00.1


-2
  1. Синтаксис посилається на формальні правила, що регулюють побудову дійсних тверджень мовою. Семантика посилається на сукупність правил, які надають значення висловлюванню.

  2. Помилки через синтаксис трапляються в програмі, коли рулі мови програмування порушуються або не використовуються. Помилки через семантику трапляються в програмі, коли висловлювання не мають сенсу.

  3. Порядок слів є основним принципом синтаксису; ті, хто намагається зрозуміти, що написано, використовують синтаксичні підказки порядку слів, щоб допомогти надати структуру та значення речення. Семантика - це власне тлумачення індивідом значення "речення" на основі їх попередніх знань. Тому речення, яке, здавалося б, не має синтаксичного сенсу, може мати значення при використанні семантичних підказів.

  4. Синтаксис стосується лише того, що є лінгвістично та граматично правильним. Семантика вимагає від усіх попередніх знань, які є, і далеко не все, що стосується мови.

  5. Речення "Дитяче молоко п'є" не має синтаксичного значення, але через семантику більшість людей трактує це як значення "Дитина п'є молоко", оскільки наші попередні знання говорять нам, що дитина п'є молоко, і тому ми можемо знайти значення з ключові слова.


1
Оновлення всього, окрім останнього (точка 5)
nawfal

-2

Синтаксис і семантика схожі на стратегію і тактику або зліва і справа .

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

Отже, якщо ви пишете код мовою, синтаксис - це мова, якою ви користуєтесь, а бажана поведінка - це семантика. Але якщо ви реалізуєте або обговорюєте компілятор для цієї мови, то синтаксис - це граматика і, можливо, тип системи та семантика все, що побудовано на цьому. І так далі.


4
Що це за езотеричний БС? Як лівий і правий? Як стратегія та тактика? Можливо, навіть як Інь і Ян, Бог і Диявол, Гаррі і Волдеморт?
JensG

-3

Синтаксис - це те, що розуміє комп’ютер, семантика - це те, що розуміє людина.

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


"Синтаксис - це те, що розуміє комп'ютер, семантика - це те, що розуміє людина", - це велика спрощеність. Люди теж розуміють синтаксис, і комп'ютери розуміють деякі види семантики.
CesarGon

4
Явно неправильно. Є мови з однаковим синтаксисом і абсолютно різною семантикою (наприклад, жадібна і ледача версії однієї мови), є мови практично без синтаксису і дуже багатою і змінною семантикою (наприклад, Forth і Lisp). Семантика - це те, як компілятор інтерпретує вашу мову. Людина може нічого про це не знати і все-таки зможе користуватися мовою.
SK-логіка

@ SK-логіка, ти суперечить собі. Якщо різну семантику можна виразити одним і тим же синтаксисом, то явно семантика міститься не в синтаксисі, а в тому, як вона використовується. Однак компілятор має лише синтаксис для роботи. Він не інтерпретує семантику, він інтерпретує синтаксис. Він не компілює один і той же синтаксис по-різному, виходячи з того, що хотів сказати розробник, а лише на те, що він ввів. Семантика подається розробником, і має для неї лише сенс.
kylben

3
@kylben, я собі не суперечу, бо ніколи не говорив, що синтаксис і семантика навіть пов'язані між собою. І компілятор нічого не робить із синтаксисом відразу після етапу розбору - компілятор реалізує семантику . Очевидно, що ваше тлумачення термінології неправильне. Прочитайте це для початку: en.wikipedia.org/wiki/Denotational_semantics
SK-логіка

3
Ви говорите про значення програми , яка є "семантикою", як це було б визначено лінгвістом. Але в інформатиці семантика - це значення мови , а не конкретної програми.
SK-логіка

-3

Дуже короткий приклад з "звичайним c":

void main()
{
  int a = 10;
  int x = a - 1;
  int y = - 1;

  printf("x = %i", x);
  printf("y = %i", y);
    getch();
}

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

У присвоєнні "x", "-" означає операцію "субстракція", У "а" асигнації "-" означає операцію "негативний знак".


3
Неправильно. Два -оператора ті ж лексема , але вони синтаксично різні, тому що вони використовуються в різних контекстах. 0 - 1відповідає правилу синтаксису additive-expression: additive-expression - multiplicative-expression, тоді як - 1відповідає правилу синтаксису unary-expression: unary-operator cast-expression(посилання: стандарт C99).
Кіт Томпсон

@Keith Thompson: Ви пропустили суть. Це питання семантики чи синтаксису, а не питання стандарту С. Стандарт правильний, але моя відповідь була спрямована на пояснення концепції, а не, буквально слідуючи, стандарту. Це як питання "Капітан Кірк" проти "Д-р Спок". Ура ;-)
umlcat

Я не погоджуюсь. Відмінність двох -ептера є синтаксичним, а не просто семантичним (хоча вони також мають різну семантику). Синтаксис визначається граматикою мови, а два оператори вказані в різних розділах граматики. Див. Проект N1570 , розділ 6.5.3 для одинарних операторів та 6.5.6 - для операторів добавок. (BTW, якщо ви збираєтесь використовувати приклад C, він, мабуть, має бути правильним; void main()повинен бути int main(void), і ви не вистачаєте, #include <stdio.h>і все, що заголовок оголошуєgetch
Кіт Томпсон,

Щоб уточнити суть, синтаксис не лише в послідовності лексем, а в тому, як ці лексеми створюють більші конструкції. Компілятор, як правило, має лексичний аналізатор (токенізатор) та аналізатор як окремі компоненти; обидва вони мають справу з синтаксисом.
Кіт Томпсон
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.