Αν κάνεις κάτι τέτοιο, η διαχείριση μνήμης είναι το μικρότερο από τα προβλήματα σου. Τί επίδραση θα έχει αυτό το statement στο σύστημα σου? Πόσα μπλοκαρίσματα θα δημιουργήσει? Γιατί θέλεις να τραβήξεις όλα αυτά τα δεδομένα στον client? Γιατί θέλεις να δουλέψεις με τόσα δεδομένα με τη μία?
Οι DataReaders δεν προσφέρουν κάποια διαφορετική προσέγγιση. Ένας cursors δουλεύει με ένα row τη φορά. Η διαφορά μεταξύ των διαφόρων τύπων cursor είναι αν επιτρέπουν να πας προς τα πίσω ή μόνο προς τα εμπρός, αν επιτρέπεται να αλλάξεις το row ή όχι κλπ. Ανάλογα με την υλοποίηση του, ένας DataReader θα χρησιμοποιήσει τον γρηγορότερο τύπο cursor (τυπικά read-only, forward-only) για να επιστρέψει τα αποτελέσματα όσο το δυνατόν πιο γρήγορα. Άρα δεν υπάρχει κάποια διαφορετική προσέγγιση με τους DataReaders.
Το τί θα πρέπει να κάνεις τελικά εξαρτάται από το πως και γιατί θέλεις να επεξεργαστείς τόσα δεδομένα.
- Μπορεί να υπάρχει πρόβλημα με την κανονικοποίηση της βάσης. Μπορεί να υπάρχουν στις εγγραφές δεδομένα τα οποία δεν έπρεπε να είναι εκεί, για παράδειγμα ποσοστά προμηθειών. Σε αυτή την περίπτωση είναι καλύτερο να διορθώσες το σχήμα της βάσης παρά να προσπαθείς να βρεις ένα τρόπο να πειράξεις όλα τα δεδομένα. Μπορεί να φαίνεται ότι θα πάρει περισσότερο χρόνο, αλλά στο τέλος θα σε γλυτώσει από πολλούς μπελάδες.
- Μπορεί να υπάρχουν δεδομένα τα οποία όντως πρέπει να τροποποιηθούν μαζικά. Σε τέτοιες περιπτώσεις ή καλύτερη λύση είναι να φτιάξεις ένα stored procedure το οποίο θα εκτελεί όλες τις αλλαγές στη βάση, χρησιμοποιώντας cursors. Θα πρέπει να λάβεις υπόψη πόσο συχνά θα καλείται αυτό το stored procedure και πόσο σύντομα θέλεις τα αποτελέσματα του. Αν για παράδειγμα μπορείς να καθυστερήσεις την εκτέλεση του για το βράδυ, μπορείς να χρησιμοποιήσεις ένα cursors χωρίς να σε απασχολεί αν κάποιοι άλλοι θα διαβάζουν τα στοιχεία που μόλις πείραξες. Αν πρέπει να το κάνεις κατά τη διάρκεια της ημέρας, ίσως είναι καλύτερο να δουλεύεις με batch εγγραφών, π.χ. 5000 τη φορά, έτσι ώστε να μην εμποδίζεις άλλους.
- Μπορεί να θέλεις να φτιάξεις reports. Σε αυτή την περίπτωση είναι προτιμότερο να φτιάξεις κάποιους reporting πίνακες στους οποίους θα μεταφέρεις τα δεδομένα που χρειάζεσαι για το reporting, π.χ. κάθε βράδυ, ή μερικές φορές τη μέρα. Έτσι και τα report σου θα φτιάχνονται ευκολότερα και θα έχεις να δουλέψεις με λιγότερα δεδομένα κάθε φορά.
Σχεδόν σε καμμία περίπτωση δεν θα πρέπει η μαζική επεξεργασία να γίνει στον client ή στον application server. Ναι, λέμε ότι δεν πρέπει να υπάρχει business logic στη βάση, αλλά αυτό το λέμε για επεξεργασία transactions. Ένα σύστημα δεν κάνει μόνο business transactions. Οι μαζικές αλλαγές και το reporting πρέπει να γίνονται όσο πιο κοντά στα δεδομένα είναι δυνατόν, δηλαδή στη βάση.
Έχει τύχει να δουλέψω σε σύστημα στο οποίο υπήρξε βελτίωση περίπου 19200 φορές όταν μετακινήθηκε η επεξεργασία κάποιων reports από τον client στη βάση: από 4 ημέρες ο χρόνος κατέβηκε στις 2 ώρες, χωρίς τη χρήση ειδικών πινάκων για reporting. Διαφορετικά θα μπορούσε να κατέβει στα 15-30 λεπτά.
Παναγιώτης Καναβός, Freelancer
Twitter: http://www.twitter.com/pkanavos