Чи компілюється Java чи інтерпретована мова програмування?


169

Раніше я використовував C ++ як мову програмування. Я знаю, що код, написаний на C ++, проходить процес компіляції, поки він не стане об'єктним кодом "машинного коду".

Я хотів би знати, як працює Java в цьому відношенні. Як керується комп'ютером написаний користувачем код Java?


14
C ++ можна інтерпретувати. Там є кілька перекладачів С.
Том Хотін - тайклін

Відповіді:


220

В реалізації Java зазвичай використовується двоступінчастий процес компіляції. Компілятор Java збирає вихідний код Java до байт-коду . Байт-код виконується віртуальною машиною Java (JVM). Сучасні JVM використовують техніку під назвою Just-in-Time (JIT) для компіляції байтового коду до рідних інструкцій, зрозумілих апаратним процесором під час виконання під час виконання.

Деякі реалізації JVM можуть вибрати інтерпретацію байт-коду замість JIT, компілюючи його в машинний код, і запустити його безпосередньо. Хоча це все ще вважається "інтерпретатором", він зовсім відрізняється від інтерпретаторів, які читають і виконують вихідний код високого рівня (тобто в цьому випадку вихідний код Java не інтерпретується безпосередньо, байт-код, вихід компілятора Java, є.)

Технічно можливо скомпілювати Java до початкового коду заздалегідь і запустити отриманий двійковий код. Також можливо інтерпретувати код Java безпосередньо.

Підсумовуючи, залежно від середовища виконання, байт-код може бути:

  • компілюється достроково і виконується як власний код (подібно до більшості компіляторів C ++)
  • складений щойно і виконаний
  • інтерпретується
  • безпосередньо виконується підтримуваним процесором (байт-код - це нативний набір інструкцій деяких процесорів)

20
Насправді, деякі JVM HotSpot починаються з інтерпретації байт-кодів і компілюють їх у нативний код лише після того, як вони зрозуміли, що варто компілювати, і зібрали деякі статистичні дані про те, як працює код; наприклад, щоб визначити найбільш поширений шлях у кожній умовній галузі.
Стівен C

1
Звідси термін "Точка доступу" :) Це робить це для того, що працює часто, щоб отримати оптимізацію.
Шовковий полудень

4
Ви можете вимкнути перекладач у HotSpot за допомогою -Xcomp. Варто спробувати додаток, щоб побачити, що це погана ідея.
Том Хотін - тайклін

1
Є твердження: "У поточній версії JVM Sun HotSpot використовується техніка, що називається Just-in-time (JIT) для компіляції байтового коду до рідних інструкцій, зрозумілих процесором під час руху під час виконання". У мене склалося враження, що JVM є інтерпретатором, але це пропонує йому додатково компілювати байт-код. Я збентежений. Також написано, що він робить це під час руху під час виконання. Хтось може це також пояснити?
Ананд

оскільки java - це інтерпретована мова, як це вплине на продуктивність чи будь-яке виконання програми Java
NAND,

93

введіть тут опис зображення

Код, написаний на Java:

  • Спочатку компілюється в байт-код програмою під назвою javac, як показано в лівій частині зображення вище;
  • Потім, як показано у правій частині наведеного зображення, інша програма під назвою java запускає середовище виконання Java і може компілювати та / або інтерпретувати байт-код за допомогою компілятора Java Interpreter / JIT.

Коли java інтерпретує байт-код і коли він його компілює? Код програми спочатку інтерпретується, але JVM відстежує, які послідовності байт-коду часто виконуються, і переводить їх у машинний код для безпосереднього виконання на апаратному забезпеченні. Для байт-коду, який виконується лише кілька разів, це економить час компіляції та зменшує початкову затримку; для часто виконуваного байт-коду компіляція JIT використовується для запуску з високою швидкістю, після початкової фази повільної інтерпретації. Крім того, оскільки програма витрачає більшість часу на виконання меншої частини свого коду, скорочення часу на компіляцію є значним. Нарешті, під час початкової інтерпретації коду статистику виконання можна збирати перед компіляцією, що допомагає покращити оптимізацію.


Це через кешований байт-код, що Java використовує багато пам'яті?
Педро Гордо

