Bagaimana belajar perakitan membantu dalam pemrograman? [Tutup]

132

Saya telah pemrograman dalam bahasa tingkat yang lebih tinggi (Python, C #, VBA, VB.NET) selama sekitar 10 tahun dan saya benar-benar tidak memahami apa yang terjadi, "di bawah tenda."

Saya bertanya-tanya apa manfaat dari belajar perakitan, dan bagaimana ini akan membantu saya sebagai seorang programmer? Bisakah Anda memberi saya sumber daya yang akan menunjukkan kepada saya persis hubungan antara apa yang saya tulis dalam kode tingkat yang lebih tinggi dengan apa yang terjadi dalam perakitan?

Yuck
sumber
2
Jika Anda benar-benar ingin tahu apa yang ada di bawah kode Anda, daripada melihat manual prosesor Intel (hanya bagian pengantar): download.intel.com/products/processor/manual/325462.pdf . Mungkin ini sedikit lebih dalam dari yang Anda inginkan, tetapi saya merasa ini berguna.
superM
4
Jika Anda ingin tahu apa yang terjadi di bawah tenda khusus di .Net, Anda mungkin ingin mempelajari lebih lanjut tentang CIL. Ini mirip dengan perakitan dalam beberapa hal, tetapi jauh lebih tinggi. Karena itu, lebih mudah dipahami daripada perakitan yang sebenarnya.
svick
6
Jika Anda mempelajari perakitan, Anda dapat menghindari berpikir Anda mengoptimalkan satu forlingkaran dengan mendeklarasikan variabel di luarnya. contoh
StriplingWarrior
7
Ya Tuhan. Anda baru saja mengingatkan saya tentang kelas bahasa Majelis yang saya ambil di perguruan tinggi sekitar 1 tahun yang lalu. Sungguh menakjubkan melihat betapa hal-hal yang sangat sederhana yang kita terima begitu saja diterjemahkan dalam ratusan atau bahkan ribuan operasi tingkat rendah dan lebih rendah. Komputer adalah mesin yang luar biasa.
Radu Murzea
14
Learning assembly akan melimpahi Anda dengan cinta yang mendalam dan tetap pada konsep bahasa pemrograman yang melindungi Anda dari EVER yang harus menulis kode kompleks dalam assembly lagi.
Shadur

Jawaban:

188

Karena Anda akan memahami cara benar-benar bekerja.

  • Anda akan memahami bahwa panggilan fungsi tidak gratis dan mengapa tumpukan panggilan dapat meluap (misalnya, dalam fungsi rekursif). Anda akan memahami bagaimana argumen dilewatkan ke parameter fungsi dan cara yang bisa dilakukan (menyalin memori, menunjuk ke memori).
  • Anda akan memahami bahwa memori tidak gratis dan betapa berharganya manajemen memori otomatis. Memori bukanlah sesuatu yang Anda "miliki", pada kenyataannya itu perlu dikelola, diurus dan yang paling penting, tidak dilupakan (karena Anda perlu membebaskannya sendiri).
  • Anda akan memahami bagaimana aliran kontrol bekerja pada level paling mendasar.
  • Anda akan lebih menghargai konstruk dalam bahasa pemrograman tingkat yang lebih tinggi.

Apa intinya adalah bahwa semua hal yang kita tulis dalam C # atau Python perlu diterjemahkan ke dalam urutan tindakan dasar yang dapat dieksekusi komputer. Sangat mudah untuk memikirkan komputer dalam hal kelas, generik dan daftar pemahaman tetapi ini hanya ada dalam bahasa pemrograman tingkat tinggi kami.

Kita dapat memikirkan konstruksi bahasa yang terlihat sangat bagus tetapi itu tidak diterjemahkan dengan sangat baik ke cara tingkat rendah dalam melakukan sesuatu. Dengan mengetahui cara kerjanya, Anda akan lebih memahami mengapa segala sesuatunya berjalan sebagaimana mestinya.

Simeon Visser
sumber
12
+1 untuk "Anda akan lebih menghargai konstruk dalam bahasa pemrograman tingkat yang lebih tinggi" saja. Jawaban yang bagus
DevSolo
42
Kecuali bahwa setelah beberapa minggu asm, Anda akan mulai menganggap C sebagai bahasa pemrograman tingkat tinggi. Kecuali jika Anda berbicara dengan pengembang perangkat tertanam tingkat rendah, mengatakan itu dengan keras akan membuat kebanyakan orang berpikir Anda sedikit gila.
Dan Neely
19
@Dan: Agak lucu bagaimana istilah ini berubah dari waktu ke waktu. 20 tahun yang lalu, ketika saya memulai pemrograman, jika Anda bertanya kepada seseorang bahwa mereka akan berkata "Tentu saja C adalah bahasa tingkat tinggi!" Itu harus jelas; ini menyediakan model tumpukan dan akses memori standar. Dan itu beberapa abstraksi serius dari perangkat keras; dalam bahasa tingkat rendah, Anda harus melacak semua alamat memori sendiri, atau jika Anda melakukan sesuatu yang benar - benar mewah, Anda menulis pengalokasian tumpukan Anda sendiri! Jadi saya harus bertanya-tanya, apa kriteria yang membuat sesuatu tingkat tinggi atau rendah hari ini?
Mason Wheeler
9
Tingkat tinggi / rendah bukanlah biner. Seorang programmer berpengetahuan luas yang menulis baik assembly dan Python dalam karirnya mungkin menganggap C atau C ++ sebagai bahasa tingkat menengah.
Russell Borogove
6
Itu adalah hal-hal penting untuk dipahami, tetapi mudah dicakup pada tingkat abstrak: misalnya, dalam kursus pengantar tentang komputer pada tingkat instruksi mesin. Saya bukan programmer perakitan tetapi saya memahaminya dengan baik, jika saya mengatakannya sendiri. Dalam beberapa jawaban SO saya melihat diskusi tentang cache instruksi dan jalur pipa, dan itu memang membuat kepala saya berputar; tetapi tingkat sub-instruksi ini (sejauh ini) hilang dari jawaban. Jadi apa manfaat sebenarnya belajar pemrograman perakitan, dibandingkan mengambil kursus dasar?
alexis
33

Ini akan memberi Anda pemahaman yang lebih baik tentang apa yang "terjadi di bawah tenda" dan bagaimana pointer bekerja dan makna variabel register dan arsitektur (alokasi dan manajemen memori, melewati parameter (berdasarkan nilai / dengan referensi), dll) secara umum.

Untuk mengintip cepat dengan C bagaimana ini?

#include <stdio.h>

main()
{
  puts("Hello World.");
  return(0);
}

kompilasi dengan gcc -S so.cdan lihat output assembly di so.s:

 $ cat so.s

    .file   "so.c"
    .section    .rodata
.LC0:
    .string "Hello World."
    .text
.globl main
    .type   main, @function
main:
    pushl   %ebp
    movl    %esp, %ebp
    andl    $-16, %esp
    subl    $16, %esp
    movl    $.LC0, (%esp)
    call    puts
    movl    $0, %eax
    leave
    ret
    .size   main, .-main
    .ident  "GCC: (Ubuntu 4.4.3-4ubuntu5.1) 4.4.3"
    .section    .note.GNU-stack,"",@progbits
Levon
sumber
2
+1: Kiat bagus! Anda dapat belajar banyak dengan melihat apa yang dilakukan oleh kompiler C.
Giorgio
8
... Apakah SOS disengaja? (meminta bantuan, dll.)
Izkata
1
@Izkata ha ha .. bagus, aku bahkan tidak menyadarinya. Saya memiliki so.cfile standar untuk pertanyaan stackoverflow (seperti yang saya miliki so.py, so.awkdll) untuk menguji hal-hal dengan cepat. So.S .. :)
Levon
9
Jika Anda mengkompilasi dengan gcc -O -c -g -Wa,-ahl=so.s so.cAnda dapat melihat output perakitan untuk setiap baris kode C. Ini membuatnya sedikit lebih mudah untuk memahami apa yang sedang terjadi.
Mackie Messer
1
Ya, hasilnya panjang. Anda dapat mencari untuk 5:so.cmenemukan kode untuk baris 5 dari so.c.
Mackie Messer
30

