Τα πάντα για την C

...του ubuntu και έργων ΕΛ/ΛΑΚ (Έργα-Οδηγοί-Προτάσεις)

Συντονιστής: konnn

Re: Τα πάντα για την C

Δημοσίευσηαπό Ilias95 » 25 Φεβ 2012, 15:22

migf1 έγραψε:ΥΓ. Δεν το βρίσκω το upc.c πρόγραμμα στην ενότητα 4.1 που λέει.

Σελ. 57
Ilias95
saintTUX
saintTUX
 
Δημοσιεύσεις: 1548
Εγγραφή: 29 Απρ 2011, 23:26
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό migf1 » 25 Φεβ 2012, 15:29

Πάντως όταν θέλεις να διαβάζεις ξεχωριστά ψηφία, μια εναλλακτική πρόταση του "%1d" που τα διαβάζει σαν μονοψήφιους ακέραιους, είναι να τα διαβάζεις ως χαρακτήρες, με "%c".

Π.χ...
Μορφοποιημένος Κώδικας: Επιλογή όλων
...
char d1, d2, d3; /* three digits, as characters */
printf('Enter a 3-digit integer: ");
mySCANF( "%c%c%c", &d1, &d2, &d3 );
printf( "%c%c%c\n", d1, d2, d3 );
...

Η βασική διαφορά είναι πως σου γλιτώνει μνήμη... ο κάθε χαρακτήρας καταλαμβάνει 1 byte μνήμης, ενώ ο κάθε ακέραιος καταλαμβάνει τουλάχιστον 2 bytes μνήμης (συνήθως 4... εκτός από τον τύπο char, για τους υπόλοιπους το στάνταρ καθορίζει ελάχιστες χωρητικότητες, το αφήνει δηλαδή ανοιχτό να καταλαμβάνουν περισσότερα bytes από ότι ορίζει το στάνταρ).
Go under the hood with C: Pointers, Strings, Linked Lists
Άβαταρ μέλους
migf1
powerTUX
powerTUX
 
Δημοσιεύσεις: 2082
Εγγραφή: 03 Ιουν 2011, 16:32
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό Star_Light » 25 Φεβ 2012, 15:42

Ilias95 έγραψε:
Διάβασε το hint που δίνει.


Aμα διαβασω το hint που δινει ειναι ουτε 1 λεπτο δουλεια !
Τετοιες ασκησεις μας έβαζαν στην C στην σχολη. Δεν ειχαμε ποτε
δεικτες ή συμβολοσειρες σαν εργασιες ;)

To ειδα το hint δεν ειναι αυτο το προβλημα μου ρε συ.
Τελευταία επεξεργασία από Star_Light και 25 Φεβ 2012, 15:50, έχει επεξεργασθεί 1 φορά/ες συνολικά
Γνώσεις ⇛ Linux: Βασικές ┃ Προγραμματισμός: Δέν θέλω μεροκάματο , θέλω C και κακο θάνατο! ┃ Αγγλικά: Lower
Λειτουργικό ⇛ Ubuntu 10.10 σε Dual Boot με Windows 7
Προδιαγραφές ⇛ Επεξεργαστής : Intel(R) Core(TM) i3 CPU 540 @3.07Ghz (64bit)
RAM : Kingston 2GB
HDD : Coreshare 500GB
Κάρτα Γραφικών : Intel Corporation Core Processor Integrated Graphics Controller(rev 18) (prog-if 00 [VGA controller]) [8086:0042]
Star_Light
superbTUX
superbTUX
 
Δημοσιεύσεις: 2787
Εγγραφή: 01 Μάιος 2010, 21:07
Τοποθεσία: Αθήνα
IRC: Star_Light
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό Star_Light » 25 Φεβ 2012, 15:43