3
@sedulam: "Багато пам'яті" - нечітка заява. Управління пам'яттю Java досить просте - три покоління - це те, що JVM використовує для створення та обслуговування своїх об'єктів. Ця ще відповідь ТА може бути корисною для вас.
displayName

З вищезгаданим поясненням теоретично, компільований код C ++ завжди повинен бути швидшим, ніж логічно подібний код Java, оскільки завжди буде частина файлу .class, яку JIT вирішує не перетворювати на машинний код. Іншими словами, java ніколи не може досягти швидкості виконання голого металу, яку продемонстрував C ++. Це правильне припущення?
DevdattaK

@DevdattaK: Я настільки не знаю C ++, але я гадаю , що для менших та спеціалізованих програм Java може дати вам результат швидше, тому що не витрачає час на компіляцію тих частин коду, де не існує великої швидкості.
показНазви

1
@DevdattaK ваше припущення обговорюється на цій вікі-сторінці en.m.wikipedia.org/wiki/Java_performance?wprov=sfla1 Якщо коротко, це не завжди так.
Сундар Раджан

57

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

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

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


5
Крім того, Google V8 JavaScript Execution Engine не просто робить часткову своєчасну компіляцію. Він завжди компілюється в нативний код, насправді V8 навіть не має перекладача. У ньому є лише компілятор (подібний до Maxine, але на відміну від Maxine V8 має лише один компілятор). Усі три наведені приклади (GCJ, Maxine і V8) ще сильніше підтверджують вашу думку: немає такої речі, як інтерпретована мова чи мова, що складена. Мова не інтерпретується та не компілюється. Мова якраз є (Це фактично цитата Шрірама Кришнамурті).
Йорг W Міттаг

3
Чому ви говорите про JavaScript у запитанні java?
Корай Тугай

1
@KorayTugay Як приклад. Я, звичайно, не хочу натякати на те, що Java та Javascript мають щось спільне, крім перших чотирьох літер їх імені.
starblue

Принаймні, різниця в інтерпретованій та компільованій мові не означатиме, що бінарний текст, що складений, не може змінити його потік виконання в будь-який час, тоді як інтерпретована мова дуже послушна деяким поточним функціям функцій? Бібліотеки в C - це варіант, тоді як на інших мовах ви не можете мати об'єкт масиву без бінарного розширення C, яке можна оновити або бути зовсім іншим кодом на іншій платформі. Мова сценаріїв може працювати на обох, тоді як для компільованої мови потрібен інший бінарний файл
Ітон Еммеріх

53

Java компілюється в байт-код, який потім переходить у Java VM, який її інтерпретує.


33
... але не суворо точно.
Стівен C

2
JVM може вирішити не "інтерпретувати" байт-код. Він може компілювати його та виконувати безпосередньо JIT.
Мехрдад Афшарі

1
JIT технічно не виконує це безпосередньо. Це просто згадати, як це було виконано.
клент

Мехрдад: Погодився, я не описував можливих операцій JIT тут, оскільки вважаю, що це до JVM, і я все-таки тримав свою відповідь простою :)
полудень шовк,

7
клетус: Після JIT він буде безпосередньо виконаний. JIT читає шматок байт-коду (наприклад, повний метод) і компілює машинний код і переходить до нього.
Мехрдад Афшарі

12

Java є компільованою мовою програмування, але замість того, щоб компілювати прямо у виконавчий машинний код, він компілюється у проміжну двійкову форму, яку називають байт-кодом JVM. Потім байтовий код компілюється та / або інтерпретується для запуску програми.


11

Вид обох. По-перше, компільований Java (дехто вважає за краще перекласти "перекладений") в байт-код, який потім або компілюється, або інтерпретується залежно від настрою JIT.


32
Це вдосконалене програмне забезпечення, яке розробило настрої :)
Торарін,

5
Справжній JIT - це дуже складна частина програмного забезпечення, яка може робити оптимізацію, засновану на інформації про час виконання (наприклад, профайлер), чого не може зробити достроковий компілятор (тому що він не має інформації про поведінку часу виконання програма достроково). Але, мабуть, насправді немає настроїв ... :-)
Jesper

5

Java здійснює компіляцію та інтерпретацію,

У Java програми не збираються у виконувані файли ; вони компілюються в байт-код (як обговорювалося раніше), який JVM (віртуальна машина Java) потім інтерпретує / виконує під час виконання. Вихідний код Java компілюється в байт-код, коли ми використовуємо компілятор javac. Байт-код зберігається на диску з розширенням файлу .class .