Saya pikir jawaban yang Anda cari ada di sini: http://www.codeproject.com/Articles/89460/Why-Learn-Assembly-Language

Kutipan dari artikel:

Meskipun itu benar, Anda mungkin tidak akan menemukan diri Anda menulis aplikasi pelanggan berikutnya dalam perakitan, masih ada banyak manfaat dari pembelajaran assembly. Saat ini, bahasa assembly digunakan terutama untuk manipulasi perangkat keras langsung, akses ke instruksi prosesor khusus, atau untuk mengatasi masalah kinerja kritis. Penggunaan yang umum adalah driver perangkat, sistem tertanam tingkat rendah, dan sistem waktu nyata.

Faktanya adalah, bahasa tingkat tinggi yang lebih kompleks menjadi, dan semakin banyak ADT (tipe data abstrak) yang ditulis, semakin banyak biaya tambahan yang dikeluarkan untuk mendukung opsi ini. Dalam contoh. NET, mungkin MSIL membengkak. Bayangkan jika Anda mengenal MSIL. Di sinilah bahasa assembly bersinar.

Bahasa assembly sedekat mungkin dengan prosesor seperti yang Anda dapatkan sebagai programmer sehingga algoritma yang dirancang dengan baik menyala - perakitan sangat bagus untuk optimasi kecepatan. Ini semua tentang kinerja dan efisiensi. Bahasa assembly memberi Anda kendali penuh atas sumber daya sistem. Sama seperti jalur perakitan, Anda menulis kode untuk memasukkan nilai tunggal ke dalam register, menangani alamat memori secara langsung untuk mengambil nilai atau pointer.