O migf1 σαν εργασια στο 1ο εξαμηνο ειχε να φτιαξει δικο του compiler :lol: :lol:
εμεις ειχαμε να φτιάξουμε ενα προγραμμα που κανει προσθεση / αφαιρεση / διαιρεση / πολλαπλασιασμο !!!!
Γνώσεις ⇛ Linux: Βασικές ┃ Προγραμματισμός: Δέν θέλω μεροκάματο , θέλω C και κακο θάνατο! ┃ Αγγλικά: Lower
Λειτουργικό ⇛ Ubuntu 10.10 σε Dual Boot με Windows 7
Προδιαγραφές ⇛ Επεξεργαστής : Intel(R) Core(TM) i3 CPU 540 @3.07Ghz (64bit)
RAM : Kingston 2GB
HDD : Coreshare 500GB
Κάρτα Γραφικών : Intel Corporation Core Processor Integrated Graphics Controller(rev 18) (prog-if 00 [VGA controller]) [8086:0042]
Star_Light
superbTUX
superbTUX
 
Δημοσιεύσεις: 2787
Εγγραφή: 01 Μάιος 2010, 21:07
Τοποθεσία: Αθήνα
IRC: Star_Light
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό migf1 » 25 Φεβ 2012, 16:19

Ilias95 έγραψε:
migf1 έγραψε:ΥΓ. Δεν το βρίσκω το upc.c πρόγραμμα στην ενότητα 4.1 που λέει.

Σελ. 57

Αχα, thanks!

Από ότι βλέπω, κάνει πράξεις κατόπιν με τα ψηφία (digits). Οπότε αν τα διαβάζεις ως χαρακτήρες, θα πρέπει πρώτα να τα μετατρέψεις σε αντίστοιχα int... βασικά ο τύπος char στη C είναι υποσύνολο του int. Ο κάθε χαρακτήρας αντιστοιχεί στον ακέραιο αριθμό του ASCII table.

Οπότε για παράδειγμα, ο χαρακτήρας '0' αντιστοιχεί στον ακέραιο 48 (σύμφωνα με το ASCII table), ο 'A' αντιστοιχεί στον ακέραιο 65, και πάει λέγοντας. Επειδή ο τύπος char είναι ορισμένος fixed σε 1 byte μνήμης, το εύρος των έγκυρων τιμών του είναι από 0 έως 255 αν πρόκειται για unsigned char ή από -128 έως 127 αν πρόκειται για signed char (σημείωση: το σκέτο char δεν γνωρίζουμε αν είναι signed ή unsigned ... το στάνταρ το αφήνει στην κρίση του κάθε compiler, συνήθως είναι signed αλλά δεν μπορούμε να το θεωρήσουμε δεδομένο για όλους τους compilers).

Άρα λοιπόν, στη C (και σε πολλές άλλες γλώσσες) μπορούμε να διαβάσουμε μια μεταβλητή ως char και να την τυπώσουμε ως int. Δες για παράδειγμα τον παρακάτω κώδικα:

Μορφοποιημένος Κώδικας: Επιλογή όλων
#include <stdio.h>
#include "myextras.h"

int main( void )
{
char ch;
printf( "Enter a character: " );
mySCANF( "%c", &ch );

printf( "print as char: %c\n", ch );
printf( "print as int : %d\n", ch );

return 0;
}

Διαβάζει τη μεταβλητή ch ορισμένη ως char και κατόπιν την τυπώνει και ως char αλλά και ως int (το ASCII code του ch δηλαδή).

Μπορείς να κάνεις και το ανάποδο, να διαβάσεις δηλαδή μια μεταβλητή int και κατόπιν να την τυπώσεις σαν char αλλά αν ο χρήστης σου δώσει ως int στην είσοδο τιμή μεγαλύτερη ή μικρότερη από το εύρος τιμών που μπορεί να χωρέσει σε char, τότε ο χαρακτήρας αυτό που θα τυπωθεί θα είναι λάθος, δεν θα αντιστοιχεί δηλαδή στον int που διάβασες από την είσοδο!

Τώρα, εφόσον οι χαρακτήρες είναι επί της ουσίας πολύ μικροί int μπορούμε κάνουμε πράξεις πάνω τους (και μάλιστα μπορούμε να τους δηλώνουμε και σαν int αν θέλουμε).

Ο παρακάτω κώδικας διαβάζει έναν χαρακτήρα από την κύρια είσοδο και τυπώνει αν ήταν αριθμητικό ψηφίο ή όχι...

Μορφοποιημένος Κώδικας: Επιλογή όλων
#include <stdio.h>
#include "myextras.h"

