Sobes.tech
Junior

Τι είναι ο παραλληλισμός στον προγραμματισμό;

sobes.tech AI

Απάντηση από AI

Παραλληλισμός στον προγραμματισμό είναι η εκτέλεση πολλαπλών εργασιών ταυτόχρονα ή η ψευδαίσθηση ταυτόχρονης εκτέλεσης, που επιτρέπει την αύξηση της απόδοσης και της ανταπόκρισης των εφαρμογών.

Διακρίνονται διάφορα είδη παραλληλισμού:

  • Πολυεπεξεργασία (Multiprocessing): Χρησιμοποιεί πολλαπλές ανεξάρτητες διεργασίες, καθεμία με το δικό της χώρο διευθύνσεων. Αυτό ξεπερνά τον περιορισμό του GIL (Global Interpreter Lock) στο CPython και είναι κατάλληλο για εργασίες που χρησιμοποιούν έντονα την CPU.

    import multiprocessing
    import time
    
    def worker(num):
        """Μια εργασία"""
        time.sleep(1)
        print(f'Εργάτης {num} τελείωσε')
    
    if __name__ == '__main__':
        διεργασίες = []
        for i in range(5):
            p = multiprocessing.Process(target=worker, args=(i,))
            διεργασίες.append(p)
            p.start()
    
        for p in διεργασίες:
            p.join()
        print("Όλοι οι εργάτες τελείωσαν")
    
  • Πολυνηματικότητα (Multithreading): Χρησιμοποιεί πολλά νήματα εντός μιας διαδικασίας, που μοιράζονται τον ίδιο χώρο διευθύνσεων. Λόγω του GIL στο CPython, τα νήματα δεν εκτελούνται παράλληλα σε διαφορετικούς πυρήνες για εργασίες CPU-bound, αλλά είναι αποτελεσματικά για εργασίες I/O-bound.

    import threading
    import time
    
    def worker(num):
        """Μια εργασία"""
        time.sleep(1) # Προσομοίωση λειτουργίας I/O
        print(f'Νήμα {num} τελείωσε')
    
    νήματα = []
    for i in range(5):
        t = threading.Thread(target=worker, args=(i,))
        νήματα.append(t)
        t.start()
    
    for t in νήματα:
        t.join()
    print("Όλα τα νήματα τελείωσαν")
    
  • Ασύγχρονος προγραμματισμός (Asyncio): Χρησιμοποιεί ένα μόνο νήμα και έναν βρόχο γεγονότων (event loop) για τη διαχείριση της εκτέλεσης εργασιών. Κατάλληλο για εφαρμογές υψηλού φόρτου I/O-bound και web servers. Δεν μπλοκάρει την εκτέλεση κατά την αναμονή για I/O.

    import asyncio
    import time
    
    async def worker(num):
        """Μια ασύγχρονη εργασία"""
        await asyncio.sleep(1) # Ασύγχρονη αναμονή I/O
        print(f'Ασύγχρονος εργάτης {num} τελείωσε')
    
    async def main():
        tasks = []
        for i in range(5):
            task = asyncio.create_task(worker(i))
            tasks.append(task)
        await asyncio.gather(*tasks)
        print("Όλοι οι ασύγχρονοι εργάτες τελείωσαν")
    
    if __name__ == '__main__':
        asyncio.run(main())
    

Η επιλογή προσέγγισης εξαρτάται από τη φύση της εργασίας:

Προσέγγιση CPU-bound εργασίες I/O-bound εργασίες GIL Χρήση μνήμης
Πολυεπεξεργασία Εξαιρετικό Καλό Ξεπερνά Μεγάλο (ιδιωτική διαδικασία)
Πολυνηματικότητα Κακό (λόγω GIL) Εξαιρετικό Μπλοκάρει Μικρό (κοινή διαδικασία)
Ασύγχρονο Κακό Εξαιρετικό Δεν μπλοκάρει Μικρό (ένα νήμα)

Ο παραλληλισμός απαιτεί προσεκτική διαχείριση συγχρονισμού και πόρων για την αποφυγή συνθηκών αγώνα και deadlocks.