Menulis bersama adalah memahami dengan tepat bagaimana prosesor dan memori bekerja bersama untuk "mewujudkan sesuatu". Berhati-hatilah, bahasa rakitan bersifat samar, dan ukuran kode sumber aplikasi jauh lebih besar daripada bahasa tingkat tinggi. Tapi jangan salah, jika Anda bersedia meluangkan waktu dan upaya untuk menguasai majelis, Anda akan menjadi lebih baik, dan Anda akan menjadi menonjol di lapangan.

Selain itu, saya akan merekomendasikan buku ini karena memiliki versi sederhana dari arsitektur komputer: Pengantar Sistem Komputasi: Dari Bits dan Gates ke C and Beyond, 2 / e Yale N. Patt, Universitas Texas di Austin Sanjay J. Patel, Universitas Illinois di Urbana / Champaign

notkilroy
sumber
7
Ini menggambarkan untuk apa ASM digunakan, dan menyebutkan bahwa HLL membengkak, tetapi satu-satunya manfaat spesifik yang diberikan untuk mempelajari ASM adalah menulis kode super cepat. Ya, tetapi bahkan jika Anda mempelajari ASM, seberapa besar kemungkinan Anda benar-benar memasukkannya ke dalam aplikasi? Dengan asumsi Anda menulis aplikasi bisnis, bukan pengontrol perangkat keras atau driver perangkat.
+1 @notkilroy, terima kasih atas tautannya dan terutama rekomendasi buku
Anthony
2
@ Jon, saya benar-benar tidak mengerti mengapa Anda melakukannya jika Anda sedang mengembangkan perangkat lunak bisnis. Itu satu hal jika Anda seorang DBA, atau menulis kompiler, atau memiliki ruang memori terbatas, tetapi saya tidak berpikir banyak orang sering menyentuhnya. Optimasi sebagian besar diurus oleh kompiler, yang merupakan alasan terbesar untuk menulis dalam perakitan. Terkadang membantu saat melacak kebocoran memori.
Brynne
Karena saya berspesialisasi dalam mengembangkan aplikasi bisnis, saya terutama mengandalkan alat pengembangan aplikasi berbasis SQL yang menggunakan 4GL. Mereka memungkinkan saya untuk membuat prototipe aplikasi dengan cepat dan menyesuaikannya menjadi sistem produksi. Jarang saya perlu menulis cfunc yang bisa dipanggil. Waktu untuk menyampaikan dan waktu untuk memodifikasi adalah faktor besar di dunia saya!
Frank R.
2
Saya sangat tidak setuju. Pengoptimal otomatis seringkali mengalahkan programmer manusia dalam membuat perakitan cepat.
DeadMG
22

Menurut pendapat saya yang sederhana, itu tidak banyak membantu.

Saya dulu tahu perakitan x86 dengan sangat baik. Itu sedikit membantu ketika perakitan muncul di kursus saya, muncul sekali selama wawancara, dan itu membantu saya membuktikan bahwa kompiler (Metrowerks) menghasilkan kode yang buruk. Sangat menarik bagaimana komputer sebenarnya bekerja, dan saya merasa secara intelektual lebih kaya karena telah mempelajarinya. Itu juga sangat menyenangkan untuk dimainkan saat itu.

Namun, kompiler hari ini lebih baik dalam menghasilkan perakitan daripada hampir semua orang di hampir semua bagian kode. Kecuali Anda menulis kompiler atau memeriksa apakah kompiler Anda melakukan hal yang benar, Anda mungkin membuang-buang waktu dengan mempelajarinya.

Saya akui bahwa banyak pertanyaan yang masih berguna diajukan oleh programmer C ++ diinformasikan dengan mengetahui assembly. Sebagai contoh: haruskah saya menggunakan variabel stack atau heap? saya harus melewati nilai atau referensi const? Namun, dalam hampir semua kasus, saya berpikir bahwa pilihan ini harus dibuat berdasarkan keterbacaan kode daripada penghematan waktu komputasi. (Misalnya, gunakan variabel tumpukan setiap kali Anda ingin membatasi variabel ke ruang lingkup.)

Saran saya yang sederhana adalah fokus pada keterampilan yang benar-benar penting: desain perangkat lunak, analisis algoritma, dan pemecahan masalah. Dengan pengalaman mengembangkan proyek-proyek besar, intuisi Anda akan meningkat, yang meningkatkan nilai Anda lebih dari sekadar mengetahui perakitan (menurut saya).

