Anda di halaman 1dari 107

Artikel Teknik Kompilasi

Dibuat Oleh :

Nama : Yudi Chandra

NPM : 2013.10.225.229

Semester / Kelas : VII / Reguler A Sore


1

Pendahuluan
Teknik Kompilasi merupakan mata kuliah yang khusus ditujukan kepada mahasiswa
jurusan Teknik Informatika dan Ilmu Komputer. Adapun sejumlah sasaran dari
mempelajari mata kuliah Teknik Kompilasi ini diantaranya adalah :
1. Mahasiswa diharapkan mampu memahami prinsip kerja yang mendasar dari suatu
kompiler.
2. Mengetahui tahapan - tahapan dari suatu proses kompilasi.
3. Mahasiswa juga diharapkan mempunyai bekal mendasar untuk mengembangkan
ilmu pengetahuan yang dimilikinya ke tingkat yang lebih lanjut.

Bahasa Pemrograman
Manusia dapat melakukan interaksi secara efektif dengan menggunakan media
bahasa. Bahasa memungkinkan penyampaian gagasan dan pemikiran, tanpa itu
komunikasi akan sulit terjadi. Dalam lingkungan pemrograman komputer, bahasa
pemrograman bertindak sebagai sarana komunikasi antara manusia dan
permasalahannya dengan komputer yang dipakai untuk membantu memperoleh
pemecahan.

Bahasa pemrograman berdasarkan tingkat ketergantungannya dengan mesin bisa


meliputi:
1. Bahasa Mesin
Merupakan bentuk terendah dari bahasa komputer. Setiap instruksi dalam program
direpresentasikan dengan kode numerik, yang secara fisik berupa deretan angka 0
dan 1.
2. Bahasa Assembly
Merupakan bentuk simbolik dari bahasa mesin. Setiap kode operasi memiliki kode
simbolik, misalnya ADD untuk penjumlahan (Addition) dan MUL untuk perkalian
(Multiplication). Pada bahasa assembly tersedia alat bantu untuk diagnostik atau
debug yang tidak terdapat pada bahasa mesin. Contoh produk yang ada untuk
pengembangan dan debug bahasa assembly di pasaran saat ini, misalnya Turbo
Assembler dari Borland, Macro Assembler dari Microsoft, Debug yang tersedia
pada DOS, dan lain - lain.
2

3. Bahasa tingkat tinggi (User Oriented)


Disebut tingkat tinggi karena lebih dekat dengan manusia. Memberikan fasilitas
yang lebih banyak, kontrol program yang terstruktur, kalang (nested), block, dan
prosedur. Contohnya : Pascal, C, Basic, dan lain - lain.
4. Bahasa yang Problem Oriented
Memungkinkan penyelesaian untuk suatu masalah atau aplikasi yang spesifik.
Contohnya : SQL (Structured Query Language) untuk aplikasi database, COGO
untuk aplikasi teknik sipil. Bahasa yang problem oriented kadang dimasukkan pula
sebagai bahasa tingkat tinggi.

Keuntungan bahasa tingkat tinggi dibandingkan bahasa tingkat rendah adalah sebagai
berikut.
1. Kemudahan untuk dipelajari.
2. Lebih mendekati permasalahan yang akan diselesaikan.
3. Pemrogram tidak perlu mengetahui bagaimana representasi data ke dalam bentuk
internal di memory.
4. Memberikan banyak pilihan struktur kontrol seperti :
Kondisional (IF - THEN - ELSE)
Looping
Struktur Blok (Begin ... End)
Nested Statement
5. kompabilitas dan dokumentasi yang lebih baik dalam pengembangan program.

Translator
Sebuah translator melakukan pengubahan source code / source program (program
sumber) ke dalam target code / object code / object program (program objek). Source
code ditulis dalam bahasa sumber, sedang object code bisa berupa suatu bahasa
pemrograman lain atau bahasa mesin pada suatu komputer. Ada beberapa macam
translator.
1. Assembler
Menerjemahkan langsung dari source code ke object code. Source Code adalah
bahasa assembly sedangkan object code adalah bahasa mesin. Contohnya adalah
TASM.
3

Assembler File .Exe


File.ASM atau .Com

Contoh yang menghasil .Com adalah : Debug, TASM (bila linker dilakukan
dengan perintah Tlink/x/t), emu8086,
Contoh yang menghasilkan .Exe adalah : TASM dengan perintah linker Tlink,
HLA, MASM32, FASM
Khusus TASM terkadang file .Com yang dihasilkan akan lebih baik daripada file .Exe
yang dihasilkan sebagai contoh adalah pada program berikut :
.Model Small
.Code
Org 100h
Main :
Jmp Mulai
Pesan db 'Selamat Datang!','$'
Mulai :
Mov Ah,09H
Mov dx,offset pesan
int 21h
mov ah,4ch
int 21h
end Main

2. Kompilator (Compiler)
Source Code adalah bahasa tingkat tinggi (misal bahasa Pascal), object code
adalah bahasa mesin atau bahasa assembly. Source Code dan data diproses pada
saat yang berbeda. Contohnya : Turbo Pascal, C++.

Source Compiler Object File


File Code Executable

3. Interpreter
Interpreter tidak membangkitkan Object Code, hasil translasi hanya dalam bentuk Run
Time Code.
Contohnya : Bahasa Basica, Dbase/Foxbase
4

Source Interpreter Run Time


Code Code

Perbedaan antara Interpreter dengan Compile


Interpreter
1. Menerjemahkan instruksi per instruksi
2. Tidak menghasilkan objek program
3. Tidak menghasilkan executable program
4. Source program terus dipergunakan karena tidak dihasilkan executable program.

Compiler
1. Menerjemahkan secara keseluruhan sekaligus
2. Dihasilkan objek program
3. Dihasilkan executable program
4. Source program tidak dipergunakan lagi untuk menjalankan program.

Model Kompilator
Pengembangan kompilator untuk sebuah bahasa merupakan pekerjaan yang
kompleks. Kompleksitas kompilator bisa dikurangi bila perancang bahasa
pemrograman mempertimbangkan bermacam - macam faktor perancangan. Karena kita
berhubungan dengan bahasa tingkat tinggi, bagaimanapun suatu model dasar dari
kompilator dapat diformulasikan.

Sebuah kompilator umumnya memiliki 2 tugas pokok :


1. Fungsi Analisis
Fungsi analisis biasa disebut sebagai Front End. Tugasnya melakukan
dekomposisi program sumber menjadi bagian - bagian dasarnya.
2. Fungsi Sintesis
Fungsi sintesis biasa disebut sebagai Back End. Tugasnya melakukan
pembangkitan dan optimasi program objek.
5

Model sebuah kompilator bisa dilihat pada gambar di bawah ini.

Source Object
Code Code

Analysis Synthesis

Lexical Syntetic Sematic Code Code


Intermediate
Analyzer Analyzer Analyzer Generator Optimizer
Code
(Scanner) (Parser) Intermediate
Code
Generator

Tabel Informasi

Keterangan gambar :
Scanner : memecah program sumber menjadi besaran leksikalnya.
Beberapa kegiatan pada tahap scanner ini diantaranya adalah :
- Menangani kesalahan
Contohnya : A = +B 1
- Membuang Blank
Contohnya : A = B + 1
- Mengenali besaran leksikal
Contohnya di sini adalah mengenali apakah huruf atau angka
- Dan lain - lain
Parser : Memeriksa kebenaran dan urutan kemunculan token
Seperti :
- Samping kiri = pasti variabel
- Samping kanan = pasti ekspresi
- Tiap operator +, -, *, /, tidak boleh double. Contohnya : A = 3++7
6

Analisis semantik : Melakukan analisa semantik, biasanya dalam realisasi akan