Коли програма має бути запущена, байт-код перетворюється, байт-код може бути перетворений, використовуючи щойно вчасно (JIT) компілятор. Результат - машинний код, який потім подається в пам'ять і виконується.

Javac - компілятор Java, який компілює Java-код у байт-код. JVM - це віртуальна машина Java, яка працює / інтерпретує / переводить байтовий код у код корінної машини. У Java, хоча вона розглядається як інтерпретована мова, вона може використовувати компіляцію JIT (Just-in-Time), коли байт-код знаходиться в JVM. Компілятор JIT зчитує байтові коди у багатьох розділах (або в повному обсязі, рідко) та динамічно компілює їх у машинний код, щоб програма могла працювати швидше, а потім кешуватись та використовувати повторно, не потребуючи перекомпіляції. Таким чином, компіляція JIT поєднує швидкість компільованого коду з гнучкістю інтерпретації.

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

Мова компіляції - це мова програмування, реалізацією якої є, як правило, компілятори (перекладачі, які генерують машинний код із вихідного коду), а не інтерпретатори (покрокові виконавці вихідного коду, де не відбувається переклад перед виконанням часу).

У сучасних реалізаціях мови програмування, як у Java, платформа набуває все більшої популярності для надання обох варіантів.


Повинно бути «байт - код може бути перетворений» , а не « це перетворене». Специфікації Java визначають байт-код. Незалежно від того, що цей байт-код запускається (a) безпосередньо в апаратному забезпеченні , (b) через інтерпретатор, (c) заздалегідь складений або (d) частково складений під час руху під час виконання , всі залишені як деталі реалізації. Зауважте, що всі чотири з цих варіантів справді використовувалися різними реалізованими реалізаціями Java.
Василь Бурк

Дякуємо, що вказали на це. Що ж станеться, якщо байт-код не буде перетворений на машинний код? Я можу придумати сценарій, коли байт-код - це нативна інструкція, встановлена ​​для деяких процесорів, і тоді немає необхідності в перетворенні. Або я щось пропускаю.
прем’єр

Клацніть посилання, яке я надав для технології Jazelle DBX (Direct Bytecode eXecution) , де підмножина байт-коду JVM - це вбудована машинна інструкція ЦП ( своєрідна сортація ). Без цього ви отримуєте машинний код, сформований з байт-коду (а) від інтерпретатора (на льоту), (б) від компілятора заздалегідь, або (в) в режимі "льоту" за допомогою щойно введеного часу компілятора ( інтерпретується спочатку, а потім іноді компілюється та кешується під час виконання).
Василь Бурк

-2

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


1
Що означає "складений байт"?
Джеспер

2
@Jesper: "Байт-компільований" зазвичай означає "компільований для байт-коду". "Байт-код" - це загальний термін, який охоплює будь-який нетекстовий проміжний код (як правило, не виконується машиною).
Грег Хьюгілл

-3

Цитата від: https://blogs.oracle.com/ask-arun/entry/run_your_java_applications_faster

Розробники програм можуть розробляти код програми на будь-якій з різних ОС, які доступні на ринку сьогодні. На цій стадії мова Java є агностичною для ОС. Блискучий вихідний код, написаний розробником програми Java, тепер збирається в код Java Byte, який у термінології Java називається компіляцією на стороні клієнта. Ця компіляція до коду Java Byte - це те, що дозволяє розробникам Java "писати один раз". Java-байт-код може працювати на будь-якій сумісній ОС та сервері, отже, робить вихідний код агностиком OS / Server. Опублікуйте створення коду Java Byte, взаємодія між додатком Java та базовою ОС / сервером є більш інтимною. Подорож триває - Корпоративна програма програм виконує ці Java-байт-коди в середовищі часу виконання, яке відоме як віртуальна машина Java (JVM) або середовище виконання Java Java (JRE). JVM тісно пов'язаний з базовою ОС та апаратним забезпеченням, оскільки використовує ресурси, пропоновані ОС та Сервер. Тепер код байтового Java компілюється у виконавчий код машинної мови, який залежить від платформи. Це називається компіляцією на стороні сервера.

Тому я б сказав, що Java - це безумовно компільована мова.

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