Neil G
sumber
2
Saya tidak setuju. Jika Anda memiliki pengetahuan luas tentang algoritma tertentu dan pemahaman yang baik tentang perangkat keras, biasanya dimungkinkan untuk membuat kode rakitan yang lebih baik dioptimalkan daripada apa yang dapat dibuat oleh kompiler karena harus memainkannya dengan aman. Mengetahui secara kasar bagaimana kode Anda diterjemahkan ke dalam rakitan juga membantu saat melakukan optimasi.
Leo
Optimasi bukan alasan untuk mempelajarinya. Dalam aspek itu, saya setuju dengan Neil G. Namun, Neil G tidak mengerti intinya; Dia meremehkan bagaimana pemahaman yang mendasarinya tentang mesin nyata menginformasikan bagaimana dia menggunakan bahasa tingkat tinggi.
Warren P
Dalam pengalaman saya, algoritma dibuat cepat dengan mengimplementasikannya, mengukur sesuatu, menemukan cara untuk mengoptimalkannya, menerapkan cara yang lebih baik, dll. Dll. Masalah dengan perakitan adalah bahwa hal itu membutuhkan waktu lama untuk diimplementasikan, sehingga Anda tidak akan memiliki kesempatan penyempurnaan berulang.
gnasher729
Ada beberapa kasus yang harus dikodekan dalam perakitan hari ini, tetapi mengetahui cara kerjanya sangat berharga dan akan banyak membantu bagi mereka yang ingin tahu cara kerjanya. Saya, misalnya, merasa sulit untuk mengikuti hal-hal ketika saya tidak tahu mengapa hal itu terjadi.
Winger Sendon
21

Anda harus terbiasa dengan satu level 'lebih dalam' dalam sistem yang sedang Anda kerjakan. Melewati terlalu jauh dalam sekali jalan tidak buruk, tetapi mungkin tidak membantu seperti yang diinginkan seseorang.

Seorang programmer dalam bahasa tingkat tinggi harus belajar bahasa tingkat yang lebih rendah (C adalah pilihan yang sangat baik). Anda tidak perlu pergi jauh-jauh ke perakitan untuk memiliki apresiasi terhadap apa yang terjadi di bawah selimut ketika Anda memberi tahu komputer untuk membuat instance objek, atau membuat tabel hash, atau set - tetapi Anda harus dapat membuat kode mereka.

Untuk seorang programmer java, mempelajari beberapa C akan membantu Anda dengan manajemen memori, melewati argumen. Menulis beberapa perpustakaan java yang luas di C akan pergi cara untuk memahami kapan harus menggunakan implementasi Set apa (Anda ingin hash? Atau tree?). Berurusan dengan char * di lingkungan berulir akan membantu memahami mengapa String tidak dapat diubah.

Dibawa ke tingkat berikutnya ... AC programmer harus memiliki pengetahuan tentang perakitan, dan jenis perakitan (sering ditemukan di toko-toko sistem tertanam) kemungkinan akan lebih baik dengan memahami hal-hal di tingkat gerbang. Mereka yang bekerja dengan gerbang harus mengetahui beberapa fisika kuantum. Dan para fisikawan kuantum itu, mereka masih berusaha mencari tahu apa abstraksi selanjutnya.

pengguna40980
sumber
1
Satu tingkat lebih dalam adalah tentang benar. Saya cenderung mencari pasangan, tetapi dengan asumsi bahwa pengetahuan perakitan x86 bernilai investasi dibandingkan dengan mempelajari MSIL untuk seorang programmer C # meminta terlalu banyak. Sebagai seseorang yang mempelajari fisika solid state dan perakitan di uni, saya tidak berpikir bahwa mengetahui fisika desain gerbang telah membantu saya sama sekali, selain lulus dengan gelar dalam bidang elektronik.
Muhammad Alkarouri
@MuhammadAlkarouri Saya berpikir untuk memahami kebocoran saat ini, lama berjalan, resistensi dan dampak panas pada sistem. Pemahaman yang mendasari 'mengapa' membantu dalam membuat keputusan lebih dari aturan pemisahan minimum dan toleransi operasi.
5

Karena Anda tidak menyebutkan C atau C ++ dalam bahasa yang Anda tahu daftar. Saya SANGAT merekomendasikan untuk mempelajarinya dengan baik bahkan sebelum berpikir tentang berkumpul. C atau C ++ akan memberikan semua konsep dasar yang benar-benar transparan dalam bahasa yang dikelola dan Anda akan memahami sebagian besar konsep yang disebutkan di halaman ini dengan salah satu bahasa paling penting yang dapat Anda gunakan dalam proyek dunia nyata. Ini adalah nilai tambah nyata untuk keterampilan pemrograman Anda. Perlu diketahui bahwa rakitan digunakan di area yang sangat spesifik dan hampir tidak berguna seperti C atau C ++.