int main( void )
{
char ch;

mySCANF( "%c", &ch );
if ( ch < '0' || ch > '9' )
printf( "%c is NOT a digit\n", ch );
else
printf( "%c is a digit\n", ch );

return 0;
}


Αν βεβαιωθείς πως ένας χαρακτήρας είναι ψηφίο, τότε είναι πολύ εύκολο να τον χρησιμοποιήσεις ως αριθμο σε πράξεις. Δες για παράδειγμα τον παρακάτω κώδικα που διαβάζει ένα-ένα 3 ψηφία ως χαρακτήρες και τα μετατρέπει σε ενιάιο ακέραιο αριθμό, τον οποίο και τυπώνει...

Μορφοποιημένος Κώδικας: Επιλογή όλων
#include <stdio.h>
#include "myextras.h"

#define ISDIGIT( ch ) ( (ch) >= '0' && (ch) <= '9' )

int main( void )
{
char c1, c2, c3;
int n;

mySCANF( "%c%c%c", &c1, &c2, &c3 ); /* ανάγνωση 3 χαρακτήρων, ένας για κάθε ψηφίο */

if ( !ISDIGIT(c1) )
c1 = '0';
if ( !ISDIGIT(c2) )
c2 = '0';
if ( !ISDIGIT(c3) )
c3 = '0';

n = (c1 - '0') * 100 + (c2 - '0') * 10 + (c3 - '0');

printf( "Print as a whole integer: %d\n", n );

return 0;
}


Αν κάποιος από τους χαρακτήρες c1, c2, c3 δοθεί στην είσοδο ως μη ψηφίο (π.χ. ως γράμμα ή ως σημείο στίξης, κλπ) μετατρέπεται από το αντίστοιχο if στον χαρακτήρα '0' (που έχει ASCII code 48).

Στις πράξεις τώρα, για να βρούμε όχι το ASCII code αλλά ποιον αριθμό από 0 έως 9 απεικονίζει ο κάθε χαρακτήρας c?, τον αφαιρούμε από τον χαρακτήρα '0' (αυτός είναι ο 1ος αριθμητικός χαρακτήρας στον πίνακα ASCII.

Δηλαδή αν π.χ. ο c1 δοθεί ως '7' τότε το ('7' - '0') μεταφράζεται από τον compiler σε (55 - 48) = 7 ... 55 είναι το ASCII code του χαρακτήρα '7' και 48 είναι το ASCII code του χαρακτήρα '0'.

Οπότε το n υπολογίζεται σωστά :)

Με λίγα λόγια, στη C μπορούμε να διαχειριστούμε τα char σαν είναι int αρκεί να φροντίζουμε οι τιμές τους να βρίσκονται μέσα στο εύρος τιμών του τύπου char ;)
Τελευταία επεξεργασία από migf1 και 26 Φεβ 2012, 11:29, έχει επεξεργασθεί 5 φορά/ες συνολικά
Go under the hood with C: Pointers, Strings, Linked Lists
Άβαταρ μέλους
migf1
powerTUX
powerTUX
 
Δημοσιεύσεις: 2082
Εγγραφή: 03 Ιουν 2011, 16:32
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό migf1 » 25 Φεβ 2012, 16:24

@StartLight: Κοντά έπεσες :) Αλλά όχι στο 1ο εξάμηνο, στο 3ο... στο 1ο είχαμε ξεκινήσει με Pascal, στο 2ο ξεκινήσαμε C (μαζί με μερικές άλλες... Ada, Modula-2, Lisp) και στο 3ο κάναμε 2-3 άλλες επιφανειακά αλλά κατά βάση συνεχίσαμε με C + Αssembly, με την οποία Assembly είχαμε φτιάξει editor, compiler, assembler, linker και loader μιας απλοποιημένης γλώσσας που έμοιαζε με Pascal.
Go under the hood with C: Pointers, Strings, Linked Lists
Άβαταρ μέλους
migf1
powerTUX
powerTUX
 
Δημοσιεύσεις: 2082
Εγγραφή: 03 Ιουν 2011, 16:32
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό migf1 » 25 Φεβ 2012, 16:37

