Pensar en C++ (Volumen 1) - Grupo ARCO
Pensar en C++ (Volumen 1) - Grupo ARCO Pensar en C++ (Volumen 1) - Grupo ARCO
✐ ✐ ✐ “Volumen1” — 2012/1/12 — 13:52 — page 180 — #218 ✐ Capítulo 5. Ocultar la implementación } ///:~ La clase (class) en un concepto OOP fundamental en C++. Es una de la palabras clave que no se pondrán en negrita en este libro - es incomodo pues se repite mucho. El cambio a clases es tan importante que sospecho que Stroustrup hubiese preferido eliminar completamente struct, pero la necesidad de compatibilidad con C no lo hubiese permitido. Mucha gente prefiere crear clases a la manera struct en vez de a la mánera class, pues sustituye el «por-defecto-private» de class empezando con los elementos public: class X { public: void miembro_de_interfaz(); private: void miembro_privado(); int representacion_interna; }; El porqué de esto es que tiene más sentido ver primero lo que más interesa, el programador cliente puede ignorar todo lo que dice private. De hecho, la única razón de que todos los miembros deban ser declarados en la clase es que el compilador sepa como de grande son los objetos y pueda colocarlos correctamente, garantizando así la consistencia. De todas formas, los ejemplos en este libro pondrán los miembros privados primero, así: class X { void private_function(); int internal_representation; public: void interface_function(); }; Alguna gente incluso decora sus nombres privados class Y { public: void f(); private: int mX; // "Self-decorated" name }; Como mX esta ya oculto para Y, la m (de «miembro») es innecesaria. De todas formas, en proyectos con muchas variables globales (algo que debe evitar a toda costa, aunque a veces inevitable en proyectos existentes), es de ayuda poder distinguir variables globales de atributos en la definición de los métodos. 180 ✐ ✐ ✐ ✐
✐ ✐ ✐ “Volumen1” — 2012/1/12 — 13:52 — page 181 — #219 ✐ 5.5. La clase 5.5.1. Modificaciones en Stash para usar control de acceso Tiene sentido coger el ejemplo del capítulo 4 y modificarlo para usar clases y control de acceso. Dese cuenta de cómo la parte de la interfaz a usar en la programación cliente está claramente diferenciada, así no hay posibilidad de que el programador cliente manipule accidentalmente parte de la clase que no debería. //: C05:Stash.h // Converted to use access control #ifndef STASH_H #define STASH_H class Stash { int size; // Size of each space int quantity; // Number of storage spaces int next; // Next empty space // Dynamically allocated array of bytes: unsigned char* storage; void inflate(int increase); public: void initialize(int size); void cleanup(); int add(void* element); void* fetch(int index); int count(); }; #endif // STASH_H ///:~ La función inflate() se ha hecho private porque solo es usada por la función add() y por tanto es parte de la implementación interna, no de la interfaz. Esto significa que, más tarde, puede cambiar la implementación interna para usar un sistema de gestión de memoria diferente. Aparte del nombre del archivo include, la cabecera de antes es lo único que ha sido cambiado para este ejemplo. El fichero de implementación y de prueba son los mismos. 5.5.2. Modificar Stack para usar control de acceso Como un segundo ejemplo, aquí está Stack convertido en clase. Ahora la estructura anidada es private, lo que es bueno pues asegura que el programador cliente no tendrá que fijarse ni depender de la representación interna de Stack: //: C05:Stack2.h // Nested structs via linked list #ifndef STACK2_H #define STACK2_H class Stack { struct Link { void* data; Link* next; void initialize(void* dat, Link* nxt); 181 ✐ ✐ ✐ ✐
- Page 167 and 168: ✐ ✐ ✐ “Volumen1” — 2012
- Page 169 and 170: ✐ ✐ ✐ “Volumen1” — 2012
- Page 171 and 172: ✐ ✐ ✐ “Volumen1” — 2012
- Page 173 and 174: ✐ ✐ ✐ “Volumen1” — 2012
- Page 175 and 176: ✐ ✐ ✐ “Volumen1” — 2012
- Page 177 and 178: ✐ ✐ ✐ “Volumen1” — 2012
- Page 179 and 180: ✐ ✐ ✐ “Volumen1” — 2012
- Page 181 and 182: ✐ ✐ ✐ “Volumen1” — 2012
- Page 183 and 184: ✐ ✐ ✐ “Volumen1” — 2012
- Page 185 and 186: ✐ ✐ ✐ “Volumen1” — 2012
- Page 187 and 188: ✐ ✐ ✐ “Volumen1” — 2012
- Page 189 and 190: ✐ ✐ ✐ “Volumen1” — 2012
- Page 191 and 192: ✐ ✐ ✐ “Volumen1” — 2012
- Page 193 and 194: ✐ ✐ ✐ “Volumen1” — 2012
- Page 195 and 196: ✐ ✐ ✐ “Volumen1” — 2012
- Page 197 and 198: ✐ ✐ ✐ “Volumen1” — 2012
- Page 199 and 200: ✐ ✐ ✐ “Volumen1” — 2012
- Page 201 and 202: ✐ ✐ ✐ “Volumen1” — 2012
- Page 203 and 204: ✐ ✐ ✐ “Volumen1” — 2012
- Page 205 and 206: ✐ ✐ ✐ “Volumen1” — 2012
- Page 207 and 208: ✐ ✐ ✐ “Volumen1” — 2012
- Page 209 and 210: ✐ ✐ ✐ “Volumen1” — 2012
- Page 211 and 212: ✐ ✐ ✐ “Volumen1” — 2012
- Page 213 and 214: ✐ ✐ ✐ “Volumen1” — 2012
- Page 215 and 216: ✐ ✐ ✐ “Volumen1” — 2012
- Page 217: ✐ ✐ ✐ “Volumen1” — 2012
- Page 221 and 222: ✐ ✐ ✐ “Volumen1” — 2012
- Page 223 and 224: ✐ ✐ ✐ “Volumen1” — 2012
- Page 225 and 226: ✐ ✐ ✐ “Volumen1” — 2012
- Page 227 and 228: ✐ ✐ ✐ “Volumen1” — 2012
- Page 229 and 230: ✐ ✐ ✐ “Volumen1” — 2012
- Page 231 and 232: ✐ ✐ ✐ “Volumen1” — 2012
- Page 233 and 234: ✐ ✐ ✐ “Volumen1” — 2012
- Page 235 and 236: ✐ ✐ ✐ “Volumen1” — 2012
- Page 237 and 238: ✐ ✐ ✐ “Volumen1” — 2012
- Page 239 and 240: ✐ ✐ ✐ “Volumen1” — 2012
- Page 241 and 242: ✐ ✐ ✐ “Volumen1” — 2012
- Page 243 and 244: ✐ ✐ ✐ “Volumen1” — 2012
- Page 245 and 246: ✐ ✐ ✐ “Volumen1” — 2012
- Page 247 and 248: ✐ ✐ ✐ “Volumen1” — 2012
- Page 249 and 250: ✐ ✐ ✐ “Volumen1” — 2012
- Page 251 and 252: ✐ ✐ ✐ “Volumen1” — 2012
- Page 253 and 254: ✐ ✐ ✐ “Volumen1” — 2012
- Page 255 and 256: ✐ ✐ ✐ “Volumen1” — 2012
- Page 257 and 258: ✐ ✐ ✐ “Volumen1” — 2012
- Page 259 and 260: ✐ ✐ ✐ “Volumen1” — 2012
- Page 261 and 262: ✐ ✐ ✐ “Volumen1” — 2012
- Page 263 and 264: ✐ ✐ ✐ “Volumen1” — 2012
- Page 265 and 266: ✐ ✐ ✐ “Volumen1” — 2012
- Page 267 and 268: ✐ ✐ ✐ “Volumen1” — 2012
✐<br />
✐<br />
✐<br />
“Volum<strong>en</strong>1” — 2012/1/12 — 13:52 — page 180 — #218<br />
✐<br />
Capítulo 5. Ocultar la implem<strong>en</strong>tación<br />
} ///:~<br />
La clase (class) <strong>en</strong> un concepto OOP fundam<strong>en</strong>tal <strong>en</strong> <strong>C++</strong>. Es una de la palabras<br />
clave que no se pondrán <strong>en</strong> negrita <strong>en</strong> este libro - es incomodo pues se repite mucho.<br />
El cambio a clases es tan importante que sospecho que Stroustrup hubiese preferido<br />
eliminar completam<strong>en</strong>te struct, pero la necesidad de compatibilidad con C no lo<br />
hubiese permitido.<br />
Mucha g<strong>en</strong>te prefiere crear clases a la manera struct <strong>en</strong> vez de a la mánera<br />
class, pues sustituye el «por-defecto-private» de class empezando con los elem<strong>en</strong>tos<br />
public:<br />
class X {<br />
public:<br />
void miembro_de_interfaz();<br />
private:<br />
void miembro_privado();<br />
int repres<strong>en</strong>tacion_interna;<br />
};<br />
El porqué de esto es que ti<strong>en</strong>e más s<strong>en</strong>tido ver primero lo que más interesa, el programador<br />
cli<strong>en</strong>te puede ignorar todo lo que dice private. De hecho, la única razón<br />
de que todos los miembros deban ser declarados <strong>en</strong> la clase es que el compilador sepa<br />
como de grande son los objetos y pueda colocarlos correctam<strong>en</strong>te, garantizando<br />
así la consist<strong>en</strong>cia.<br />
De todas formas, los ejemplos <strong>en</strong> este libro pondrán los miembros privados primero,<br />
así:<br />
class X {<br />
void private_function();<br />
int internal_repres<strong>en</strong>tation;<br />
public:<br />
void interface_function();<br />
};<br />
Alguna g<strong>en</strong>te incluso decora sus nombres privados<br />
class Y {<br />
public:<br />
void f();<br />
private:<br />
int mX; // "Self-decorated" name<br />
};<br />
Como mX esta ya oculto para Y, la m (de «miembro») es innecesaria. De todas<br />
formas, <strong>en</strong> proyectos con muchas variables globales (algo que debe evitar a toda costa,<br />
aunque a veces inevitable <strong>en</strong> proyectos exist<strong>en</strong>tes), es de ayuda poder distinguir<br />
variables globales de atributos <strong>en</strong> la definición de los métodos.<br />
180<br />
✐<br />
✐<br />
✐<br />
✐