Saya bahkan akan melangkah lebih jauh dengan mengatakan bahwa Anda tidak harus terjun ke kebaktian sebelum memahami cara kerja bahasa yang tidak dikelola. Ini hampir merupakan bacaan wajib.

Anda harus belajar perakitan jika Anda ingin melangkah lebih jauh ke bawah. Anda ingin tahu bagaimana tepatnya setiap konstruksi bahasa dibuat. Ini informatif tetapi tingkat kerumitannya sangat berbeda.

AhHatem
sumber
5

Jika Anda tahu bahasa dengan baik, Anda harus memiliki setidaknya pengetahuan dasar tentang teknologi satu tingkat abstraksi yang lebih rendah.

Mengapa? Ketika terjadi kesalahan, pengetahuan tentang mekanisme yang mendasari membuatnya jauh lebih mudah untuk men-debug masalah aneh, dan secara alami menulis kode yang lebih efisien

Menggunakan Python (/ CPython) sebagai contoh, jika Anda mulai mendapatkan crash aneh atau kinerja buruk, pengetahuan tentang cara men-debug kode C bisa sangat berguna, sama seperti pengetahuan tentang penghitungan ulang metode manajemen memori. Ini juga akan membantu Anda mengetahui kapan / jika menulis sesuatu sebagai ekstensi C, dan seterusnya ...

Untuk menjawab pertanyaan Anda dalam hal ini, pengetahuan tentang perakitan benar-benar tidak akan membantu pengembang Python yang berpengalaman (terlalu banyak langkah dalam abstraksi - apa pun yang dilakukan dengan Python akan menghasilkan banyak instruksi perakitan)

..tapi, jika Anda berpengalaman dengan C, maka mengetahui "level selanjutnya turun" (perakitan) memang akan berguna.

Demikian pula, jika Anda menggunakan CoffeScript maka (sangat) berguna untuk mengetahui Javascript. Jika Anda menggunakan Clojure, pengetahuan tentang Java / JVM berguna.

Ide ini juga berfungsi di luar bahasa pemrograman - jika Anda menggunakan Assembly, ide yang bagus untuk membiasakan diri dengan bagaimana fungsi perangkat keras yang mendasarinya. Jika Anda seorang perancang web, ide yang baik untuk mengetahui bagaimana aplikasi web diimplementasikan. Jika Anda seorang mekanik mobil, sebaiknya memiliki pengetahuan tentang beberapa fisika

dbr
sumber
3

Tuliskan program c kecil, dan bongkar hasilnya. Itu saja. Namun, bersiaplah untuk kode "housekeeping" yang lebih besar atau lebih kecil yang ditambahkan untuk kepentingan Sistem Operasi.

Majelis membantu Anda memahami apa yang terjadi di bawah kap karena berhubungan langsung dengan memori, register prosesor dan sejenisnya.

Jika Anda benar-benar ingin menggunakan bare-metal tanpa semua kerumitan sistem operasi yang menyulitkan, coba pemrograman Arduino dalam bahasa assembly.

Robert Harvey
sumber
3

Tidak ada jawaban pasti, karena programmer tidak semuanya tipe. Apakah Anda PERLU untuk tahu apa yang mengintai di bawahnya? Jika demikian, maka pelajari. apakah Anda hanya ingin mempelajarinya, karena penasaran? Jika demikian, maka pelajari. Jika itu tidak memiliki manfaat praktis bagi Anda, lalu mengapa repot-repot? Apakah seseorang membutuhkan tingkat pengetahuan mekanik hanya untuk mengendarai mobil? Apakah montir membutuhkan tingkat pengetahuan insinyur, hanya untuk bekerja di mobil? Ini analogi yang serius. Seorang mekanik dapat menjadi mekanik yang sangat baik, produktif tanpa menyelam untuk merekayasa kedalaman pemahaman tentang kendaraan yang dipeliharanya. Sama untuk musik. Apakah Anda benar-benar menyelami kompleksitas melodi, harmoni dan ritme untuk menjadi penyanyi atau pemain yang baik? Tidak. Beberapa musisi yang sangat berbakat tidak dapat membaca sedikitpun musik, apalagi memberi tahu Anda perbedaan antara mode Dorian dan Lydian. Jika Anda ingin, baik-baik saja, tetapi tidak, Anda tidak perlu melakukannya. Jika Anda seorang pengembang web, majelis tidak memiliki penggunaan praktis yang dapat saya pikirkan. Jika Anda berada di sistem tertanam atau sesuatu yang sangat khusus, maka mungkin diperlukan, tetapi jika ya, Anda akan mengetahuinya.

Inilah pendapat Joel tentang nilai bersandar pada bahasa tingkat tinggi: http://www.joelonsoftware.com/articles/ThePerilsofJavaSchools.html