digabungkan dengan intermediate code generator (bagian yang berfungsi
membangkitkan kode antara.
Seperti :
- Triples Notation
- Quadruples Notation
Code Generator : Membangkitkan kode objek. Bagian ini merupakan bagian yang
bersifat abstrak, artinya tidak dilaksanakan oleh programmer. Tetapi dilakukan
oleh bahasa pemrograman yang dilakukan oleh programmer dalam perancangan
compiler. Di sini kode antara dari program biasanya ditranslasi ke bahasa
assembly atau bahasa mesin.
Code Optimizer : Upaya untuk memperkecil hasil dan mempercepat proses
Tabel Informasi : Menyimpan semua informasi yang berhubungan dengan proses
kompilasi.

Pada beberapa kompilator, bagaimanapun, fase - fase kompilasi tersebut bisa


dikombinasikan. Bisa kita lihat, misalnya interaksi antara scanner dan parser terdapat dua
kemungkinan :
1. Scanner menghasilkan suatu token untuk diproses oleh parser. Parser akan
memanggil scanner bila token berikutnya diperlukan.
2. Scanner menghasilkan semua token yang berhubungan dengan source program
sebelum memneruskan ke parser. Pada kasus ini scanner telah memeriksa
keseluruhan source program.

Mutu Kompilator
Misalkan saja kita pernah menggunakan kompilator untuk bahasa Basic seperti Turbo
Basic dan Quick Basic. Kemudian kita bisa mengatakan bahwa salah satu lebih baik dari
lainnya. Tentu ada beberapa hal yang menjadi pertimbangan kita, dalam hal ini bisa kita
sebut sebagai mutu dari kompilator yang bersangkutan. Mutu sebuah kompilator
bergantung dari beberapa faktor, yaitu :
1. Kecepatan dan waktu proses kompilasi.
Bisa Anda bayangkan misalkan saat Anda menekan F9 (Compile) dalam
kompilator Turbo Pascal untuk melakukan kompilasi suatu program. Berapa lama
7

Anda harus menunggu untuk memperoleh hasil kompilasi itu merupakan waktu
proses kompilasi.

Mutu ini tergantung dari :


Penulisan algoritma kompilator : yaitu algoritma yang digunakan untuk
menuliskan program kompilator tersebut. Misalkan saja bisa dikatakan bahwa
suatu kompilator lebih cepat melakukan kompilasi dibandingkan lainnya,
karena para pemrogramnya menggunakan algoritma yang lebih baik saat
membuat kompilator tersebut.
Kompilator pengkompilasi : sebuah program khusus yang menghasilkan
kompilator tersebut. Bisa kita bayangkan kompilator Turbo Basic, misalnya,
tentu saja tidak dibuat dengan bahasa Basic, tetapi menggunakan bahasa lain
dan dikompilasi.dengan kompilator lain. Kalau sebuah kompilator dibuat
dengan bahasa C, misalnya , kompilator C tersebut juga ikut menentukan mutu
kompilator yang dibuat.

Source Program Kompilator


Kompilator A Pengkompilasi Kompilator
dalam Bahasa K (K) Bahasa A

2. Mutu Program Objek


Mutu suatu program objek (program hasil dari proses kompilasi) ditentukan oleh
ukuran dan kecepatan eksekusi dari program objek. Misalkan saja kita bisa
mengatakan bahwa Turbo Pascal 6 lebih baik dari Turbo Pascal 5, bila program
Objek (EXE) yang dihasilkan berukuran lebih kecil dan lebih cepat dieksekusi.
Hal ini tergantung dari fungsi translasi yang digunakan oleh kompilator tersebut
(cara untuk melakukan perubahan dari source code ke object code). Misalkan saja
kita akan membuat suatu kompilator yang memiliki instruksi untuk menuliskan
suatu kalimat ke layar, kita sebut saja instruksi writekar. Kompilator ini kita buat
dengan bahasa assembly. Sementara pada assembly untuk melakukan pencetakan
kalimat bisa dengan Intterupt 10 atau Intterupt 21. Maka pilihan apakah instruksi
8

writekar tadi akan diubah ke intterupt 10 atau intterupt 21, akan ikut menentukan
ukuran object code - nya

3. Integrated Environtment
Merupakan fasilitas - fasilitas terintegrasi yang dimiliki oleh kompilator tersebut.
Misalnya untuk melakukan editing, debugging, testing. Biasa disebut juga dengan
IDE (Integrated Development Environtment). Misalkan saja dengan Turbo Pascal
(Turbo.Exe) Anda bisa melakukan penyuntingan sekaligus kompilasi dan debug
dalam satu lingkungan pemrograman. Sementara kalau menggunakan Clipper
(Clipper.Exe) Anda harus melakukan penyuntingan dengan menggunakan suatu
program editor (PE.Exe) ataupun notepad yang terpisah dari kompilatornya.

Pembuatan Kompilator
Pembuatan suatu kompilator dapat dilakukan dengan :
1. Bahasa Mesin
Tingkat kesulitannya sangat tinggi, karena bahasa mesin ini sangat dekat dengan
mesin sehingga sangat tidak manusiawi, dan tingkat ketergantungannya pada
mesin yang tinggi. Pembuatan kompilator dengan bahasa mesin hampir mustahil
dilakukan. Bahasa mesin mungkin digunakan saat membuat assembler. 2.
Bahasa Assembly
Bahasa assembly bisa dan biasa digunakan sebagai tahap awal pada proses
pembuatan sebuah kompilator. Keuntungan penggunaan bahasa assembly adalah
program hasil (object code) yang memiliki ukuran kecil. Kerugiannya
memerlukan usaha yang besar, karena instruksi assembly pendek - pendek (sulit
dimengerti) dan memiliki fasilitas yang terbatas. Sehingga masih terdapat
kesulitan untuk mengembangkan sebuah kompilator yang secara keseluruhan
dibuat dengan bahasa assembly.
3. Bahasa tingkat tinggi
Keuntungannya adalah proses pembuatan kompilator akan lebih mudah, karena
menggunakan bahasa tingkat tinggi yang lebih mudah dimengerti dan fasilitasnya
lebih baik dibandingkan assembly. Kerugiannya kompilator yang dihasilkan akan
memiliki ukuran yang besar. Bisa dibayangkan kalau kita akan mengembangkan
suatu kompilator untuk suatu bahasa dengan menggunakan Turbo Pascal.
9

4. Bootstrap
Gagasan dari Bootstrap adalah kita bisa membangun sesuatu yang besar dengan
lebih dulu membuat bagian intinya. Cara ini diperkenalkan oleh Niklaus Wirth saat
membuat kompilator untuk bahasa Pascal.
P2
P1

P0

Pada gambar di atas, P0 dibangun dengan assembly, P1 dibangun dengan P0, P2


dibangun dengan P1. Jadi kompilator untuk bahasa P bisa dibuat tanpa harus
secara keseluruhan menggunakan assembly.

Soal :
1. Mengapa kita memerlukan bahasa pemrograman ?
2. Berikan penjelasan dari istilah - istilah berikut :
a. Kompilator
b. Translator
c. Interpreter
d. Assembler
e. Emulator
3. Berikan beberapa contoh produk yang ada dipasaran untuk setiap istilah pada
nomor 2.
4. Apa keuntungan dari penggunaan metode Bootsrap.

Jawab :
1. Alasan pentingnya bahasa pemrograman : Bahasa pemrograman digunakan
sebagai alat untuk berkomunikasi dengan komputer untuk menjalankan suatu
instruksi (program) tertentu, sehingga melalui bahasa pemrograman dapat
dihasilkan suatu sistem yang sederhana hingga sistem yang kompleks.
2. Artinya adalah :
10

a. Kompilator adalah suatu bahasa tingkat tinggi untuk menerjemahkan dari


suatu source code untuk menjadi object code, untuk kemudian menghasilkan
suatu executable program.
b. Interpreter adalah suatu bahasa tingkat tinggi untuk menerjemahkan dari suatu
source code menjadi run time code.
c. Translator adalah Suatu bahasa tingkat tinggi untuk menerjemahkan dari suatu
source code manjadi bahasa mesin.
d. Assembler adalah suatu bahasa untuk menerjemahkan dari suatu sintaks
assembly menjadi bahasa mesin.
e. Emulator adalah suatu bahasa pemrograman yang dirancang untuk menyerupai
cara kerja dari suatu bahasa yang lain.
3. Contoh kompilator adalah :Bahasa Pascal, C++.
Contoh Interpreter adalah : Bahasa Basica, Dbase / Foxbase
Contoh Translator adalah : Bahasa Pascal, C++, Bahasa Basica
Contoh Assembler adalah : TASM, MASM, NASM, FASM
Contoh Emulator : emu8086
4. Jika program inti sudah dirancang dengan baik, maka pengembangan akan lebih
cepat dilakukan.

Sumber Perancangan Bahasa Pemrograman


Gagasan untuk perancangan bahasa pemrograman bisa berasal dari bahasa alami
(natural language), matematika, dan bahasa pemrograman yang sudah ada.
Penjelasannya masing - masing sebagai berikut.
1. Konstruksi yang diturunkan dari bahasa alami berguna untuk kejelasan dan
kemudahan pembacaan. Sebuah instruksi akan mengerjakan mirip dengan arti
instruksi itu. Hal ini memberikan kenyamanan untuk para pemrogram, khususnya
yang belum berpengalaman. Di sisi lain bisa pula menimbulkan ambiguitas / ke -
dwi artian- yang tidak diinginkan dalam sebuah bahasa pemrograman.
Bagaimanapun, bahasa alami bisa digunakan sebagai panduan untuk perancangan
sintaks sebuah bahasa pemrograman.
2. Matematika telah banyak dipakai untuk aturan - aturan yang terdapat pada bahasa
pemrograman, misalnya ekspresi aritmatika. Tetapi, seseorang pemrogram dan
ahli matematika menggunakan metode dan memecahkan masalah yang berbeda.
11

Meskipun matematika merupakan suatu sumber yang berguna, perlu kehati -


hatian saat mengadopsi notasi matematika untuk suatu konsep.
3. Bahasa pemrograman yang sudah ada bisa menjadi sumber yang bagus untuk
perancangan bahasa pemrograman. Tetapi perlu ketelitian saat menggunakannya,
karena bahasa yang sudah ada itu mungkin mengandung kesalahan yang serius.
Beberapa fasilitas yang diinginkan bisa dibatasi untuk meningkatkan kemudahan
baca (readability) dan pemeriksaaan kesalahan, dengan mengamati bagian mana
dari bahasa yang jarang digunakan. Misalnya motivasi untuk tidak menggunakan
instruksi GOTO datang dari pengamatan bahwa pemrogram yang baik tidak
menggunakan GOTO untuk membuat struktur yang lebih mudah dipahami.

Pertimbangan dalam Perancangan Bahasa Pemrograman


Adapun pertimbangan - pertimbangan yang perlu dalam perancangan sebuah bahasa
pemrograman adalah sebagai berikut.
1. Komunikasi dengan manusia
Jika sebuah program sulit dimengerti oleh manusia, akan terjadi kesulitan juga
untuk memeriksa dan melakukan pemeliharaan / modifikasi. Masalah ini tidak
bisa dipecahkan dengan sekedar menambahkan komentar atau melalui
dokumentasi tersendiri. Pemrogram tidak suka menambahkan komentar yang
berlebihan, sementara dokumentasi program sering tidak lengkap. Sintaks sebuah
bahasa pemrograman harus merefleksikan semantiknya. Keterbatasan kemampuan
pikir menyulitkan untuk memahami suatu struktur yang kompleks, sementara
kompilator tidak. Mungkin suatu statement bermakna ambigu bagi manusia,
sementara sudah cukup jelas bagi kompilator, misalkan instruksi aritmatika
berikut :
A/b/c
Bisa berarti
a dibagi dengan b, baru hasilnya dibagi dengan c
Atau
a dibagi dengan hasil pembagian b dengan c 2.
Pencegahan dan deteksi kesalahan
Sebuah bahasa pemrograman yang baik perlu mengidentifikasikan error yang
mungkin terjadi. Sehingga mempermudah deteksi kesalahan dan
menghilankannya.
12

3. Usability
Bahasa pemrograman harus mudah dipelajari dan diingat. Sekali seorang
pemrogram familiar dengan bahasa itu, dia tidak harus melihat manual terus -
menerus. Usability berkaitan dengan aspek kenyamanan seorang pemrogram
menggunakan bahasa.
4. Efektifitas pemrograman
Efektifitas pemrograman berkaitan erat dengan kemudahan dalam proses
pembuatan program. Bahasa pemrograman yang case sensitive akan mempunyai
tingkat efektifitas yang lebih rendah dibandingkan dengan bahasa pemrograman
yang non case sensitive
5. Compilability
Pengembangan sebuah kompilator merupakan pekerjaan yang tidak sederhana.
Sebuah bahasa yang terlalu kompleks akan menyulitkan pembuatan kompilator
untuk bahasa tersebut. Kompleksitas tersebut bisa muncul baik pada tahapan
analisis maupun sintaksis. Sebagai contoh yang sederhana adalah penggunaan
buka kurung dan tutup kurung, yang bisa digunakan untuk banyak kegunaan.
1. Untuk membatasi argumen pada pemanggilan prosedur
2. Untuk membatasi parameter pada definisi prosedur
3. Ekspresi logika
4. dll
6. Efisiensi
Efisiensi merupakan bahasan yang penting dalam sejarah pengembangan bahasa
pemrograman. Dalam hal ini perlu diingat bahwa tidak seharusnya user
dikorbankan dengan memaksa mereka mengeluarkan uang untuk peningkatan
perangkat keras.
7. Machine Independent
Sebuah bahasa dikatakan machine independent jika dan hanya jika sebuah
program yang telah sukses dikompilasi dan dieksekusi pada suatu mesin, saat
dipindahkan ke mesin lainnya akan berjalan dengan input dan output yang tepat
sama
8. Kesederhanaan (simpiclicty)
Suatu bahasa pemrograman harus dirancang secara sederhana, seperti menyangkut
pendeklarasian variabel, pemakaian suatu fungsi, ataupun untuk mengakses suatu
13

properti pada suatu bahasa. Bahasa pemrograman visual basic misalnya memiliki
konsep keserhanaan dalam artian untuk pendeklrasian variabel.

Detail Rancangan
Microstructure
Microstructure pada dasarnya mencakup masalah - masalah dalam perancangan
bahasa yang mempengaruhi penampilan bahasa sehingga lebih mudah dimengerti.
Prinsip mendasar dari suatu microstructure adalah arti dari suatu konstruksi, seperti
keyword, harus jelas dari wujudnya. Dengan kata lain, token suatu bahasa harus
mudah dikenali apakah itu dan apa yang dilakukan.

Keyword harus bisa diucapkan, karena akan lebih mudah diingat. Keyword harus
dipilih sedemikian sehingga tidak akan sama dengan identifier yang dibuat user.
Misalkan saja gunakan operator SIZE ketimbang SIZ. Jika mungkin jangan
gunakan dua keyword yang memiliki ejaan yang mirip (misal PROGEND dengan
PROCEND). Terdapat tiga pendekatan bagaimana memisahkan keyword dengan
identifier yang didefinisikan user :
1. Keyword adalah reserved dan tidak boleh digunakan sebagai identifier
Merupakan alternatif terbaik karena sederhana dan jarang menimbulkan masalah.
2. Keyword dibedakan dari identifier berdasarkan konteksnya
Menyulitkan pada tahap parser, karena jumlah keyword pada beberapa
implementasi begitu besar sehingga user tidak dapat menghindarinya.
3. Keyword diawali dengan karakter khusus untuk menandainya
Memerlukan tambahan pengetikan dan membuat program lebih susah dibaca.

Aspek lain dari Microstructure adalah pengaturan komentar. Salah satu pendekatan
dalam yang digunakan adalah dengan menggunakan suatu simbol untuk menandai
awal komentar dan kemudian apapun sampai akhir baris dianggap sebagai komentar.
Pemilihan simbol yang mendahului komentar idealnya :
1. Simbol terdiri dari dua karakter, lebih baik karakter yang sama
2. Simbol yang jarang dipergunakan
3. Terdiri dari karakter berlokasi sama pada keyboard
Contohnya simbol // adalah pilihan yang baik untuk menandai komentar.
14

Struktur Ekspresi
Salah satu topik yang berhubungan dengan ekspresi adalah urutan dari evaluasinya.
Seperti dalam operasi aritmatika memiliki urutan evaluasi :
1. Operator ( dan operator )
2. Operator * dan /
3. Operator + dan -

Struktur Data
Empat aspek dari struktur data adalah :
1. Deklarasi Data
Biasanya kebutuhan bahasa pemrograman berkaitan dengan deklarasi untuk :
a. Konstanta
b. Tipe
c. Variabel
2. Tipe Data
Terdapat tiga pendekatan untuk tipe data dalam bahasa pemrograman :
a. Tidak ada sama sekali. Merupakan karakteristik yang ada pada bahasa
assembly
b. Soft Typing. Ditentukan suatu jenis tipe, di mana setiap variabel boleh
memuat nilai apapun.
c. Hard typing. Ditentukan suatu jenis tipe, di mana setiap variabel hanya boleh
memuat nilai yang menjadi domain dari tipe tersebut. Dari sudut pandang
pemeriksaan kesalahan saat kompilasi hard typing lebih unggul.

Struktur Kontrol
Sering dipakai dengan menggunakan If then else dan juga perintah Case.

Struktur Kompilasi
Struktur kompilasi mencakup aspek dari bahasa yang berkaitan dengan proses
kompilasi, berhubungan dengan operasi pada bahasa yang dikerjakan saat kompilasi dan
bagaimana kompilasi modul yang berbeda dan terpisah dari program. Salah satu fasilitas
adalah untuk menyisipkan suatu file lain (seperti include pada bahasa C ataupun uses
pada bahasa Pascal).
15

Pendahuluan
Teknik Kompilasi merupakan mata kuliah yang khusus ditujukan kepada mahasiswa
jurusan Teknik Informatika dan Ilmu Komputer. Adapun sejumlah sasaran dari
mempelajari mata kuliah Teknik Kompilasi ini diantaranya adalah :
1. Mahasiswa diharapkan mampu memahami prinsip kerja yang mendasar dari suatu
kompiler.
2. Mengetahui tahapan - tahapan dari suatu proses kompilasi.
3. Mahasiswa juga diharapkan mempunyai bekal mendasar untuk mengembangkan
ilmu pengetahuan yang dimilikinya ke tingkat yang lebih lanjut.

Bahasa Pemrograman
Manusia dapat melakukan interaksi secara efektif dengan menggunakan media
bahasa. Bahasa memungkinkan penyampaian gagasan dan pemikiran, tanpa itu
komunikasi akan sulit terjadi. Dalam lingkungan pemrograman komputer, bahasa
pemrograman bertindak sebagai sarana komunikasi antara manusia dan
permasalahannya dengan komputer yang dipakai untuk membantu memperoleh
pemecahan.

Bahasa pemrograman berdasarkan tingkat ketergantungannya dengan mesin bisa


meliputi:
1. Bahasa Mesin
Merupakan bentuk terendah dari bahasa komputer. Setiap instruksi dalam program
direpresentasikan dengan kode numerik, yang secara fisik berupa deretan angka 0
dan 1.
2. Bahasa Assembly
Merupakan bentuk simbolik dari bahasa mesin. Setiap kode operasi memiliki kode
simbolik, misalnya ADD untuk penjumlahan (Addition) dan MUL untuk perkalian
(Multiplication). Pada bahasa assembly tersedia alat bantu untuk diagnostik atau
debug yang tidak terdapat pada bahasa mesin. Contoh produk yang ada untuk
pengembangan dan debug bahasa assembly di pasaran saat ini, misalnya Turbo
Assembler dari Borland, Macro Assembler dari Microsoft, Debug yang tersedia
pada DOS, dan lain - lain.
16

Mengenali Huruf pada Suatu Input


Pengenalan huruf ini penting untuk mengetahui apakah suatu besaran leksik itu
berupa identifier, variabel ataupun konstanta.
1) Identifier atau Keyword
Terdiri dari deretan kata kunci pada suatu bahasa pemrograman seperti : if, else, end
if, then, for, while, dll
2) Konstanta
Berupa angka tetap
3) Delimiter dan Operator
Terdiri dari rangkaian operator, dalam hal ini adalah operator aritmatika dan
operator pembanding seperti : +, -, <, >, dll.