Έκανα κάτι διορθώσεις στους κώδικες του παραπάνω ποστ, γιατί τους γράφω απευθείας στο φόρουμ χωρίς να τους δοκιμάζω και είχαν λάθη (π.χ. % αντί για & στην mySCANF() ... κάπου αλλού δήλωνα μια μεταβλητή digit αλλά μετά την χρησιμοποιούσα ως ch :lol: και κατί τέτοια ).
Go under the hood with C: Pointers, Strings, Linked Lists
Άβαταρ μέλους
migf1
powerTUX
powerTUX
 
Δημοσιεύσεις: 2082
Εγγραφή: 03 Ιουν 2011, 16:32
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό migf1 » 25 Φεβ 2012, 16:40

Διόρθωσα κι άλλα :lol:

Πάω σπίτι, χάζεψα :lol:
Go under the hood with C: Pointers, Strings, Linked Lists
Άβαταρ μέλους
migf1
powerTUX
powerTUX
 
Δημοσιεύσεις: 2082
Εγγραφή: 03 Ιουν 2011, 16:32
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό Ilias95 » 25 Φεβ 2012, 16:49

migf1 έγραψε:Ο παρακάτω κώδικας διαβάζει έναν χαρακτήρα από την κύρια είσοδο και τυπώνει αν ήταν αριθμητικό ψηφίο ή όχι...

Μορφοποιημένος Κώδικας: Επιλογή όλων
#include <stdio.h>
#include "myextras.h"

int main( void )
{
char ch;

mySCANF( "%c", &ch );
if ( ch < '0' || ch > '9' )
printf( "%c is NOT a digit\n", ch );
else
printf( "%c is a digit\n", ch );

return 0;
}

Στην σύγκριση ch < '0' τι ακριβώς συγκρίνουμε; Η μεταβλητή ch θα είναι char (όπως δηλώθηκε) ή int; Επίσης το '0' είναι char;
Ακόμα απ' ότι κατάλαβα παίζουν ρόλο τα εισαγωγικά. Αν αντί για '0' γράψω "0" ο compiler θα μου πει για σύγκριση μεταξύ pointer και integer.
Ilias95
saintTUX
saintTUX
 
Δημοσιεύσεις: 1548
Εγγραφή: 29 Απρ 2011, 23:26
Εκτύπωση

Re: Τα πάντα για την C

Δημοσίευσηαπό Star_Light » 25 Φεβ 2012, 16:56

Η μεταβλητή char ειναι "τύπου int" επειδη οι χαρακτήρες στην C έχουν αριθμητική φύση
λογω της αποθηκευσής τους στο συστημα μας. (ASCII)

πχ το παρακάτω

Κώδικας: Επιλογή όλων


#include<stdio.h>

int main(void)
{
char mychar='A';

printf("%c %d" , mychar , mychar);

return 0;
}


Θα εκτυπώσει τον χαρακτήρα Α και μετα την αριθμητική του τιμη σε ASCII
Τελευταία επεξεργασία από Star_Light και 25 Φεβ 2012, 17:01, έχει επεξεργασθεί 2 φορά/ες συνολικά
Γνώσεις ⇛ Linux: Βασικές ┃ Προγραμματισμός: Δέν θέλω μεροκάματο , θέλω C και κακο θάνατο! ┃ Αγγλικά: Lower
Λειτουργικό ⇛ Ubuntu 10.10 σε Dual Boot με Windows 7
Προδιαγραφές ⇛ Επεξεργαστής : Intel(R) Core(TM) i3 CPU 540 @3.07Ghz (64bit)
RAM : Kingston 2GB
HDD : Coreshare 500GB
Κάρτα Γραφικών : Intel Corporation Core Processor Integrated Graphics Controller(rev 18) (prog-if 00 [VGA controller]) [8086:0042]
Star_Light
superbTUX
superbTUX
 
Δημοσιεύσεις: 2787
Εγγραφή: 01 Μάιος 2010, 21:07
Τοποθεσία: Αθήνα
IRC: Star_Light
Εκτύπωση

ΠροηγούμενηΕπόμενο

Επιστροφή στο Ανάπτυξη Λογισμικού / Αλγόριθμοι