GrayFox374
sumber
2

Sebenarnya, apa yang mungkin terbaik untuk Anda adalah kelas yang tidak (sepengetahuan saya) ada di mana saja: Ini akan menjadi kelas yang menggabungkan tinjauan singkat tentang bahasa mesin / assembler dan konsep penyimpanan yang menangani dengan tur melalui konstruksi kompiler , pembuatan kode, dan lingkungan runtime.

Masalahnya adalah bahwa dengan bahasa tingkat tinggi, jauh dari perangkat keras seperti C # atau Python Anda tidak benar-benar menghargai kenyataan bahwa setiap gerakan yang Anda lakukan berubah menjadi ratusan jika tidak ribuan instruksi mesin, dan Anda tidak cenderung memahami bagaimana beberapa baris bahasa tingkat tinggi dapat menyebabkan sejumlah besar penyimpanan diakses dan dimodifikasi. Anda tidak perlu tahu persis apa yang sedang terjadi "di balik selimut", tetapi Anda perlu memiliki apresiasi untuk ruang lingkup apa yang terjadi, dan konsep umum tentang jenis hal yang terjadi.

Daniel R Hicks
sumber
1

Jawaban saya untuk pertanyaan ini telah berkembang relatif baru-baru ini. Jawaban yang ada mencakup apa yang akan saya katakan di masa lalu. Sebenarnya, ini masih dicakup oleh jawaban atas - titik "menghargai konstruk dalam pemrograman tingkat tinggi", tapi ini adalah kasus khusus yang menurut saya layak disebutkan ...

Menurut posting blog Jeff Atwood ini , yang merujuk pada penelitian, memahami tugas adalah masalah utama dalam memahami pemrograman. Pemrogram pelajar memahami bahwa notasi hanya mewakili langkah-langkah yang diikuti oleh komputer, dan alasan demi langkah, atau kalau tidak terus menerus menjadi bingung dengan analogi yang menyesatkan dengan persamaan matematika dll.

Nah, jika Anda memahami yang berikut dari 6502 assembler ...

LDA variable
CLC
ADC #1
STA variable

Itu benar-benar hanya langkah-langkahnya. Kemudian ketika Anda belajar menerjemahkannya ke pernyataan tugas ...

variable = variable + 1;

Anda tidak perlu analogi yang menyesatkan dengan persamaan matematika - Anda sudah memiliki model mental yang tepat untuk memetakannya.

EDIT - tentu saja jika penjelasan yang Anda dapatkan LDA variablepada dasarnya ACCUMULATOR = variable, yang persis seperti yang Anda dapatkan dari beberapa tutorial dan referensi, Anda akhirnya kembali ke tempat Anda memulai dan sama sekali tidak membantu.

Saya belajar 6502 assembler sebagai bahasa kedua saya, yang pertama adalah Commodore Basic, dan saya belum benar-benar belajar banyak tentang itu pada saat itu - sebagian karena ada begitu sedikit yang harus dipelajari, tetapi juga karena assembler hanya tampak jauh lebih menarik saat itu . Sebagian waktu, sebagian karena saya adalah seorang geek berusia 14 tahun.

Saya tidak merekomendasikan melakukan apa yang saya lakukan, tetapi saya ingin tahu apakah mempelajari beberapa contoh yang sangat sederhana dalam bahasa assembler yang sangat sederhana mungkin merupakan awal yang bermanfaat untuk belajar bahasa tingkat yang lebih tinggi.

Steve314
sumber
0

Kecuali jika Anda seorang penulis kompiler, atau membutuhkan sesuatu yang sangat dioptimalkan (seperti algoritma pemrosesan data), mempelajari kode perakitan tidak akan memberikan manfaat apa pun.

Menulis dan memelihara kode yang ditulis dalam kumpulan sangat sulit, oleh karena itu bahkan jika Anda tahu bahasa assembler dengan sangat baik, Anda tidak boleh menggunakannya, kecuali tidak ada cara lain.

Artikel " Mengoptimalkan untuk SSE: Studi Kasus " menunjukkan apa yang mungkin dilakukan jika Anda pergi ke pertemuan. Penulis berhasil mengoptimalkan algoritma dari 100 siklus / vektor menjadi 17 siklus / vektor.

BЈовић
sumber
1
Penulis tidak menggunakan instruksi vektor atau intrinsik apa pun di versi C ++. Anda tidak perlu assembler untuk menulis kode SSE.
gnasher729
@ gnasher729 Ya, Anda tidak perlu. Tetapi dengan perakitan, program dapat berjalan lebih cepat. Bagaimanapun, manusia bisa lebih pintar daripada kompiler (dalam kasus yang jarang terjadi).
BЈовић
0

Menulis dalam kumpulan tidak akan memberi Anda peningkatan kecepatan ajaib karena jumlah detail (alokasi register dll.) Anda mungkin akan menulis algoritma paling sepele yang pernah ada.