Berikut ini adalah program pada Bahasa Pemrograman Visual Basic untuk mengenali
apakah suatu input itu huruf atau tidak.
Private Sub Form_Load()
a = InputBox("Masukkan Input:")
For i = 1 To Len(a)
d = Mid(a, i, 1)
If (d >= "A" And d <= "Z") Or (d >= "a" And d <= "z") Then
Debug.Print "Huruf"
Else
Debug.Print "Bukan Huruf"
End If
Next i
End Sub

Atau, cara lain :


Private Sub Form_Load()
a = InputBox("Masukkan Input:")
For i = 1 To Len(a)
d = Mid(a, i, 1)
If (Asc(d) >= Asc("A") And Asc(d) <= Asc("Z")) Or (Asc(d) >=
Asc("a") And Asc(d) <= Asc("z")) Then
Debug.Print "Huruf"
Else
Debug.Print "Bukan Huruf"
17

End If

Next i
End Sub

Dengan menggunakan Bahasa Pascal :


uses crt;
var
ekspresi : String;
tampung:char;
i:integer;
begin
clrscr;
write('Masukkan ekspresi:');
readln(ekspresi);
for i:=1 to length(ekspresi) do
begin
if ((ekspresi[i]>=#65) and (ekspresi[i]<=#97)) or
((ekspresi[i]>=#97) and (ekspresi[i]<=#122)) then
writeln('Huruf')
else
writeln('Bukan Huruf');
end;
readln;
end.

Dengan menggunakan bahasa C :


#include <stdio.h>
#include <conio.h>
#include <ctype.h>
#include <string.h>
void main()
{
clrscr();
char ekspresi[100];
int i;
printf("Masukkan Ekspresi:");
scanf("%s",&ekspresi);
for(i=0;i<strlen(ekspresi);i++)
{
18

if (isalpha(ekspresi[i]))
printf("Adalah huruf\n");
else
printf("Bukan Huruf\n");
}
getch();
}

Versi II :
#include <stdio.h>
#include <conio.h>
#include <string.h>
void main()
{
clrscr();
char ekspresi[100];
int kar;
int i;
printf("Masukkan Ekspresi:");
scanf("%s",&ekspresi);
for(i=0;i<strlen(ekspresi);i++)
{
kar=ekspresi[i];
if (((kar>=65) && (kar<=90)) || ((kar>=97) && (kar<=122)))
printf("Adalah huruf\n");
else
printf("Bukan Huruf\n");
}
getch();
}

Mengenali Angka pada Suatu Input


Private Sub Form_Load()
Debug.Print "--------------"
a = InputBox("Masukkan Input:")
For i = 1 To Len(a)
d = Mid(a, i, 1)
If (Asc(d) >= Asc("0") And Asc(d) <= Asc("9")) Then
Debug.Print "Angka"
Else
19

Debug.Print "Bukan Angka"


End If

Next i
End Sub

Cara lain :
Private Sub Form_Load()
a = InputBox("Masukkan Input:")
For i = 1 To Len(a)
d = Mid(a, i, 1)
If (d >= "0" And d <= "9") Then
Debug.Print "Angka"
Else
Debug.Print "Bukan Angka"
End If

Next i
End Sub

Dengan menggunakan bahasa Pascal :


uses crt;
var
ekspresi : String;
tampung:char;
i:integer;
begin
clrscr;
write('Masukkan ekspresi:');
readln(ekspresi);
for i:=1 to length(ekspresi) do
begin
if ((ekspresi[i]>=#48) and (ekspresi[i]<=#57))then
writeln('Angka')
else
writeln('Bukan Angka');
end;
readln;
end.
20

Dengan menggunakan Bahasa C :


#include <stdio.h>
#include <conio.h>
#include <ctype.h>
#include <string.h>
void main()
{
clrscr();
char ekspresi[100];
int i;
printf("Masukkan Ekspresi:");
scanf("%s",&ekspresi);
for(i=0;i<strlen(ekspresi);i++)
{
if (isdigit(ekspresi[i]))
printf("Angka\n");
else
printf("Bukan Angka\n");
}
getch();
}

Versi :
#include <stdio.h>
#include <conio.h>
#include <string.h>
void main()
{
clrscr();
char ekspresi[100];
int kar;
int i;
printf("Masukkan Ekspresi:");
scanf("%s",&ekspresi);
for(i=0;i<strlen(ekspresi);i++)
{
kar=ekspresi[i];
if ((kar>=48) && (kar<=57))
printf("Angka\n");
else
21

printf("Bukan Angka\n");
}
getch();
}

Analisis Leksikal
Tugas utama penganalisis leksikal / Scanner adalah mengidentifikasi semua besaran
yang membangun suatu bahasa pada program sumber. Scanner adalah bagian dari
kompilator yang menerima input berupa stream karakter kemudian memilah program
sumber menjadi satuan leksik yang disebut dengan token. Token ini akan menjadi
input bagi parser.
Pekerjaan yang dikerjakannya antara lain :
1. Melakukan pembacaan kode sumber dengan merunut karakter demi karakter. 2.
Mengenali besaran leksik.
3. Membuang komentar : Komentar biasanya ditulis oleh programmer untuk
mempermudah dalam mempelajari program yang dibuat. Dalam setiap bahasa
pemrograman selalu disediakan simbol untuk mengawali / mengakhiri komentar.
Oleh karena itu scanner pada analisis leksikal ini harus dapat mengenali bagian
awal dan akhir setiap komentar supaya dapat dibuang atau tidak ikut dalam proses
kompilasi.
4. Menyeragamkan huruf kapital menjadi huruf kecil atau sebaliknya : Untuk bahasa
bahasa - bahasa pemrograman yang bersifat non - case sensitive, identifier
arraySize dan arraysize dianggap sama. Oleh karena itu, bagian penganalisis
leksikal bertugas menyeragamkan jenis huruf agar identifier semacam itu tidak
dianggap berbeda.
5. Membuang spasi
6. Menangani kesalahan

Besaran Leksik
Besaran pembangun bahasa / leksik meliputi :
1. Identifier
Bisa berupa keywords atau nama. Keywords adalah kata kunci yang sudah
didefinisikan oleh suatu bahasa seperti Begin, End, If, dan Else di dalam Pascal.
Nama dideklarasikan sendiri oleh pemakai seperti nama pada sebuah variabel.
Misal :
22

Var
Nama : Integer;
Suhu : Real;
2. Nilai Konstanta
Adalah suatu konstanta yang terdapat pada program. Bisa berupa konstanta
integer, real, boolean, character, string, dan sebagainya.
Misal :
Const
N := 10;
Kata := Saya
3. Operator dan Delimiter
Operator misalnya +, -, *, dan /.

Menghilangkan Blank
Dalam pengetikan suatu program, terkadang sering terjadi adanya banyak blank yang
tidak diperlukan. Salah satu dari tugas scanner atau lexical analyzer ini adalah untuk
mengabaikan blank yang dimaksud. Sebagai contoh adalah :
C=A + B
Maksud dari pernyataan di atas, adalah C = A + B.
Jika pernyataan semacam itu tidak diantisipasi oleh compiler maka pernyataan ini
tidak akan dapat dieksekusi, karena tidak dimengerti oleh compiler.
Berikut ini adalah program untuk menghilangkan blank.
Private Sub Form_Load()
c = InputBox("Masukkan Ekspresi:")
d = ""
flag = False
For i = 1 To Len(c)
If Mid(c, i, 1) = " " Then
If flag = False Then
d = d + Mid(c, i, 1)
End If
flag = True
Else
d = d + Mid(c, i, 1)
flag = False
End If
23

Next i
Debug.Print d
End Sub

Dengan menggunakan Bahasa Pascal :


uses crt;
var
ekspresi : String;
tampung:string;
i:integer;
flag:boolean;
begin
clrscr;
flag:=false;
write('Masukkan ekspresi:');
readln(ekspresi);
for i:=1 to length(ekspresi) do
begin
if ekspresi[i]=' 'then
begin
if flag=false then
tampung:=tampung+ekspresi[i];
flag:=true;
end
else
begin
tampung:=tampung+ekspresi[i];
flag:=false
end;
end;
writeln(tampung);
readln;
end.

Dengan menggunakan Bahasa C :


#include <stdio.h>
#include <conio.h>
#include <string.h>
void main()
{
24

clrscr();
char ekspresi[100];
char kalimat[100];
int kar;
int i;
int hitung;
int flag;
hitung=0;
flag=0;
printf("Masukkan Ekspresi:");
gets(ekspresi);
for(i=0;i<strlen(ekspresi);i++)
{
if (ekspresi[i]==' ')
{
if (flag==0)
{
kalimat[hitung]=ekspresi[i];
hitung=hitung+1;
}
flag=1;
}
else
{
kalimat[hitung]=ekspresi[i];
hitung=hitung+1;
flag=0;
}
}
for(i=0;i<hitung;i++)
printf("%c",kalimat[i]);
getch();
}

Pemakaian Procedure
1. Pada Pascal
Pada Pascal pengiriman parameter dapat dilakukan dengan dua cara yaitu :
a. Pengiriman parameter secara nilai
Jika nilai parameter pada prosedur diubah tidak akan mempengaruhi nilai
parameter nyata.
25

b. Pengiriman parameter secara acuan.


Jika nilai parameter pada prosedur diubah akan mempengaruhi nilai parameter
nyata.
Contoh pengiriman parameter secara nilai :
uses crt;
procedure hitung(a,b:integer);
var
c:integer;
begin
c:=a+b;
writeln('Nilai c = ',c);
end;
var
x,y:integer;
begin
write('Masukkan Nilai X :');
readln(x);
write('Masukkan Nilai Y :');
readln(y);
hitung(x,y);
readln;
end.

Contoh pengiriman parameter secara acuan :


uses crt;
procedure hitung(var a,b:integer);
var
c:integer;
begin
a:=10;
c:=a+b;
writeln('Nilai c = ',c);
end;
var
x,y:integer;
begin
write('Masukkan Nilai X :');
readln(x);
write('Masukkan Nilai Y :');
readln(y);
26

hitung(x,y);
writeln('Nilai variabel x=',x);
readln;
end.

2. Pada Visual Basic


Pada VB 6, ada 4 jenis procedure yaitu :
a. Procedure Sub - procedure yang tidak mengembalikan nilai setelah tugasnya
selesai. Sering disebut juga Procedure.
b. Procedure Function - Procedure yang mengembalikan nilai setelah tugasnya
selesai. Sering disebut juga Fungsi
c. Procedure Event - Procedure untuk sebuah event pada suatu object. Digunakan di
dalam Class Module.
d. Procedur Property - Procedure untuk mengubah (Let) dan mengambil (Get) nilai
property pada sebuah object. Digunakan di dalam Class Module.

Contoh pemakaian Procedure Sub :


Private Sub Form_Load()
a = InputBox("Masukkan Panjang:")
b = InputBox("Masukkan Lebar:")
Call hitung(Val(a), Val(b))
End Sub

Private Sub hitung(panjang As Integer, lebar As Integer)


luas = panjang * lebar
Debug.Print luas
End Sub

3. Pada Bahasa C
# include <stdio.h>
# include <conio.h>
void hitung(int panjang,int lebar);

void main()
{
int a,b;
clrscr();
printf("Masukkan Panjang :");
27

scanf("%i",&a);
printf("Masukkan Lebar:");
scanf("%i",&b);
hitung(a,b);
getch();
}

void hitung(int panjang,int lebar)


{
int luas;
luas=panjang*lebar;
printf("Luas = %i",luas);
}

Pemakaian Fungsi
Berikut ini adalah contoh pemakaian fungsi pada Turbo Pascal
1. Fungsi Tanpa parameter
uses crt;
Function garis:string;
begin
garis:='----------------';
end;
begin
writeln(garis);
writeln('Pascal');
writeln(garis);
readln;
end.

2. Fungsi dengan Parameter


uses crt;
function luas(panjang,lebar:integer):integer;
begin
luas:=panjang*lebar;
end;

var
p,l:integer;
begin
clrscr;
28

write('Masukkan Panjang :');


readln(p);
write('Masukkan Lebar :');
readln(l);
writeln('Luas=',luas(p,l));
readln;
end.

Pemakaian Fungsi pada Bahasa pemrograman Visual Basic


Private Sub Form_Load()
a = InputBox("Masukkan panjang :")
b = InputBox("Masukkan lebar:")
luas = luaspersegi(a, b)
Debug.Print luas
End Sub

Private Function luaspersegi(panjang, lebar)


luaspersegi = Val(panjang) * Val(lebar) End
Function

Pemakaian fungsi pada Bahasa C


# include <stdio.h>
# include <conio.h>
int hitung(int panjang,int lebar);
void main()
{
int a,b;
clrscr();
printf("Masukkan Panjang :");
scanf("%i",&a);
printf("Masukkan Lebar:");
scanf("%i",&b);
printf("Luas=%i",hitung(a,b));
getch();
}

int hitung(int panjang,int lebar)


{
int luas;
luas=panjang*lebar;
29

Token dan Lexemes


Untuk keperluan parsing, suatu pernyataan yang ada perlu dipisahkan menjadi token
dan lexemes. Ada sebagian pendapat yang menyamakan antara token dan lexemes
dengan hanya menggunakan istilah token saja. Namun, tidak jarang kita menemukan
pendapat yang membedakan antara token dengan lexemes ini. Secara umum, token
menyatakan suatu kelompok misalnya kelompok identifier, operator atau delimiter,
ataupun konstanta. Sedangkan lexemes menjelaskan anggota - anggota dari token
bersangkutan.

Berikut ini adalah program untuk Memisahkan suatu input menjadi bagian -
bagiannya :
Dengan menggunakan bahasa pascal :
uses crt;
var
Kalimat:string;
i,n:integer;
pos:array[1..100]of integer;
posisi:integer;
kar:array[1..100] of string;
token:array[1..100] of string;
karb:string;
begin
clrscr;
posisi:=1;
karb:='';
write('Masukkan sebuah kalimat:');
readln(kalimat);
kalimat:=kalimat+' ';
for i:=1 to length(kalimat) do
begin
if kalimat[i]<>' 'then
begin
karb:=karb+kalimat[i];
end
else if (kalimat[i]=' ') then
Begin
30

kar[posisi]:=karb;
karb:='';
posisi:=posisi+1;
end;

end;
for i:=1 to posisi-1 do
begin
write('Kata ke- ',i,' adalah ',kar[i]);
writeln;
end;
readln;
end.

Program untuk mengecek apakah input terdapat di dalam array identifier atau tidak.
Misal identifier itu terdiri dari kata If dan Then
Input yang dimasukkan adalah :
If nama= Anton then lakukan penyeleksian
Maka tampilan hasil program adalah sebagai berikut : If
termasuk identifier
Nama= bukan identifir
Anton bukan identifier
Then termasuk identifier
Lakukan bukan identifier
Penyeleksian bukan identifier.

Programnya adalah sebagai berikut :


uses crt;
var
Kalimat:string;
i,n,j,jiden,hitung:integer;
pos:array[1..100]of integer;
posisi:integer;
kar:array[1..100] of string;
iden:array[1..100] of string;
karb:string;
begin
clrscr;
31

posisi:=1;
hitung:=1;
karb:='';
write('Masukkan jumlah identifier:');
readln(jiden);
write('Masukkan sebuah kalimat:');
readln(kalimat);
kalimat:=kalimat+' ';
for i:=1 to length(kalimat) do
begin
if kalimat[i]<>' 'then
begin
karb:=karb+kalimat[i];
end
else if (kalimat[i]=' ') then
Begin
kar[posisi]:=karb;
karb:='';
posisi:=posisi+1;
end;

end;

writeln('Posisi=',posisi);
for i:=1 to jiden do
begin
write('Masukkan identifier:');
readln(iden[i]);
end;
for i:=1 to posisi-1 do
begin
for j:=1 to jiden do
begin
if kar[i]<>iden[j] then
begin
if hitung=jiden then
begin
writeln('Kata ',kar[i],' Bukan Termasuk
Identifier');
end;
hitung:=hitung+1;
32

end
else
begin
writeln('Kata ',kar[i],' Termasuk Identifier');
hitung:=1;
j:=jiden;
end;
end;
hitung:=1;
end;
readln;
end.

Pembuatan Unit
Sebelum kita mempelajari penggunaan unit, maka ada baiknya program yang udah
dibuat, kita jadikan menggunakan Function ataupun Procedure.

Pada soal sebelumnya untuk pemisahan suatu kalimat menjadi bagian - bagian
pembentuknya dapat dibuat menjadi sebuah procedure seperti yang tampak pada
program di bawah ini.

uses crt;
procedure pisah(var a:string);
var
i,n,posisi:integer;
kar,token:array[1..20] of string;
karb:string;
begin
posisi:=1;
karb:='';
a:=a+' ';

for i:=1 to length(a) do


begin
if a[i]<>' 'then
begin
karb:=karb+a[i];
end
else if (a[i]=' ') then
33

Begin
kar[posisi]:=karb;
karb:='';
posisi:=posisi+1;
end;
end;
for i:=1 to posisi-1 do
begin
write('Kata ke- ',i,' adalah ',kar[i]);
writeln;
end;
end;
var
Kalimat:string;
begin
clrscr;
write('Masukkan sebuah kalimat:');
readln(kalimat);
pisah(kalimat);
readln;
end.

Bila dibuat dalam bentuk unit menjadi.


unit mesin;
interface
procedure pisah(var a:string);
implementation
uses crt;
procedure pisah;
var
i,n,posisi:integer;
{pos:array[1..100]of integer;}
kar,token:array[1..20] of string;
karb:string;
begin
posisi:=1;
karb:='';
a:=a+' ';
for i:=1 to length(a) do
begin
34

if a[i]<>' 'then
begin
karb:=karb+a[i];
end
else if (a[i]=' ') then
Begin
kar[posisi]:=karb;
karb:='';
posisi:=posisi+1;
end;
end;
for i:=1 to posisi-1 do
begin
write('Kata ke- ',i,' adalah ',kar[i]);
writeln;
end;
end;
end.

Sedangkan programnya menjadi :


uses crt,mesin;
var
Kalimat:string;
begin
clrscr;
write('Masukkan sebuah kalimat:');
readln(kalimat);
pisah(kalimat);
readln;
end.

Analisis Sintaks
Sintaks adalah susunan kalimat dan aturan - aturan dalam membentuk kalimat disebut
grammar. Penganalisis sintaks dalam bidang kompilasi sering disebut dengan parser.

Aturan pendeklarasian variabel :


1. Samping kiri : pasti variabel
2. Samping kanan : pasti tipe data
3. Karakter paling kiri dari suatu variabel harus berupa huruf
35

4. Karakter selanjutnya harus berupa Huruf ataupun angka

Program untuk mengecek bagian paling kiri dari suatu variabel yang harus berupa
huruf.
uses crt;
var
variabel : String;
begin
clrscr;
write('Masukkan variabel:');
readln(variabel);
if ((ord(variabel[1])>=65) and (ord(variabel[1])<=91))
or((ord(variabel[1])>=97) and (ord(variabel[1])<=122)) then
writeln('Variabel Benar')
else
writeln('Karakter pertama harus berupa huruf');
readln;
end.

Program untuk mengecek karakter kedua dan seterusnya dari suatu variabel yang
harus berupa huruf
uses crt;
var
variabel : String;
posisi,i:integer;
flag:boolean;
begin
clrscr;
write('Masukkan variabel:');
readln(variabel);
flag:=true;
for i:=2 to length(variabel) do
begin
if variabel[i]=':' then
posisi:=i;
end;
for i:=2 to posisi-1 do
begin
36

if not(((ord(variabel[i])>=65) and (ord(variabel[i])<=91))


or((ord(variabel[i])>=97) and (ord(variabel[i])<=122)) or
((ord(variabel[i])>=48) and (ord(variabel[i])<=57))) then
flag:=false;
end;
if flag=false then
writeln('Ada kesalahan dengan variabel Anda')
else
writeln('Variabel sudah benar');
readln;
end.

Program untuk memisahkan tipe data dari suatu deklarasi variabel.


uses crt;
var
variabel : String;
tdata:string;
posisi,i:integer;
flag:boolean;
begin
clrscr;
write('Masukkan variabel:');
readln(variabel);

for i:=1 to length(variabel) do


begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=posisi+1 to length(variabel) do


tdata:=tdata+variabel[i];
writeln('Tipe data anda adalah :',tdata);
readln;
end.

Cara untuk mengetahui apakah tipe data yang kita masukkan merupakan tipe data
yang ada dalam suatu kompiler atau tidak.
uses crt;
var
37

variabel : String;
tdata:string;
tipe:array[1..100] of string;
posisi,i,jlh_tipe:integer;
flag:boolean;
begin
clrscr;
flag:=false;
write('Masukkan variabel:');
readln(variabel);
write('Masukkan tipe data yang dikenali:');
readln(jlh_tipe);
for i:=1 to jlh_tipe do
begin
write('Masukkan tipe data ke-[',i,']:');
readln(tipe[i]);
end;
for i:=1 to length(variabel) do
begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=posisi+1 to length(variabel) do


tdata:=tdata+variabel[i];
writeln('Tipe data anda adalah :',tdata);

for i:=1 to jlh_tipe do


begin
if tdata=tipe[i] then
flag:=true;
end;

if flag=true then
writeln('Tipe data yang anda masukkan yaitu ',tdata, ' Sudah
terdaftar')
else
writeln('Periksa kembali tipe data Anda yaitu ',tdata);
readln;
end.
38

Untuk perbandingan ada baiknya tipe data Anda terlebih dahulu dikonversi menjadi
huruf besar semua.
uses crt;
var
variabel : String;
tdata,tdatab,tampung,tampungb:string;
tipe,tipeb:array[1..100] of string;
posisi,i,jlh_tipe,j:integer;
flag:boolean;
begin
clrscr;
flag:=false;
write('Masukkan variabel:');
readln(variabel);
write('Masukkan tipe data yang dikenali:');
readln(jlh_tipe);
for i:=1 to jlh_tipe do
begin
write('Masukkan tipe data ke-[',i,']:');
readln(tipe[i]);
end;
for i:=1 to length(variabel) do
begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=posisi+1 to length(variabel) do


tdata:=tdata+variabel[i];

for i:=1 to length(tdata) do


tdatab:=tdatab+upcase(tdata[i]);
writeln('Tipe data anda adalah :',tdatab);

for i:=1 to jlh_tipe do


begin
tampung:=tampung+tipe[i];
for j:=1 to length(tampung) do
tampungb:=tampungb+upcase(tampung[j]);
tipeb[i]:=tampungb;
39

tampung:='';
tampungb:='';
end;
for i:=1 to jlh_tipe do
begin
writeln(tipeb[i]);
end;
for i:=1 to jlh_tipe do
begin
if tdatab=tipeb[i] then
flag:=true;
end;

if flag=true then
writeln('Tipe data yang anda masukkan yaitu ',tdata, ' Sudah
terdaftar')
else
writeln('Periksa kembali tipe data Anda yaitu ',tdata);
readln;
end.

Penggunaan File
Dalam perancangan suatu kompiler, sering digunakan suatu file untuk menyimpan
source code yang diketikkan oleh user. User mengetikkan program mereka kemudian
barulah program tersebut dikompilasi. Cara yang hampir mirip diterapkan pada
bahasa pemrograman Java. Pada bahasa pemrograman Pascal ada dua tipe teks yaitu :
1. File Teks
2. File Bertipe

Kedua jenis file ini mempunyai cara pemakaian yang berbeda. File bertipe lebih
mudah dipakai, namun kita tidak dapat mengetikkan source program secara langsung
pada suatu teks editor.

File Bertipe
File bertipe untuk memasukkan data :
Uses crt;
Type
Mahasiswa=record
40

Nomor : integer;
Nama: String;
Nilai: String;
End;
Var
FileMahasiswa:File of Mahasiswa;
RecordMahasiswa: Mahasiswa;
I,n:Byte;
Begin
Assign ( FileMahasiswa,'MHS.txt');
Rewrite ( FileMahasiswa );
Clrscr;
Write('Ketikkan Banyak Mahasiswa:');
Readln(n);
For i:= 1 to n do
Begin
Writeln('Mahasiswa ke-',i);
Write('Nomor:');
Readln(RecordMahasiswa.Nomor);
Write('Nama:');
Readln(RecordMahasiswa.Nama);
Write('Nilai:');
Readln(RecordMahasiswa.Nilai);
Write(FileMahasiswa,RecordMahasiswa);
Writeln;
End;
Close ( FileMahasiswa );
End.

File bertipe untuk menampilkan keseluruhan data :


uses crt;
type
mahasiswa=record
Nomor :integer;
nama : String;
Nilai : String;
end;
var
FileMahasiswa : File of Mahasiswa;
41

RecordMahasiswa : Mahasiswa;
i:integer;
begin
Assign (FileMahasiswa,'Mhs.txt');
reset(FileMahasiswa);
clrscr;
writeln('-----------------------------');
writeln('Nomor ');
writeln('Mhs Nama Mahasiswa Nilai');
writeln('-----------------------------');
while not eof(filemahasiswa) do
begin
read(FileMahasiswa,RecordMahasiswa);
with RecordMahasiswa do
writeln(Nomor:2,Nama:10,Nilai:14);
end;
writeln('------------------------------');
readln;
close(FileMahasiswa);
end.

File bertipe untuk menampilkan data tertentu


uses crt;
type
mahasiswa=record
Nomor :integer;
nama : String;
Nilai : String;
end;
var
FileMahasiswa : File of Mahasiswa;
RecordMahasiswa : Mahasiswa;
i,cari:integer;
ketemu:boolean;
begin
Assign (FileMahasiswa,'Mhs.txt');
reset(FileMahasiswa);
clrscr;
Write('Ketik no. mahasiswa yang ingin dibaca:');
Readln(cari);
while not eof(filemahasiswa) do
42

begin
read(filemahasiswa,recordmahasiswa);
if(recordmahasiswa.nomor=cari) then
begin
ketemu:=true;
writeln('nama Mahasiswa:',recordmahasiswa.nama);
writeln('Nilai Mahasiswa:',recordmahasiswa.nilai);
end;
end;
readln;
end.

File Teks
File Teks untuk memasukkan data:
Uses crt;
Var
BerkasTeks : Text;
KodeBrg : String;
NamaBrg : String;
UnitBrg : string;
HargaBrg:String;
lagi,jawab : char;
sudahada : Boolean;
Begin
Assign ( berkasteks,'Dataku.txt');
sudahada:=(ioresult=0);
if sudahada then
begin
jawab:=' ';
while not((jawab='Y') or (jawab='T')) do
begin
write(chr(7));
write('File sudah pernah ada, tumpangi
!!!!(Y/T) ?');
readln(Jawab);
jawab:=upcase(jawab);
end;
if jawab='T' then halt;
end;
rewrite(BerkasTeks);
43

lagi:='Y';

while upcase(lagi)='Y' do
begin
clrscr;
gotoxy(5,6);
write('Kode Barang :');
gotoxy(5,8);
write('Nama Barang :');
gotoxy(5,10);
write('Unit Barang:');
gotoxy(5,12);
write('Harga Satuan Barang :');

gotoxy(27,6); Readln(KodeBrg);
gotoxy(27,8); Readln(NamaBrg);
gotoxy(27,10); Readln(UnitBrg);
gotoxy(27,12); Readln(HargaBrg);

writeln(BerkasTeks,kodebrg);
writeln(BerkasTeks,namabrg);
writeln(BerkasTeks,unitbrg);
writeln(BerkasTeks,hargabrg);

gotoxy(5,15);
write('Ada Lagi?(Y/T)');
readln(lagi);
end;
close(berkasteks);
end.

End.

File teks untuk menampilkan semua data


Uses Crt;
Var
BerkasTeks : Text;
KodeBrg : string;
NamaBrg : string;
44

UnitBrg :string;
hargabrg:string;
I,n : byte;
Begin
Assign ( berkasteks,'Dataku.txt');
Reset ( berkasteks);
Clrscr;
Writeln('--------------------------------------------');
writeln(' Kode Unit harga
');
writeln(' Brg Nama Barang Akhir
Satuan');
writeln('--------------------------------------------
---------');
While not EOF ( berkasteks ) do
Begin
Readln(
berkasteks,kodebrg,namabrg,unitbrg,hargabrg);
write(kodeBrg,' ',namaBrg,'
',unitbrg,' ',hargabrg);
end;
close ( BerkasTeks );
readln;
end.

File teks untuk menampilkan data tertentu :


uses crt;
var
berkasteks:text;
kodebrg:string;
namabrg:string;
unitbrg:string;
hargabrg:string;
kodecari:string;
spasi:string;
lagi:char;
begin
assign(berkasteks,'Dataku.txt');
lagi:='Y';
while upcase(lagi)='Y' do
begin
45

reset(berkasteks);
clrscr;
write('Kode Barang dicari ?');
readln(kodecari);
writeln;
while(not eof(berkasteks)) and (kodebrg<>kodecari) do
readln(berkasteks,kodebrg);
readln(berkasteks,namabrg);
readln(berkasteks,unitbrg);
readln(berkasteks,hargabrg);

if kodebrg=kodecari then
begin
writeln('kode barang:',kodeBrg);
writeln('Nama barang:',namaBrg);
writeln('unit barang:',unitBrg);
writeln('harga barang:',hargaBrg);
end
else
writeln('Tidak ada data barang ini !!!');

close(berkasteks);
writeln;
writeln('Ada Lagi data yang akan dicari (Y/T)');
readln(lagi);
end;
readln;
end.

Perhatikan bahwa untuk mahasiswa.txt, hasil dari File bertipe berisi :


46

Dan hasil dari file teks (dataku.txt) berisi :


47

Soal :
Buatlah program untuk memisahkan pendeklarasian variabel yang jumlahnya lebih
dari satu.
Contoh : Panjang,lebar,luas:integer
Dipisahkan menjadi :
Variabel 1 : Panjang
Variabel 2 : Lebar
Variabel 3 : Luas
Jawab :
uses crt;
var
variabel : String;
tdata:string;
posisi,i:integer;
48

pkar:integer;
kar:array[1..100] of string;
karb:string;
begin
clrscr;
write('Masukkan variabel:');
readln(variabel);

for i:=1 to length(variabel) do


begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=1 to posisi-1 do


tdata:=tdata+variabel[i];
writeln(tdata);

tdata:=tdata+',';
pkar:=1;
karb:='';

for i:=1 to length(tdata) do


begin
if tdata[i]<>','then
begin
karb:=karb+tdata[i];
end
else if (tdata[i]=',') then
Begin
kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;

end;
for i:=1 to pkar-1 do
begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
49

readln;
end.

Pemakaian Procedure
uses crt;
procedure cek(tdata:string);
var
i:integer;
pkar:integer;
kar:array[1..20] of string;
karb:string;
begin
tdata:=tdata+',';
pkar:=1;
karb:='';

for i:=1 to length(tdata) do


begin
if tdata[i]<>','then
begin
karb:=karb+tdata[i];
end
else if (tdata[i]=',') then
Begin
kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;

end;
for i:=1 to pkar-1 do
begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
end;
var
variabel : String;
i,posisi:integer;
tdata:string;
50

begin
clrscr;
write('Masukkan variabel:');
readln(variabel);
for i:=1 to length(variabel) do
begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=1 to posisi-1 do


tdata:=tdata+variabel[i];
cek(tdata);
readln;
end.

Pemakaian Unit
Unit kompilasi.pas
unit kompilasi;

interface
procedure cek(tdata:string);
implementation
uses crt;
procedure cek(tdata:string);
var
i:integer;
pkar:integer;
kar:array[1..20] of string;
karb:string;
begin
tdata:=tdata+',';
pkar:=1;
karb:='';

for i:=1 to length(tdata) do


begin
if tdata[i]<>','then
begin
karb:=karb+tdata[i];
51

end
else if (tdata[i]=',') then
Begin
kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;

end;
for i:=1 to pkar-1 do
begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
end;
end.

Program Cek.pas
uses kompilasi,crt;

var
variabel : String;
i,posisi:integer;
tdata:string;
begin
clrscr;
write('Masukkan variabel:');
readln(variabel);
for i:=1 to length(variabel) do
begin
if variabel[i]=':' then
posisi:=i;
end;

for i:=1 to posisi-1 do


tdata:=tdata+variabel[i];
cek(tdata);
readln;
end.
52

Aturan Pendeklarasian Konstanta


Konstanta adalah suatu tempat untuk menampung nilai di mana nilai yang ditampung
adalah tetap dan tidak dapat berubah. Secara umum bentuk pendeklarasian variabel
pada suatu konstanta adalah dituliskan sebagai :
Konstanta = Nilai
Contoh :
Panjang = 1
Nama = Hartono
Jadi, pada suatu konstanta untuk nilai selain angka maka harus diapit dengan tanda
petik ganda.
Program untuk memisahkan nama konstanta dari nilai konstanta.
uses crt;
var
kons : String;
konstanta:string;
posisi,i:integer;
flag:boolean;
begin
clrscr;
write('Masukkan deklarasi konstanta:');
readln(kons);

for i:=1 to length(kons) do


begin
if kons[i]='=' then
posisi:=i;
end;

for i:=1 to posisi-1 do


konstanta:=konstanta+kons[i];
writeln('Nama konstanta adalah :',konstanta);
readln;
end.

Program untuk memisahkan nilai konstanta dari nama konstanta.


uses crt;
var
kons : String;
53

nkonstanta:string;
posisi,i:integer;
flag:boolean;
begin
clrscr;
write('Masukkan deklarasi konstanta:');
readln(kons);

for i:=1 to length(kons) do


begin
if kons[i]='=' then
posisi:=i;
end;

for i:=posisi+1 to length(kons) do


nkonstanta:=nkonstanta+kons[i];
writeln('Nilai konstanta adalah :',nkonstanta);
readln;
end.

Program untuk mengecek kebenaran nama konstanta yang dimasukkan.


uses crt;
var
kons : String;
nkonstanta:string;
posisi,i:integer;
flag:boolean;
str:boolean;
begin
clrscr;
flag:=true;
write('Masukkan deklarasi konstanta:');
readln(kons);

for i:=1 to length(kons) do


begin
if kons[i]='=' then
posisi:=i;
end;
54

for i:=posisi+1 to length(kons) do


nkonstanta:=nkonstanta+kons[i];
writeln('Nilai konstanta adalah :',nkonstanta);
for i:=1 to length(nkonstanta) do
begin
if ((ord(nkonstanta[i])>=48) and (ord(nkonstanta[i])<=57)) then
str:=false
else
str:=true;
end;
if str=true then
begin
if ((ord(nkonstanta[1])=39) and
(ord(nkonstanta[length(nkonstanta)])=39)) then
flag:=true
else
flag:=false;
end;
if flag=false then
writeln('konstanta salah')
else
writeln('konstanta sudah benar');
readln;
end.

uses crt;
var
kons : String;
nkonstanta:string;
constan:string;
posisi,i:integer;
flag:boolean;
str:boolean;
begin
clrscr;
flag:=true;
constan:='';
write('Masukkan deklarasi konstanta:');
readln(kons);
55

for i:=1 to length(kons) do


begin
if kons[i]='=' then
posisi:=i;
end;

for i:=posisi+1 to length(kons) do


nkonstanta:=nkonstanta+kons[i];

for i:=1 to length(nkonstanta) do


begin
if ((ord(nkonstanta[i])>=48) and (ord(nkonstanta[i])<=57)) then
str:=false
else
str:=true;
end;
if str=true then
begin
for i:=1 to length(nkonstanta) do
begin
if (ord(nkonstanta[i])<>39) then
constan:=constan+nkonstanta[i]
end;
end;

if str=true then
begin
writeln('Nilai konstanta adalah :',constan);
if ((ord(nkonstanta[1])=39) and
(ord(nkonstanta[length(nkonstanta)])=39)) then
flag:=true
else
flag:=false;
end;

if flag=false then
writeln('konstanta salah')
else
writeln('konstanta sudah benar');
readln;
56

end.

Type Checking
Kompiler harus memeriksa apakah source program mengikuti konvensi sintaksis atau
semantik dari source language. Pemeriksaan ini disebut static checking, untuk
meyakinkan bahwa kesalahan programming akan dideteksi dan dilaporkan.

Static Checking : Checking yang dilakukan oleh kompiler


Dynamic Checking : Checking yang dilakukan oleh target program

Posisi Type Checking dalam kompiler :

Intermediate
Token Syntax
Parser Type Code
Checker Generator

Analisis Leksikal dan Sintaksis dengan File


Pada bagian ini kita akan melihat bagaimana imnplementasi dari file pada
perancangan suatu kompiler. Di sini peran dari file adalah untuk menyimpan source
code, menyimpan tipe data yang dikenali, menyimpan nama variabel, nama konstanta,
dan lain - lain.

Misalkan pada kompiler yang kita rancang mempunyai kemampuan untuk mengenali
tipe data :
1. Char
2. String
3. Integer dengan jangkauan dari -32768 s/d 32767
4. LongInt dengan jangkauan dari -2147483648 s/d 2147483647
5. Real untuk bilangan desimal

Berikut ini adalah contoh penggunaan dari file untuk menyimpan tipe data yang kita
kenali pada suatu file. Langkah - langkahnya adalah sebagai berikut.
57

1. Buat program untuk membentuk file dengan nama tdata.dat untuk menyimpan tipe
data yang kita kenali
2. Buat program untuk menyimpan tipe data beserta dengan jangkauannya ke dalam
file tdata.dat yang telah kita buat sebelumnya.

Program untuk membentuk file tdata.dat


Uses crt;
Var
VF:text;
Begin
Assign ( VF,'C:\tdata.dat');
Rewrite ( VF );
Close ( VF );
End.

Program untuk menyimpan tipe data.


Uses crt;
Var
BerkasTeks : Text;
tipe : String;
tipeb: string;
jangkauan : String;
lagi,jawab : char;
sudahada : Boolean;
i:integer;
Begin
Assign ( berkasteks,'C:\tdata.dat');
rewrite(BerkasTeks);
lagi:='Y';

while upcase(lagi)='Y' do
begin
clrscr;
gotoxy(5,6);
write('Tipe Data :');
gotoxy(5,8);
write('Jangkauan :');

gotoxy(27,6); Readln(tipe);
58

gotoxy(27,8); Readln(jangkauan);

for i:=1 to length(tipe) do


tipeb:=tipeb+upcase(tipe[i]);

writeln(BerkasTeks,tipeb);
writeln(BerkasTeks,jangkauan);
tipeb:=;

gotoxy(5,15);
write('Ada Lagi?(Y/T)');
readln(lagi);
end;
close(berkasteks);
end.

Menyimpan reserved word


Pada setiap bahasa pemrograman tentu ada reserved word (kata tercadang), kata
tercadang itu tidak dapat kita gunakan sebagai nama variabel. Kata tercadang itu
masing - masing mempunyai kegunaan seperti : for untuk perulangan, var untuk
59

pendeklarasian variabel, dan lain - lain. Oleh karena itu, juga ada baiknya kalau kata
tercadang itu disimpan di dalam suatu file yang digunakan khusus untuk menampung
reserved word, misalkan nama file yang dimaksud adalah cadang.dat.

Program untuk membuat file cadang.dat


Uses crt;
Var
VF:text;
Begin
Assign ( VF,'C:\cadang.dat');
Rewrite ( VF );
Close ( VF );
End.

Program untuk mengetikkan reserved word ke dalam file.


Uses crt;
Var
BerkasTeks : Text;
cadang : String;
cadangb: string;
lagi,jawab : char;
sudahada : Boolean;
Begin
Assign ( berkasteks,'C:\cadangan.dat');
rewrite(BerkasTeks);
lagi:='Y';

while upcase(lagi)='Y' do
begin
clrscr;
gotoxy(5,6);
write('Reserved Word :');
gotoxy(27,6); Readln(cadang);

for i:=1 to length(cadang) do


cadangb:=cadangb+upcase(cadang[i]);

writeln(BerkasTeks,cadangb);

cadangb:='';
60

gotoxy(5,15);
write('Ada Lagi?(Y/T)');
readln(lagi);
end;
close(berkasteks);
end.

Menyimpan variabel
Variabel di dalam perancangan suatu kompiler sering dianggap sebagai bagian di
dalam suatu program, atau dengan kata lain tidak diperlukan upaya untuk menyimpan
variabel tersebut ke dalam suatu file. Namun, untuk efisiensi di dalam program, ada
baiknya variabel tersebut di tempatkan ke dalam suatu file sehingga upaya untuk
mengeceknya dapat menjadi lebih mudah, terutama apabila variabel tersebut sering
digunakan di dalam program.

Berikut ini adalah contoh program untuk membuat file variabel.dat untuk menyimpan
nama variabel.
Uses crt;
Var
VF:text;
Begin
Assign ( VF,'C:\variabel.dat');
Rewrite ( VF );
Close ( VF );
End.

Mengecek kebenaran pendeklarasian variabel pada suatu File


Misalkan program yang diketik pada suatu teks editor adalah sebagai berikut.
Vari
Panjang,lebar,luas:integer;
end vari

Maka yang perlu diperhatikan adalah sebagai berikut.


1. Harus ada keyword vari
2. Cek pengetikan deklarasi variabel
61

a. Cek tipe data yang ada apakah sudah sesuai dengan tipe data yang dikenali
pada program atau tidak
b. Cek apakah pada pengetikan deklarasi variabel sudah ada titik koma ( ; ) atau
tidak
c. Cek pengetikan variabel dengan kriteria :
- karakter pertama pada nama variabel harus berupa huruf
- nama variabel tidak boleh sama dengan reserved word
- panjang karakter maksimal adalah 32 karakter
- huruf kedua dan selanjutnya pada nama variabel harus berupa huruf
ataupun angka.

Berikut ini adalah program untuk menampilkan kembali isi source code yang telah
diketikkan dalam suatu array.
Uses Crt;
Var
BerkasTeks : Text;
kode:string;
arkode : array [1..100] of string; I,n
: byte;
Begin
n:=1;
i:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
writeln(kode);
arkode[i]:=kode;
n:=n+1;
i:=i+1;
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
62

writeln('isi kode baris - ',i,' adalah :


',arkode[i]);
end;
readln;
end.

Program untuk mengecek apakah pendeklarasian variabel terdapat keyword vari dan
tanda ; atau tidak.
Uses Crt;
Var
BerkasTeks : Text;
kode:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
cekvar:string;
flag:boolean; {menampung status ;}
Begin
n:=1;
i:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );
63

for i:=1 to n-1 do


begin
if arkode[i]='VARI' then
posisi1:=i;
if arkode[i]='END VARI' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
if (cekvar[length(cekvar)]=';') and (flag=true) then
flag:=true;
if (cekvar[length(cekvar)]<>';') and (flag=true) then
begin
flag:=false;
possalah:=i;
end;
cekvar:='';
end;
if flag=true then
writeln('ada titik koma')
else
writeln('tidak ada titik koma pada baris ke-',possalah);
readln;
end.

Berikut ini adalah program untuk memisahkan variabel yang sudah kita definisikan di
dalam file.
Uses Crt;
Var
BerkasTeks : Text;
kode,tvari,karb:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
l,I,o,n,j,posisi1,posisi2,pkar,k : byte;
cekvar:string;
variabel1:string; {untuk menampung bagian dklarasi variabel}
posisi:integer;
64

arvari:array[1..25] of string;
kar:array[1..25] of string;
vari:array[1..25] of string;
Begin
n:=1;
i:=1;
k:=1;
o:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='VARI' then
posisi1:=i;
if arkode[i]='END VARI' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to length(cekvar) do
begin
if cekvar[j]=':' then
posisi:=j;
end;

for j:=1 to posisi-1 do


65

variabel1:=variabel1+cekvar[j];
arvari[o]:=variabel1;
variabel1:='';
o:=o+1;
end;

pkar:=1;
karb:='';
l:=1;
for i:=1 to o-1 do
begin
tvari:=tvari+arvari[i];
tvari:=tvari+',';
end;
writeln(tvari);

for j:=1 to length(tvari) do


begin
if tvari[j]<>','then
begin
karb:=karb+tvari[j];
end
else if (tvari[j]=',') then
Begin
kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;
end;

for i:=1 to pkar-1 do


begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;

readln;
end.
66

Berikut ini adalah program untuk mengecek apakah variabel yang digunakan oleh user
sudah dideklarasikan atau belum.
Uses Crt;
Var
BerkasTeks : Text;
kode,tvari,karb:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
l,I,o,n,j,posisi1,posisi2,pkar,k : byte;
cekvar:string;
variabel1:string; {untuk menampung bagian dklarasi variabel}
posisi:integer;

arvari:array[1..25] of string;
kar:array[1..25] of string;
vari:array[1..25] of string;
flag:boolean;
Begin
n:=1;
i:=1;
k:=1;
flag:=true;
o:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );
67

for i:=1 to n-1 do


begin
if arkode[i]='VARI' then
posisi1:=i;
if arkode[i]='END VARI' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to length(cekvar) do
begin
if cekvar[j]=':' then
posisi:=j;
end;

for j:=1 to posisi-1 do


variabel1:=variabel1+cekvar[j];
arvari[o]:=variabel1;
variabel1:='';
o:=o+1;
end;

pkar:=1;
karb:='';
l:=1;
for i:=1 to o-1 do
begin
tvari:=tvari+arvari[i];
tvari:=tvari+',';
end;
writeln(tvari);

for j:=1 to length(tvari) do


begin
if tvari[j]<>','then
begin
karb:=karb+tvari[j];
end
else if (tvari[j]=',') then
Begin
68

kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;
end;

for i:=1 to pkar-1 do


begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
posisi1:=0;
posisi2:=0;
for i:=1 to n-1 do
begin
if arkode[i]='PROGRAM' then
posisi1:=i;
if arkode[i]='END PROGRAM' then
posisi2:=i;
end;
cekvar:='';
o:=0;
for i:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to pkar-1 do
begin
if (cekvar=kar[j])then
o:=o+1;
end;
writeln(cekvar);

end;
if o=((posisi2-1)-(posisi1+1)+1) then
writeln('semua variabel dikenal')
else
writeln('Ada variabel yang tidak dikenal');

readln;
end.
69

Berikut ini adalah program untuk mengecek apakah nama suatu variabel sama dengan
Reserved Word atau tidak.
Uses Crt;
Var
BerkasTeks : Text;
kode,tvari,karb:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
l,I,o,n,j,posisi1,posisi2,pkar,k : byte;
cekvar:string;
variabel1:string; {untuk menampung bagian dklarasi variabel}
posisi:integer;

arvari:array[1..25] of string;
kar:array[1..25] of string;
vari:array[1..25] of string;
flag:boolean;
Begin
n:=1;
i:=1;
k:=1;
o:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


70

begin
if arkode[i]='VARI' then
posisi1:=i;
if arkode[i]='END VARI' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to length(cekvar) do
begin
if cekvar[j]=':' then
posisi:=j;
end;

for j:=1 to posisi-1 do


variabel1:=variabel1+cekvar[j];
arvari[o]:=variabel1;
variabel1:='';
o:=o+1;
end;

pkar:=1;
karb:='';
l:=1;
for i:=1 to o-1 do
begin
tvari:=tvari+arvari[i];
tvari:=tvari+',';
end;
writeln(tvari);

for j:=1 to length(tvari) do


begin
if tvari[j]<>','then
begin
karb:=karb+tvari[j];
end
else if (tvari[j]=',') then
Begin
kar[pkar]:=karb;
71

karb:='';
pkar:=pkar+1;
end;
end;

for i:=1 to pkar-1 do


begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
Assign ( berkasteks,'c:\cadang.dat');
Reset ( berkasteks);
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for i:=1 to pkar-1 do
begin
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
if kar[i]=kodeb then
flag:=true;
kodeb:='';
end;
end;
if flag=true then
writeln('nama variabel tidak boleh sama dengan reserved
word')
else
writeln('Nama variabel sudah benar');

readln;
end.

Berikut ini adalah perancangan compiler untuk mengecek keberadaan komentar pada
suatu program (untuk yang lebih 1 baris).
Uses Crt;
Var
BerkasTeks : Text;
kode:string; {untuk menampung kode}
72

kodeb:string; {untuk menampung huruf besar dari kode}


arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
cekvar:string;
flag:boolean; {menampung status ;}
Begin
n:=1;
i:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='{' then
posisi1:=i;
if arkode[i]='}' then
posisi2:=i;
end;
writeln('Komentar yang Anda masukkan adalah:');
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
writeln(cekvar);
end;
73

readln;
end.

Pada compiler yang kita rancang nantinya, maka apabila telah dibuat tanda {, harus
diakhiri dengan tanda }, karena jika tidak akan ditampilkan pesan kesalahan seperti yang
tampak pada contoh berikut.
Berikut ini adalah program untuk mengecek kesalahan akibat kurangnya tanda tutup
kurung kurawal (}).
Uses Crt;
Var
BerkasTeks : Text;
kode:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
cekvar:string;
flag:boolean; {menampung status ;}
Begin
posisi1:=0;
posisi2:=0;
n:=1;
i:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;
74

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='{' then
posisi1:=i;
if arkode[i]='}' then
posisi2:=i;
end;
if (posisi1=0) or (posisi2=0) then
writeln('Perhatikan tanda { atau } yang anda
deklarasikan')
else
begin
writeln('Komentar yang Anda masukkan adalah:');
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
writeln(cekvar);
end;
end;
readln;
end.

Berikut ini adalah program untuk mengecek komentar yang hanya 1 baris (bisa
melekat pada source code). Dalam hal ini ditandai dengan *
Uses Crt;
Var
BerkasTeks : Text;
kode:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
cekvar:string;
flag:boolean; {menampung status ;}
Begin
n:=1;
75

i:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

kodeb:='';
posisi1:=1;
posisi2:=1;
for i:=1 to n-1 do
begin
kodeb:=arkode[i];
for j:=1 to length(kodeb) do
begin
if kodeb[j]='*' then
begin
posisi1:=j;
posisi2:=i;
end;
end;
end;
kodeb:='';
kodeb:=arkode[posisi2];
write('Isi komentar anda adalah: ');
for i:=posisi1+1 to length(kodeb) do
write(kodeb[i]);

readln;
end.
76

Berikut ini adalah program untuk menghilangkan spasi kosong pada bagian sebelah kiri
program.
Uses Crt;
Var
BerkasTeks : Text;
kode:string;
arkode : array [1..100] of string;
I,n,k,posisi: byte;
tampung:string;
kode1:string;
arkode1:array[1..100] of string;
flag:boolean;
Begin
n:=1;
i:=1;
flag:=false;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
arkode[i]:=kode;
n:=n+1;
i:=i+1;
end;
for i:=1 to n-1 do
begin
kode1:=arkode[i];
if kode1[1]=' 'then
begin
for k:=1 to length(kode1) do
begin
if ((kode1[k]<>' ') and (flag=false))
then
begin
posisi:=k;
flag:=true;
end;
end;
77

flag:=false;
for k:=posisi to length(kode1) do
begin
tampung:=tampung+kode1[k];
end;
end
else
begin
for k:=1 to length(kode1) do
begin
tampung:=tampung+kode1[k];
end;
end;
arkode1[i]:=tampung;
tampung:='';
kode1:='';
end;
for i:=1 to n-1 do
begin
writeln('isi kode baris ke -',i, ' adalah : ',arkode1[i]);
end;
close ( BerkasTeks );
readln;
end.

Selain proses penghilangan spasi di bagian kiri, terkadang ada bagian tertentu di
dalam program yang tidak mengizinkan adanya spasi, seperti bagian program yang ada
di dalam blok Vari dan End Vari.
Berikut ini adalah program untuk menghilangkan keseluruhan spasi yang ada di dalam
blok Vari dan End Vari.

Tabel Informasi
Tabel infromasi atau tabel simbol dibuat guna mempermudah pembuatan dan
implementasi dari semantyc analyzer. Tabel simbol ini mempunyai dua fungsi penting
dalam proses translasi, yaitu :
1. Untuk membantu pemeriksaaan kebenaran semantik dari program sumber.
2. Untuk membantu dan mempermudah dalam pembuatan intermediate code dan
proses pembangkitan kode.
78

Hal tersebut dilakukan dengan menambah dan mengambil atribut variabel yang
dipergunakan pada program dari tabel. Atribut tersebut, seperti nama, tipe, ukuran
variabel bisa ditemukan secara eksplisit pada deklarasi, atau secara implisit
berdasarkan konteks kemunculan nama variabel pada program.

Beberapa jenis dari tabel informasi adalah sebagai berikut.


1. Tabel identifier : berfungsi menampung semua identifier yang terdapat dalam
program. Identifier yang dimaksud dapat berupa prosedur, fungsi, tipe, variabel, dan
konstanta.
2. Tabel Array : Berfungsi untuk menampung informasi tambahan untuk sebuah
array. Tabel Array memiliki Field :
- Tipe elemen Array
- Indeks batas atas array
- Indeks batas bawah array
3. Tabel Blok : Mencatat variabel - variabel yang ada pada blok yang sama
Variabel yang dimaksud termasuk variabel pada blok atau procedure maupun
parameter pada suatu blok atau procedure.
Contoh :
Program A;
Var B:Integer;
Procedure X (Z:Char);
Var C:Integer;
Begin
Maka untuk blok program A
Variabel yang ada adalah B dengan tipe data integer

Sedangkan untuk blok procedure X


Parameter yang ada adalah Z dengan tipe data Char
Variabel yang ada adalah C dengan tipe data integer
4. Tabel Real : Menyimpan elemen tabel yang bernilai Real
5. Tabel String : Menyimpan informasi String
6. Tabel Display : Mencatat Blok yang aktif.
79

Berikut ini adalah contoh untuk mengisikan suatu variabel ke dalam tabel Identifier.
(Catatan : dalam implementasi pengisian tabel identifier bisa diisikan gabung, apakah itu
variabel, konstanta, dll, ataupun diisikan pisah, seperti tabel identifier khusus untuk
variabel, konstanta, dll)

Uses Crt;
Var
BerkasTeks : Text;
teks:text;
kode,tvari,karb:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
l,I,o,n,j,posisi1,posisi2,pkar,k : byte;
cekvar:string;
variabel1:string; {untuk menampung bagian dklarasi variabel}
posisi:integer;

arvari:array[1..25] of string;
kar:array[1..25] of string;
vari:array[1..25] of string;
Begin
n:=1;
i:=1;
k:=1;
o:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;
80

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='VARI' then
posisi1:=i;
if arkode[i]='END VARI' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to length(cekvar) do
begin
if cekvar[j]=':' then
posisi:=j;
end;

for j:=1 to posisi-1 do


variabel1:=variabel1+cekvar[j];
arvari[o]:=variabel1;
variabel1:='';
o:=o+1;
end;

pkar:=1;
karb:='';
l:=1;
for i:=1 to o-1 do
begin
tvari:=tvari+arvari[i];
tvari:=tvari+',';
end;
writeln(tvari);

for j:=1 to length(tvari) do


begin
if tvari[j]<>','then
begin
karb:=karb+tvari[j];
end
81

else if (tvari[j]=',') then


Begin
kar[pkar]:=karb;
karb:='';
pkar:=pkar+1;
end;
end;

for i:=1 to pkar-1 do


begin
write('variabel ke- ',i,' adalah ',kar[i]);
writeln;
end;
karb:='';
Assign ( teks,'C:\tabel.dat');
rewrite(teks);
for i:=1 to pkar-1 do
begin
karb:=kar[i];
writeln(teks,karb);
karb:='';
end;
close(teks);
readln;
end.

Teknik Optimasi
Tahapan optimasi kode bertujuan untuk menghasilkan kode program yang berukuran
lebih kecil dan lebih cepat eksekusinya. Berdasarkan ketergantungannya pada mesin,
optimasi dibagi menjadi :
1. Machine Dependent Optimizer
Kode dioptimasi sehingga lebih efisien pada mesin tertentu. Optimasi ini
memerlukan informasi mengenai feature yang ada pada mesin tujuan dan
mengambil keuntungan darinya untuk menghasilkan kode yang lebih pendek atau
dieksekusi lebih cepat.
2. Machine Independent Optimizer
Strategi optimasi yang bisa diaplikasikan tanpa tergantung pada mesin tujuan
tempat kode yang dihasilkan akan disekusi nantinya. Bagian ini selanjutnya akan
82

membahas optimasi Machine Independent yang meliputi optimasi lokal dan


optimasi global.

Optimasai Lokal
Optimasi lokal adalah optimasi yang dilakukan hanya pada suatu blok dari source
code, cara - caranya adalah :
1. Folding
Mengganti konstanta atau ekspresi yang bisa dievaluasi pada saat Compile Time
dengan nilai komputasinya. Misalkan instruksi :
A := 2 + 3 + B
Bisa diganti menjadi :
A := 5 + B
Di situ 5 menggantikan ekspresi 2+3
2. Redundant - Subexpression Elimination
Sebuah ekspresi yang sudah pernah dikomputasi, digunakan lagi hasilnya,
ketimbang melakukan komputasi ulang. Misalkan terdapat urutan instruksi :
A := B + C
X := Y + B + C
Kemunculan kedua dari B+C yang redundan bisa diatasi dengan memanfaatkan
hasil komputasinya yang sudah ada pada instruksi sebelumnya. Perhatikan, hal ini
bisa dilakukan dengan catatan belum ada perubahan pada variabel yang berkaitan. 3.
Optimasi dalam sebuah iterasi
Loop Unrolling : Menggantikan suatu loop dengan menulis statement dalam
loop beberapa kali. Hal ini didasari pemikiran, sebuah iterasi pada
implementasi level rendah akan memerlukan operasi :
Inisialisasi / pemberian nilai awal pada variabel loop. Dilakukan sekali
pada saat permulaan eksekusi loop.
Pengetesan, apakah variabel loop telah mencapai kondisi terminasi
Adjustment, yaitu penambahan atau pengurangan nilai pada variabel loop
dengan jumlah tertentu.
Operasi yang terjadi pada tubuh perulangan (Loop Body).

Dalam setiap perulangan akan terjadi pengetesan dan adjustment yang


menambah waktu eksekusi. Contoh pada instruksi :
83

For I := 1 to 2 do
A [I] := 0;
Terdapat instruksi untuk inisialisasi I menjadi 1. Serta operasi penambahan
nilai / Increment 1 dan pengecekan nilai pada variabel I pada setiap
perulangan. Sehingga untuk perulangan saja memerlukan empat instruksi,
ditambah dengan instruksi assignment pada tubuh perkukangan.
Dapat dioptimasikan menjadi :
A[1]:=0;
A[2]:=0;

Yang hanya memelrukan dua instruksi assignment saja. Untuk menentukan


optimasi ini perlu dilihat perbandingan kasusnya dengan tanpa melakukan
optimasi.
Frequency Reduction : Pemindahan statement ke tempat yang lebih jarang
dieksekusi. Contoh :
For I := 1 to 10 do
Begin
X:=5;
A:=A+I;
End;

Kita lihat tidak terjadi perubahan / manipulasi pada variabel X di dalam iterasi,
karena itu kita bisa mengeluarkan instruksi tersebut ke luar iterasi, menjadi :
X := 5;
For I := 1 to 10 do
Begin
A:=A+I;
End;

4. Strength Reduction
Penggantian suatu operasi dengan jenis operasi lain yang lebih cepat dieksekusi.
Misalkan pada beberapa komputer operasi perkalian memerlukan waktu lebih
banyak untuk dieksekusi dari pada operasi penjumlahan, maka penghematan
waktu bisa dilakukan dengan mengganti operasi perkalian tertentu dengan
penjumlahan. Contoh lain, instruksi :
A := A+1;
Dapat digantikan dengan :
84

Inc (A);

Optimasi Global
Di sini hanya akan diterangkan sekilas mengenai optimasi global. Optimasi global
biasanya dilakukan dengan analisis Flow, yaitu suatu graph berarah yang
menunjukkan jaluar yang mungkin selama eksekusi program.

Kegunaannya :
a. Bagi pemrogram menginformasikan :
Unreachable / Dead Code : Kode yang tidak akan pernah dieksekusi.
Misalnya terdapat pada urutan instruksi :
X := 5;
If X = 0 Then
A:= A+1;
Instruksi A := A+1 tidak akan pernah dieksekusi
Unuser Parameter pada prosedur : Parameter yang tidak pernah digunakan di
dalam prosedur. Contohnya :
Procedure Jumlah (a,b,c:Integer);
Var X : Integer
Begin
X:=a+b;
End;
Kita lihat parameter c tidak pernah digunakan di dalam prosedur, sehingga
seharusnya tidak perlu diikutsertakan.
Unuser Variabel : Variabel yang tidak pernah dipakai dalam program.
Contohnya :
Program pendek;
Var a,b : Integer;
Begin
A:=5;
End;
Variabel yang dipakai tanpa nilai awal. Contohnya :
Program Awal;
Var a,b : Integer;
Begin
a:=5;
a:=a+b;
85

end;
Kita lihat variabel b digunakan tanpa memiliki nilai awal / belum di-assign
b. Bagi kompilator :
Meningkatkan efisiensi eksekusi program
Menghilangkan useless code / kode yang tidak terpakai.

Latihan :
1. Lakukan optimisasi lokal yang diperlukan pada potongan program berikut, dan
jelaskan optimasi apa saja yang diterapkan :
A := B + 10 * 4
C := B + D;
F := B + D - G;
For I := 1 to 100 do
Begin
X := X+I;
A := A+X;
B := 7;
End;
2. Apakah kita dapat melakukan optimasi Redundant Sub Expression Elimination
pada statement berikut, mengapa ?
a.
A := B + C;
A := X + Y;
F := B + C + G + H;
b.
A := B + C;
B := X + Y;
F := B + C + G + H;
3. Bisakah kita melakukan optimasi frequency reduction pada loop berikut :
10 For I := 1 to 10 do
20 A := I+1;
30
Mengapa kita tidak dapat melakukan optimasi pada instruksi baris ke 20 ? 4.
Lakukan optimasi global sederhana pada program berikut.
Program Test;
Var A, B, C : Integer;
Begin
B := 5;
86

While B < 3 do
B := B+1;
C := 10+B;
End.

Jawaban :
1.
A := B + 10 * 4 A := B + 40 (Folding)
C := B + D; C := B + D
F := B + D - G; F := C - G (Redundant Sub Expression
Elimination)
For I := 1 to 100 do B := 7;
Begin For I := 1 to 100 do
X := X+I; Begin
A := A+X; X := X + I;
B := 7; A := A + X;
End; End; (Frequency Reduction)

2.
a. Tidak bisa karena A sudah bukan B + C lagi (X + Y)
b. Tidak bisa karena nilai B sudah berubah

3.
Tidak bisa karena nilai A selalu berubah seiring berubahnya nilai I
4.
Hilangkan saja variabel A, karena variabel A tidak pernah digunakan.

Analisa Semantik (Semantic Analyzer)


Analisa semantik pada hakekatnya berfungsi untuk menentukan makna dari
serangkaian instruksi yang terdapat dalam program sumber, sebagai contoh untuk
mengenali kegunaan fungsi writeln yang digunakan untuk mencetak tulisan.
Untuk bisa mengetahui maknanya, rutin ini mungkin akan melakukan :
1. Memisahkan tiap instruksi yang terdapat dalam fungsi dalam suatu kumpulan
program
87

2. Apakah fungsi yang ada merupakan fungsi yang dikenali atau tidak dalam suatu
compiler. Oleh karena itu, biasanya dilakukan pengecekan terhadap file reserved
word yang ada di dalam suatu compiler.
3. Berdasarkan hasil pengecekan tersebut kemudian akan dilakukan pengecekan
terhadap fungsi instruksi yang dimaksud.

Berikut ini adalah contoh program untuk semantic analyzer.


Uses Crt;
Var
BerkasTeks : Text;
kode,tvari,karb:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
l,I,o,n,j,posisi1,posisi2,pkar,k : byte;
cekvar:string;
variabel1:string; {untuk menampung bagian dklarasi variabel}
posisi:integer;

arvari:array[1..25] of string;
kar:array[1..25] of string;
vari:array[1..25] of string;
flag:boolean;
Begin
n:=1;
i:=1;
k:=1;
o:=1;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
88

kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='PROGRAM' then
posisi1:=i;
if arkode[i]='END PROGRAM' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
for j:=1 to length(cekvar) do
begin
if cekvar[j]='(' then
posisi:=j;
end;

for j:=1 to posisi-1 do


variabel1:=variabel1+cekvar[j];
arvari[o]:=variabel1;
variabel1:='';
o:=o+1;
end;

for i:=1 to o-1 do


begin
write('Fungsi yang ada adalah ',arvari[i]);
writeln;
end;
posisi:=1;
posisi1:=1;
Assign ( berkasteks,'c:\cadang.dat');
Reset ( berkasteks);
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for i:=1 to o-1 do
89

begin
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
if arvari[i]=kodeb then
posisi:=posisi1;
kodeb:='';
end;
posisi1:=posisi1+1;
end;
if posisi=4 then
writeln('Ini adalah fungsi untuk mencetak tulisan');

readln;
end.

Nam et Ipsa Scientia Potestas Est


(Pengetahuan adalah Kekuatan)
Francois Bacon

Cara Penangangan Kesalahan


Sebuah kompilator akan sering menemui program yang mengandung kesalahan, maka
kompilator harus memiliki strategi apa yang harus dilakukan untuk menangani
kesalahan - kesalahan tersebut. Kesalahan program bisa merupakan :
1. Kesalahan Leksikal
Misalkan kesalahan mengeja keyword, contoh :
Then ditulis sebagai Ten
2. Sintaks
Misalkan operasi aritmatika dengan jumlah parenthesis (kurung) yang tidak pas,
contoh :
A := X + (B*(C+D)
3. Semantik
Beberapa macam kesalahan semantik :
a. Tipe data yang salah, contoh dalam program di deklarasikan :
Var Siswa : Integer (Variabel Siswa bertipe Integer)
Tetapi selanjutnya, ada instruksi yang melakukan operasi dengan tipe yang
salah pada variabel siswa.
90

Siswa := Andy (Dilakukan operasi assignment dengan tipe data string)


b. Variabel belum didefinisikan, contoh di dalam program ada instruksi :
B := B+1;
Sementara variabel B belum dideklarasikan
Penanganan Kesalahan
Langkah - langkah penanganan kesalahan :
1. Mendeteksi kesalahan
2. Melaporkan kesalahan
3. Tindak lanjut pemulihan / perbaikan

Sebuah kompilator yang menemukan kesalahan akan melakukan pelaporan kesalahan,


yang biasanya meliputi :
1. Kode kesalahan
2. Pesan kesalahan dalam bahasa natural
3. Nama dan atribut identifier

Misal terdapat pesan kesalahan :


Error 162 Jumlah : Unknown Identifier
Bisa diartikan :
- Kode kesalahan = 162
- Pesan kesalahan = Unknown Identifier
- Nama Identifier = Jumlah

Reaksi Kompilator pada Kesalahan


Terdapat beberapa tingkatan reaksi yang dilakukan oleh kompilator saat menemukan
kesalahan :
1. Reaksi - reaksi yang tidak dapat diterima (Tidak melaporkan error)
Kompilator crash : Berhenti atau hang
Looping : Kompilator masih berjalan tetapi tidak pernah berhenti karena
looping tak berhingga (indefinite / Onbounded Loop)
Menghasilkan program objek yang salah : kompilator melanjutkan proses
sampai selesai tetapu program objek yang dihasilkan salah. Ini berbahaya bila
tidak diketahui oleh pemrogram, karena baru akan muncul saat program
dieksekusi.
91

Respon - respon di atas merupakan tingkatan terendah, dan bisa muncul pada
kompilator yang dirancang tanpa mempertimbangkan kemungkinan kompilator
memproses source code yang mengandung kesalahan.
2. Reaksi yang benar tetapi kurang dapat diterima dan kurang bermanfaat
Kompilator menemukan kesalahan pertama, melaporkannya, lalu berhenti (halt).
Ini bisa muncul bila pembuat kompilator menganggap jarang terjadi kemunculan
error dalam program. Sehingga kemampuan kompilator untuk mendeteksi dan
melaporkan kesalahan hanya satu untuk setiap kali kompilasi. Pemrogram akan
membuang waktu untuk melakukan pengulangan kompilasi setiap kali terdapat
sebuah error.
3. Reaksi - reaksi yang dapat diterima
Reaksi yang dapat diterima adalah bila setelah kompilator menemukan kesalahan
melaporkan baris ke berapa kesalahan tersebut terjadi, memperbaikinya, dan
kemudian melanjutkan lagi pemeriksaan ke baris yang berikutnya.

Perbaikan kesalahan bertujuan memodifikasi source program dari kesalahan dan


membuatnya valid, sehingga memungkinkan kompilator untuk melakukan translasi
program yang mana akan dialirkan ke tahapan selanjutnya pada proses kompilasi.
Mekanisme error repair meliputi :
1. Mekanisme Ad Hoc
Tergantung dari pembuat kompilator sendiri / spesifik 2.
Syntax Directed Repair
Menyisipkan simbol terminal yang dianggap hilang atau membuang terminal
penyebab kesalahan. Contoh pada potongan program berikut kurang simbol DO :
While A<1
I := I+1;
Kompilator akan menyisipkan simbol Do
Contoh lain :
Procedure Increment;
Begin
X := X+1;
End;
End;
Terdapat kelebihan simbol end, yang menyebabkan kesalahan, maka kompilator
akan membuangnya.
92

3. Context Sensitive Repair


Perbaikan dilakukan pada kesalahan :
Tipe Identifier. Di atasi dengan membangkitkan identifier dummy, misalnya
pada potongan program :
Var A : String;
Begin
A :=0;
End;

Kompilator akan memperbaiki kesalahan dengan membangkitkan identifier


baru, misal B yang bertipe integer.
Tipe Konstanta
Di atasi dengan membangkitkan konstanta baru dengan tipe yang tepat.
4. Spelling Repair
Memperbaiki kesalahan pengetikan pada identifier, misal :
Whille A=1 Do
Identifier yang salah tersebut akan diperbaiki menjadi While
Catatan :
Contoh - contoh kesalahan yang ada di sini dan mekanisme penanganannya
bukanlah berasal dari suatu produk kompilator tertentu, meskipun instruksi -
instruksi yang ada dalam potongan program di sini memiliki kemiripan dengan
bahasa Pascal. Kemiripan tersebut hanya bertujuan untuk mempermudah
pemahaman semata.

Contoh program berikut akan menambahkan karakter ; pada bagian program yang
tidak memiliki ;
Jawab :
Uses Crt;
Var
BerkasTeks : Text;
teks:text;
kode:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
93

cekvar:string;
flag:boolean; {menampung status ;}
Begin
n:=1;
i:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='PROGRAM' then
posisi1:=i;
if arkode[i]='END PROGRAM' then
posisi2:=i;
end;
for I:=posisi1+1 to posisi2-1 do
begin
cekvar:=arkode[i];
if (cekvar[length(cekvar)]=';') and (flag=true) then
flag:=true;
if (cekvar[length(cekvar)]<>';') and (flag=true) then
begin
flag:=false;
possalah:=i;
end;
cekvar:='';
94

end;
if flag=true then
writeln('ada titik koma')
else
writeln('tidak ada titik koma pada baris ke-',possalah);
arkode[possalah]:=arkode[possalah]+';';

kodeb:='';
Assign ( teks,'C:\variabel.dat');
rewrite(teks);
writeln('Kode program setelah diperbaiki adalah :'); for
i:=1 to n do
writeln(arkode[i]);
for i:=1 to 3 do
begin
kodeb:=arkode[i];
writeln(teks,arkode[i]);
kodeb:='';
end;
close(teks);

readln;
end.

Berikut ini adalah contoh program untuk memperbaiki kesalahan pengetikan pada
suatu nama identifier (Misal While - Do), dengan format penulisan yang benar
adalah:
While

Do
95

Jawab :
Uses Crt;
Var
BerkasTeks : Text;
teks:text;
kode:string; {untuk menampung kode}
kodeb:string; {untuk menampung huruf besar dari kode}
arkode : array [1..100] of string; {untuk menampung kode dalam
{huruf besar}
I,n,j,posisi1,posisi2 : byte;
possalah:byte;
cekvar:string;
jawab:char;
flag:boolean; {menampung status ;}
Begin
clrscr;
n:=1;
i:=1;
j:=1;
flag:=true;
possalah:=0;
Assign ( berkasteks,'c:\variabel.dat');
Reset ( berkasteks);
Clrscr;
While not EOF ( berkasteks ) do
Begin
Readln( berkasteks,kode);
for j:=1 to length(kode) do
kodeb:=kodeb+upcase(kode[j]);
arkode[i]:=kodeb;
n:=n+1;
i:=i+1;
kodeb:='';
end;

close ( BerkasTeks );

for i:=1 to n-1 do


begin
if arkode[i]='WHILE' then
posisi1:=i;
96

if arkode[i]='DO' then
posisi2:=i;
end;

If posisi2=posisi1+2 then
flag:=true
else
flag:=false;
writeln('Kode anda adalah :');
for i:=1 to n-1 do
writeln(arkode[i]);
if flag=false then
begin
writeln('Kode Anda tidak ada Do :');
Writeln('Seharusnya pada baris: ',posisi1+2,' adalah do');
Writeln('Apakah Anda mau timpa?(Y/T)');
readln(jawab);
end;

if upcase (jawab)='Y' then


begin
arkode[posisi1+2]:='DO';
assign ( teks,'C:\variabel.dat');
rewrite(teks);
writeln('Kode program setelah diperbaiki adalah :'); for
i:=1 to n do
writeln(arkode[i]);
for i:=1 to n-1 do
begin
kodeb:=arkode[i];
writeln(teks,arkode[i]);
kodeb:='';
end;
end;
close(teks);
readln;
end.
97

Intermediate Code Generator


Kode antara / Intermediate Code merupakan hasil dari tahapan analisis, yang dibuat oleh
kompilator pada saat mentranslasikan program dari bahasa tingkat tinggi. Kegunaan
dari kode antara :
1. Untuk memperkecil usaha dalam membangun kompilator dari sejumlah bahasa ke
sejumlah mesin. Dengan adanya kode antara yang lebih machine independent
maka kode antara yang dihasilkan dapat digunakan lagi pada mesin lainnya.
2. Proses optimasi lebih mudah dilakukan. Beberapa strategi optimasi lebih mudah
dilakukan pada kode antara daripada pada program sumber atau pada kode
assembly dan kode mesin.
3. Bisa melihat program internal yang gampang dimengerti. Kode antara ini akan
lebih mudah dipahami daripada kode assembly atau kode mesin.

Kerugian dari kode antara, dengan melakukan dua kali translasi, maka butuh waktu
yang relatif lebih lama.

Notasi Postfix
Sehari - hari kita biasa menggunakan operasi dalam notasi infix (letak operator di
tengah). Pada notasi Postfix operator diletakkan paling akhir maka disebut juga
dengan notasi Sufix atau reverse polish. Sintax notasi Postfix :
<Operand> <Operand> <Operator>
Misalkan ekspresi :
A+b
Kalau kita nyatakan dalam postfix :
Ab+
Adapun prioritas pengerjaan suatu operator adalah sebagai berikut.
1. ( atau )
2. * atau :
3. + atau -
Untuk mengubah dari suatu notasi infix menjadi suatu notasi postfix dapat kita
lakukan dengan menggunakan suatu tumpukan, yang memiliki aturan :
1. Jika ada operator yang masuk ke dalam stack maka operand yang ada harus
dikeluarkan.
98

2. Jika operator yang masuk ke dalam stack lebih kecil atau sama dengan operator
yang ada di dalam stack maka operator yang ada di dalam stack harus dikeluarkan.
3. Operator buka kurung tidak pernah dikenai operasi stack.
4. Jika tanda tutup kurung masuk, maka semua operator maupun operand yang
masuk akan dikeluarkan sebatas tanda buka kurung ke atas.

Berikut ini adalah urutan untuk menerjemahkan instruksi A + B ke dalam bentuk


notasi postfix
Langkah 1 Langkah 2 Langkah 3 Langkah 4
A
A + B

B
A + A + A

Sehingga hasil akhirnya diperoleh :


AB+

Contoh lain :
A+B*C

Langkah 1 Langkah 2 Langkah 3 Langkah 4


A B
A + B *

B
A + A + A

Langkah 5 Maka hasil akhirnya diperoleh :

C ABC*+

*
+ AB
Contoh lain :
(A+B) * C
99

Langkah 1 Langkah 2 Langkah 3 Langkah 4


( A + A B

A +
( ( (
A

Langkah 5 Langkah 6 Langkah 7


) + * C
B
B
+
( A AB+ * AB+

Maka Hasil akhir diperoleh


AB+C*

Soal :
Ubahlah bentuk berikut ke dalam bentuk notasi Postfix
1.
A*(B+C)
2. (A+(B+C)*D-E)
3. (A-C) +((B+D)*E)

Notasi Postfix dalam Teknik Kompilasi


Kita dapat mengubah instruksi kontrol program yang ada ke dalam notasi Postfix.
Misal :
IF <exp> Then <Stmt1> Else <Stmt2>
Diubah ke dalam Postfix
<Exp> <Label1>BZ<Stmt1><Label2>BR<Stmt2>
Keterangan :
BZ : Branch If Zero (Zero=salah) {Bercabang / meloncat jika kondisi yang ditest
salah}
BR : Branch {Bercabang / meloncat tanpa ada kondisi yang ditest}
100

Arti dari notasi postfix di atas adalah :


Jika kondisi ekspresi salah, maka instruksi akan meloncat ke Label1 dan
menjalankan statement2. Bila kondisi ekspresi benar, maka statement1 akan
dijalankan lalu meloncat ke Label2. Label1 dan Label2 sendiri menunjukkan posisi
tujuan loncatan, untuk label1 posisinya tepat sebelum statement2, dan label2 setelah
statement2.

Dalam implementasi ke kode antara, label bisa berupa nomor baris intruksi. Untuk
lebih jelasnya bisa dilihat contoh berikut.
IF a>b Then
C:=d
Else
C:=e

Bisa diubah ke dalam PostFix


11 a
12 b
13 >
14 22
15 BZ
16 c
17 d
18 :=
19
20 26
21 Br
22 c
23 e
24 :=
25
26

Notasi Postfix di atas bisa dipahami sebagai berikut.


Bila ekspresi (a>b) salah, maka loncat ke instruksi no. 22
Bila ekspresi (a>b) benar, tidak terjadi loncatan, instruksi berlanjut ke 16 sampai 25, lalu
loncat ke no. 26
101

Contoh lain :
a:=1
While A<5 do
A:=a+1
Diubah ke Postfix :
10 a
11 1
12 :=
13 a
14 5
15 <
16 26
17 BZ
18 a
19 a
20 1
21 +
22 :=
23
24 13
25 br
26

Contoh lain :
a:=1
Repeat
B:=b+a
Until A<5

Diubah Ke Postfix :
10 a
11 1
12 :=
13 b
14 b
15 a
16 +
17 :=
18
19 a
102

20 a
21 1
22 +
23 :=
24
25 a
26 5
27 <
28 32
29 BZ
30 13
31 BR
32
Contoh lain :
For i := 1 to 5 do
a:=a+1
Diubah ke postfix :
10 i
11 1
12 :=
13 i
14 5
15 <=
16 32
17 BZ
18 a
19 a
20 1
21 +
22 :=
23
24 i
25 i
26 1
27 +
28 :=
29
30 13
31 BR
32
103

Notasi N - Tuple
Bila pada Postfix setiap baris intruksi hanya terdiri dari satu tupel, pada notasi N -
Tuple setiap baris bisa terdiri dari beberapa tupel. Format umum dari notasi N - Tuple
adalah :
Operator N - 1 Operand
Selanjutnya akan dibahas notasi 3 tupel dan 4 tupel

Triples Notation
Notasi tripel memiliki format
<Operator> <Operand> <Operand>
Contoh, instruksi :
A := D * C + B / E
Bila dibuat kode antara tripel :
1. *, D, C
2. /, B, E
3. +, (1), (2)
4. :=, A, (3)

Perlu diperhatikan presedensi dari operator, yaitu operator perkalian dan pembagian
mendapat prioritas dibanding penjumlahan dan pengurangan
Contoh lain :
IF X > Y then
X:= a - b
Else
X:= a + b
Kode antara tripelnya :
1. >, X, Y
2. BZ, (1), (7)
3. -, a, b
4. :=, X, (3)
5.
104

6. BR, , (10)
7. +,a, b
8. :=, x, (7)
9.
10.

Contoh lain :
Ubahlah instruksi berikut ke dalam bentuk triples notation : A
:= B + C * D / E
F:=C*D
Bila dibuat ke dalam bentuk triples notation :
1. *, C, D
2. /, (1), E
3. +, B, (2)
4. :=, A, (3)
5.
6. :=, F, (1)
7.

Contoh lain :
a:=1
While A<5 do
A:=a+1
Diubah ke Triples Notation :
1. :=,a, 1
2. <, a, 5
3. BZ,(2),(8)
4. +,a,1
5. :=,a,(4)
6.
7. BR,,(2)
8.

Contoh lain :
105

a:=1
Repeat
B:=b+a
Until A<5
Diubah Ke triples notation :
1. :=,a,1
2. +,b,a
3. :=,b,(2)
4.
5. +,a,1
6. :=,a,(5)
7.
8. <,a,5
9. BZ,(8),(11)
10. BR, ,(3)
11.
Contoh lain :
For i := 1 to 5 do
a:=a+1
Diubah ke Triples Notation :
1. :=,i,1
2. <=,i,5
3. BZ,(2),(9)
4. +,a,1
5. :=,a,(4)
6. +,i,1
7. :=,i,(6)
8. BR, ,(2)

Quadruples Notation
Format notasi Quadruples
<Operator> <Operand> <Operand> <Hasil>
Contoh instruksi :
A := D * C + B / E
Bila dibuat ke dalam bentuk quadruples notation :
106

1. *, D, C, T1
2. /, B, E, T2
3. +, T1, T2, A

Contoh lain :
a:=1
While A<5 do
A:=a+1
Bila dibuat ke dalam bentuk quadruples notation :
1. :=,a,1,T1
2. <,a,5,T2
3. BZ,T2,(6),T3
4. +,a,1,A
5. BR,,T2,T4

Anda mungkin juga menyukai