Selain itu dengan perakitan prosesor modern (baca - dirancang setelah 70-80-an) tidak akan memberikan Anda jumlah detail yang cukup untuk mengetahui apa yang sedang terjadi (yaitu - pada sebagian besar prosesor). PU modern (CPU dan GPU) cukup kompleks sejauh instruksi penjadwalan pergi. Mengetahui dasar-dasar perakitan (atau pseudoassembly) akan memungkinkan untuk memahami buku / kursus arsitektur komputer yang akan memberikan pengetahuan lebih lanjut (cache, eksekusi out-of-order, MMU dll). Biasanya Anda tidak perlu tahu ISA yang rumit untuk memahaminya (MIPS 5 adalah IIRC yang cukup populer).

Mengapa mengerti prosesor? Mungkin memberi Anda lebih banyak pemahaman tentang apa yang terjadi. Katakanlah Anda menulis perkalian matriks dengan cara naif:

for i from 0 to N
    for j from 0 to N
        for k from 0 to N
            A[i][j] += B[i][k] + C[k][j]

Ini mungkin 'cukup baik' untuk tujuan Anda (jika matriksnya 4x4 mungkin akan dikompilasi dengan instruksi vektor). Namun ada beberapa program yang cukup penting ketika Anda mengkompilasi array besar - bagaimana cara mengoptimalkannya? Jika Anda menulis kode dalam perakitan, Anda mungkin memiliki beberapa% peningkatan (kecuali jika Anda akan melakukan seperti yang dilakukan kebanyakan orang - juga dengan cara naif, register yang kurang dimanfaatkan, memuat / menyimpan ke memori secara terus-menerus dan akibatnya memiliki program yang lebih lambat daripada dalam bahasa HL) .

Namun Anda dapat membalikkan baris dan secara ajaib mendapatkan kinerja (mengapa? Saya meninggalkannya sebagai 'pekerjaan rumah') - IIRC tergantung pada berbagai faktor untuk matriks besar bahkan bisa 10x.

for i from 0 to N
    for k from 0 to N
        for j from 0 to N
            A[i][j] += B[i][k] + C[k][j]

Yang mengatakan - ada yang bekerja pada kompiler yang mampu melakukannya ( grafit untuk gcc dan Polly untuk apa pun yang menggunakan LLVM). Mereka bahkan mampu mengubahnya menjadi (maaf - saya menulis pemblokiran dari memori):

for i from 0 to N
    for K from 0 to N/n
        for J from 0 to N/n
            for kk from 0 to n
                for jj from 0 to n
                    k = K*n + kk
                    j = J*n + jj
                    A[i][j] += B[i][k] + C[k][j]

Untuk meringkas - mengetahui dasar-dasar perakitan memungkinkan Anda untuk menggali berbagai 'detail' dari desain prosesor yang akan memungkinkan Anda untuk menulis program lebih cepat. Mungkin baik untuk mengetahui perbedaan antara arsitektur RISC / CISC atau VLIW / vektor prosesor / SIMD / .... Namun saya tidak akan mulai dengan x86 karena mereka cenderung cukup rumit (mungkin ARM juga) - mengetahui apa itu register dll adalah IMHO cukup untuk memulai.

Maciej Piechotka
sumber
Saya merasa menarik bahwa Anda memberikan beberapa contoh kode, tetapi tidak satu pun dari mereka dalam bahasa assembly.
Robert Harvey
-1

Biasanya itu SANGAT penting untuk keperluan debugging. Apa yang Anda lakukan ketika sistem rusak di tengah instruksi dan kesalahan itu tidak masuk akal? Ini jauh dari masalah dengan bahasa .NET selama Anda hanya menggunakan kode aman - sistem hampir selalu akan melindungi Anda dari apa yang terjadi di bawah tenda.

Loren Pechtel
sumber
-2

Singkatnya saya pikir jawabannya adalah karena Anda dapat melakukan lebih banyak jika Anda belajar berkumpul. Unit pembelajaran memberikan akses ke bidang pemrograman perangkat tertanam, penetrasi dan pencegahan keamanan, rekayasa balik, dan pemrograman sistem yang sangat sulit untuk dikerjakan jika Anda tidak tahu assembler.

Sedangkan untuk mempelajarinya untuk meningkatkan kinerja program, ini diragukan dalam pemrograman aplikasi. Sebagian besar waktu ada begitu banyak hal yang harus difokuskan terlebih dahulu sebelum mencapai tingkat optimasi ini seperti mengoptimalkan akses i / o Anda pada disk dan jaringan, mengoptimalkan cara Anda membangun GUI, memilih algoritma yang tepat, memaksimalkan semua inti Anda , menjalankan uang perangkat keras terbaik dapat membeli dan beralih dari ditafsirkan ke bahasa yang dikompilasi. Kecuali jika Anda membuat perangkat lunak untuk pengguna akhir lainnya, perangkat keras lebih murah dibandingkan dengan upah per jam programmer, terutama dengan ketersediaan cloud.

Juga, Anda harus mempertimbangkan peningkatan kecepatan eksekusi program dengan keterbacaan kode Anda setelah Anda ditabrak bus, berhenti atau kembali ke basis kode untuk mengubahnya setahun setelah Anda menulis versi terakhir.

Peter Smith
sumber
-3

Saya akan merekomendasikan algoritma pembelajaran: pengurutan, daftar tertaut, pohon biner, hashing, dll.

Pelajari juga lisp, lihat Struktur dan Interpretasi Program Komputer beberapa perintah primitif, satu primitif cadel dan beberapa assembler provokatif).

Akhirnya jika Anda harus belajar assembler, pelajari yang mudah seperti ARM (juga digunakan di sekitar 4 kali lebih banyak perangkat daripada x86).

ctrl-alt-delor
sumber
-8

Yah, jawabannya adalah hanya karena bahasa yang Anda gunakan harus ditafsirkan atau dikompilasi menjadi assembler pada akhirnya. Tidak masalah bahasa atau mesin.

Desain bahasa berasal dari cara CPU bekerja. Lebih banyak pada program tingkat rendah, lebih sedikit pada program tingkat tinggi.

Saya akan mengakhiri dengan mengatakan bahwa Anda tidak hanya perlu mengetahui assembler kecil tetapi juga arsitektur CPU, yang Anda pelajari dengan mempelajari assembler.

Beberapa contoh: Ada banyak programmer java yang tidak mengerti mengapa ini tidak berhasil, dan bahkan kurang tahu apa yang terjadi ketika Anda menjalankannya.

String a = "X";
String b = "X";
if(a==b)  
    return true;

Jika Anda tahu assembler kecil, Anda akan selalu tahu bahwa itu tidak sama dengan isi dari lokasi memori vs angka dalam variabel pointer yang "menunjuk" ke lokasi itu.

Lebih buruk lagi, bahkan dalam buku yang diterbitkan Anda akan membaca sesuatu seperti di JAWA primitif dilewatkan oleh nilai dan objek dengan referensi, yang sama sekali tidak benar. Semua argumen di Java diteruskan oleh nilai, dan Java TIDAK bisa meneruskan objek ke fungsi, hanya pointer, yang diteruskan oleh nilai.

Jika Anda sekarang memahami apa yang sedang terjadi, jika tidak begitu rumit untuk menjelaskan bahwa sebagian besar penulis hanya memberikan Anda kebohongan yang saleh.

Tentu saja, konsekuensi dari ini tidak kentara tetapi dapat membuat Anda dalam masalah nyata di kemudian hari. Jika Anda tahu assembler itu bukan masalah, jika tidak, Anda berada dalam proses debugging yang panjang.

Alex Vaz
sumber
5
Paragraf pertama Anda benar-benar salah: bahasa tidak dikompilasi ke dalam ASM, mereka dikompilasi ke dalam Kode Mesin. Penerjemah tidak mengkompilasi ke ASM, mereka menafsirkan kode atau kode byte dan memanggil fungsi atau metode pada kode mesin yang dikompilasi.
6
Satu hal yang Anda klaim tentang Java juga tidak benar. Dimulai dengan String a = "X"; String b = "X"; if( a==b) return true;yang sebenarnya == truekarena sesuatu yang disebut String interningkompiler tidak. Semua pernyataan Java lainnya juga salah. Java tidak memiliki pointer, ia memiliki referensi yang bukan hal yang sama. Dan tidak ada satupun yang ada hubungannya dengan assembler dengan cara apa pun. Java melewati primitif berdasarkan nilai dan juga referensi berdasarkan nilai. Java tidak memiliki pointer sehingga tidak dapat melewati mereka dengan apa pun. Sekali lagi semua tidak relevan untuk mengetahui ASM.
Saya selalu berpikir bahasa tingkat yang lebih tinggi dikompilasi menjadi objek (kode mesin) atau kode semu, dan tidak ke ASM.
Frank R.
@ FrankComputer benar, tetapi kode mesin byte cukup banyak peta 1: 1 untuk instruksi perakitan, sehingga Anda dapat dengan mudah menerjemahkan antara objek kode dan ASM (mendekompilasi atau merakit)
dbr
2
@ FrankComputer terakhir kali saya melihat gcc mengkompilasi C / C ++ / fortran / java / ada / etc ke kode byte internal, dan kode byte internal untuk assembler. Kemudian mengirimkan kode assembler ini ke assembler untuk mengubahnya menjadi kode mesin.
ctrl-alt-delor