Академический Документы
Профессиональный Документы
Культура Документы
html
Contents
Um tipo abstrato de dado é um tipo definido pelo programador com um conjunto de valores e uma
coleção de operações sobre estes valores. As operações devem ser consistentes com os tipos
dos valores.
Para a implementação de um tipo abstrato de dado, o programador deve escolher uma
representação de dados de um dado abstrato usando os tipos de dados existentes e, implementar
as operações permitidas sobre estes dados com as instruções da linguagem de programação
desejada.
ORIENTAÇÃO A OBJETOS
A idéia fundamental de linguagens orientadas a objetos é a possibilidade de combinar num
único registro campos que conterão dados e campos que são funções para operar os campos de
1 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
dados do registro. Um tipo abstrato de dado que suporta este conceito é a classe.
CLASSE
Dados públicos;
Dados privados;
Dados protegidos;
Funções-membro;
Construtores;
Destrutores;
Classes Amigas.
class emp
{
private :
int empno;
char ename[10 + 1];
char job[9 + 1];
int mgr;
long int hiredate;
long int sal;
long int comm;
int deptno;
public :
emp(); // construtor
emp(int emp, char nome[10 + 1], char j[9 + 1], int m,
long int h, long int s, long int c, int d);
~emp(); // destrutor , executa a exclusão
int inclusão();
void alteração();
void consulta();
void tela();
void menu();
int le_disco(fstream *fio);
int grava_disco(fstream *fio);
int abre_arq(fstream *fio);
long num_reg(fstream *fio);
};
DADOS PRIVADOS
Os dados privados são acessados somente pelas funções-membro da classe. Dizemos que os dados
privados são ocultos para os dados não pertencentes a classe.
Exemplo : Na classe emp declarada abaixo, todas as variáveis foram declaradas como dados
privados. Isto é feito para garantir maior integridade e segurança aos dados manipulados de
um objeto.
class emp
{
private :
int empno;
char ename[10 + 1];
char job[9 + 1];
int mgr;
long int hiredate;
long int sal;
long int comm;
int deptno;
};
2 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
DADOS PÚBLICOS
Dados públicos podem ser acessados por qualquer objeto de uma classe.
Abaixo é descrito um exemplo de dados públicos.
Dados públicos, normalmente, são as funções-membro de uma classe.
class emp
{
public :
emp(); // construtor
emp(int emp, char nome[10 + 1], char j[9 + 1], int m,
long int h, long int s, long int c, int d);
~emp(); // destrutor , executa a exclusão
int inclusão();
void alteração();
void consulta();
void tela();
void menu();
int le_disco(fstream *fio);
int grava_disco(fstream *fio);
int abre_arq(fstream *fio);
long num_reg(fstream *fio);
};
DADOS PROTEGIDOS
Ao invés de declararmos os dados de uma classe como privados podemos declará-los como
protegidos. A vantagem de utilizar isto é que os dados declarados como protegidos podem ser
acessados em caso de herança pela classe derivada e se forem declarados como privados a
classe derivada não terá acesso a eles.
class BASE
{
protected : Int secreto;
private : int ultra_secreto;
public : int publico;
};
class DERIV1 : public BASE
{
public :
int a = secreto; // ok
int b = ultra_secreto; // erro : não-acessível
int c = publico // ok
};
class DERIV2 : private BASE
{
public :
int a = secreto; // ok
int b = ultra_secreto; // erro : não-acessível
int c = publico // ok
} ;
INSTÂNCIA DE CLASSE
É importante salientar que uma classe é um tipo abstrato de dado e não um objeto. Quando
criamos uma variável do tipo da classe declarada, criamos um objeto desta classe.
FUNÇÃO-MEMBRO
3 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
Nós definimos as funções-membro dentro de uma classe e, somente os objetos destas classe
poderão ter acesso as mesmas. São o único meio de acesso aos campos de dados ou também
chamados dados privados. Abaixo é descrito um exemplo da função-membro tela declarada na
classe emp. Funções-membro também são chamadas de métodos.
Exemplo :
void emp::tela()
{
clrscr();
gotoxy(30,6);
cout << "Cadastro de Empresas";
gotoxy(10,8);
cout << "Código Empresa : ";
gotoxy(10,10);
cout << "Nome Empresa : ";
gotoxy(10,12);
cout << "Cargo : ";
gotoxy(10,14);
cout << "Código Gerente : ";
gotoxy(10,16);
cout << "Data : ";
gotoxy(10,18);
cout << "Salário : ";
gotoxy(10,20);
cout << "Comissão : ";
gotoxy(10,22);
cout << "Departamento : ";
};
CHAMADA A FUNÇÕES-MEMBRO
As funções-membro só podem ser chamadas quando associadas ao objeto específico pelo operador
ponto. Uma função-membro age sobre um objeto em particular e não sobre a classe como um todo.
Um exemplo : Se quisermos chamar a função-membro inclusão da classe emp, primeiro temos que
criar um objeto desta classe e depois chamar a função-membro, como segue :
emp obj.;
obj.inclusao();
A instrução de chamada a uma função-membro é denominada MENSAGEM.
DEFINIÇÃO DE FUNÇÕES-MEMBRO
As funções-membro podem ser definidas dentro da própria declaração da classe quanto fora
dela. Se for feita fora da definição da classe, devemos declarar dentro da classe o protótipo
da função-membro. Podemos então, declarar a função-membro em qualquer parte do programa.
Quando a declararmos, deveremos colocar antes do nome da função-membro nome da classe seguido
do operador "::" para identificar a qual classe ela pertence.
Exemplo : Se quiséssemos declarar a função-membro inclusão da classe emp em qualquer lugar do
programa devemos declarar como segue :
int emp::inclusao(parâmetros)
CONSTRUTOR
Construtor é uma função-membro que é executada quando é criado uma instância de classe. Isto
garante a inicialização de uma instância de classe. O nome do construtor é o mesmo que o nome
da classe. Podemos declarar um construtor de duas maneiras:
4 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
emp::emp() // construtor
{
empno = 0;
ename[0] = '\0';
job[0] = '\0';
mgr = 0;
hiredate = 0;
sal = 0;
comm = 0;
deptno = 0;
}
emp::emp( int emp, char nome[10 + 1], char j[9 + 1], int m, long int h,
long int s, long int c, int d)
{
empno = emp;
strcpy(ename,nome);
strcpy(job,j);
mgr = m;
hiredate = h;
sal = s;
comm = c;
deptno = d;
};
DESTRUTOR
Destrutor é uma função-membro que é executada quando é destruída uma instância de classe. O
nome do destrutor é o mesmo que o nome da classe precedido do caracter `~'. Abaixo é descrito
um exemplo da classe emp que diminui o valor do salário em um cada vez que um objeto é
destruído.
emp::~emp() // destrutor , executa a exclusão { sal - -; }
CLASSES INVARIANTES
Uma classe invariante é uma declaração sobre o corrente estado de uma instância de uma
classe. Tipos invariantes referem-se tipicamente somente para os dados membros de uma classe.
Todas as funções-membro da classe devem cooperar para preservar o estado da classe
invariante. Uma classe invariante é uma pós-condição implícita para cada função-membro. E, é
também uma pré-condição implícita para a função-membro exceto os construtores. Todas classes
devem providenciar um jeito de inicializar suas classes invariantes. A estrutura de um
construtor é o local mais apropriado. Um construtor é chamado quando uma classe é criada,
antes que o usuário possa chamar qualquer outra função-membro da classe. Entretanto, os
comandos do construtor devem inicializar os dados de uma instância de classe mantendo o
resultado da classe invariante sempre verdadeiro quando o construtor retornar o controle do
programa.
ENCAPSULAMENTO DE DADOS
O encapsulamento de dados em uma classe são os dados que são escondidos, ou seja, os dados
declarados como private. Com isto, somente funções-membro podem acessar os dados declarados
como private e não qualquer variável declarada como instância de uma classe. Um exemplo do
encapsulamento de dados é descrito abaixo através da declaração de variáveis da classe emp
como dados privados.
class emp
{
private :
int empno;
char ename[10 + 1];
char job[9 + 1];
int mgr;
long int hiredate;
long int sal;
5 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
POLIMORFISMO
HERANÇA
class < nome classe > : < nome da classe base >
Após a criação de uma classe derivada, esta tem acesso a todos os dados públicos da classe
base. Todos os métodos declarados como públicos da classe base estão automaticamente
disponíveis para a classe derivada. Se uma classe derivada quiser acessar os dados privados
da classe base não terá acesso. Para possibilitar este acesso, os dados privados na classe
base devem ser declarados como protegidos. A classe derivada pode acessar os métodos da
classe base como segue abaixo : · Após a declaração de um método na classe derivada,
coloca-se o operador ":" e o nome do método da classe base; como no exemplo abaixo :
class janela
{
protected :int linicio, cinicio, lfim, cfim;
public : janela();
janela(int li, int ci, int lf, int cf);
void box(char modo[] = "[]|-=+|");
};
class window : public janela // classe derivada (herança)
{
public :
window(): janela() {};
window(int li, int ci, int lf, int cf) : janela(li,cf,lf,cf){};
void cls();
void cursor(char lin, char col);
void centra(char lin, char s[]) ;
};
No exemplo acima, a classe derivada "window" possui em seu construtor uma chamada para o
contrutor da classe base janela.
Podemos também chamar um método da classe base como se fossemos chamar um método desta mesma
classe. No exemplo acima, poderíamos ter a seguinte situação : window obj1; obj1.box; Na
situação acima, é chamado o método "box" da classe window, mas ele não existe. O compilador
6 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
Class conta
{
private :
char nome[40]; // nome do cliente
int nconta; // número da conta
float saldo; // saldo da conta
public :
void getdata();
void putdata();
float Saldo();
};
class ContaSimples : public conta {};
class ContaEspecial : public conta
{
private :float limite;
public :
void getdata();
void putdata();
};
class Poupanca : public conta
{
private : float taxa;
public :
void getdata() { conta::getdata(); cout << " Taxa:";
cin >> taxa; }
void putdata() { conta::putdata(); cout << "\n Taxa:" <<
taxa; cout << "\nSaldo Total: " << (Saldo() * taxa);}
};
No exemplo acima, declaramos uma classe conta (classe base) e declaramos as classes
conta_especial, conta_simples e poupança como classes derivadas da classe conta. Quando
declaramos uma classe como derivada de outra, a classe derivada herda todas as
características da classe-base (este processo recebe o nome de reutilização do código). A
classe derivada pode acessar todos os dados públicos e privados da classe-base. Além do que,
pode alterar estes dados, isto é, pode acrescentar novos campos de dados, pode reescrever um
método da classe-base com o mesmo nome e alterar o seu conteúdo.
O uso de uma biblioteca de classes oferece uma grande vantagem sobre o uso de uma biblioteca
de funções : o programador pode criar classes derivadas de classes bases de bibliotecas. Isto
significa que, sem alterar a classe base, é possível adicionar características diferentes que
a tornarão capaz de executar exatamente o que desejamos.
O uso de classes derivadas aumenta a eficiência da programação pela não necessidade da
criação de códigos repetitivos.
A uma função de biblioteca não podemos adicionar outras implementações a não ser que ela seja
reescrita ou que tenhamos seu código fonte para alterá-la e recompilá-la.
Quando criamos uma classe derivada com a clausula "public", estamos dizendo que os dados
públicos da classe base serão dados públicos na classe derivada e, os dados protegidos serão
os dados protegidos da classe derivada. A classe derivada não terá acesso aos dados privados.
Podemos criar uma classe com a clausula "private", com isso tanto os dados públicos como
protegidos da classe base serão dados privados da classe derivada. Com isso, a classe
derivada não terá acesso a nenhum dado da classe base.
class BASE
{
protected : Int secreto;
private : int ultra_secreto;
public : int publico;
};
class DERIV1 : public BASE
{
public :
int a = secreto; // ok
int b = ultra_secreto; // erro :não-acessível
int c = publico // ok
};
class DERIV2 : private BASE
7 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
{
public :
int a = secreto; // ok
int b = ultra_secreto; // erro :não-acessível
int c = publico // ok
} ;
É possível a criação de funções-membro na classe derivada que tenha o mesmo nome de uma
função-membro da classe base. Com isto, podemos chamar a função-membro da classe base através
do operador de escopo "::" e, construirmos este procedimento com o que queremos.
Exemplo :
};
void main()
{
Agente agente("Daniel","1",1.78,21);
agente.print();
}
No exemplo acima, o método "print()" da classe derivada agente é reescrita com o mesmo nome
do método da classe base e, ainda, chama o método "print()" da classe base BasAg através do
operador de escopo "::". Quando for executado o comando "agente.print()" do exemplo acima, o
compilador executará o método print() da classe agente. Mas, o primeiro comando deste método
é chamar o método de mesmo nome da classe base, o compilador executa este método e, após os
comandos do método da classe derivada.
HERANÇA MÚLTIPLA
Quando uma classe herda as características de mais de uma classe-base. Abaixo, temos o
exemplo de herança múltipla. Declaramos as classes simples Cadastro, Imóvel e Tipo.
Declaramos a classe Venda como herança múltipla das três anteriores.
class Cadastro
{
private :
char nome[30], fone[20];
public :
Cadastro();
void getdata();
void putdata();
};
class Imóvel
{
private :
8 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
FUNÇÕES VIRTUAIS
São utilizadas quando queremos fazer referência através de uma matriz de ponteiros para uma
classe base que contém várias classes derivadas com o objetivo de acessar um mesmo método de
cada classe derivada. Para utilizarmos este recurso da POO, declaramos os métodos que
quisermos como funções virtuais da classe base. A sintaxe é a seguinte:
Exemplo:
class base { public : virtual void print() { cout << "\nBASE"; }};
class deriv0 : public base { public : void print() { cout <<"\nDERIV0"; } };
class deriv1 : public base { public : void print() { cout <<"\nDERIV1"; } };
class deriv2 : public base { public : void print() { cout <<"\nDERIV2"; } };
void main() { base *p[3]; // matriz de ponteiro para a classe base
deriv0 dv0; // objeto da classe deriv0 deriv1 dv1; // objeto da classe deriv1 deriv2 dv2;
// objeto da classe deriv2
p[0] = &dv0; p[1] = &dv1; p[2] = &dv2;
for (int i = 0; i < 3; i++) p[i]-> print(); }
9 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
class base {
public : virtual void print() = 0; };
class deriv0 : public base { public : void print() { cout <<"\nDERIV0"; } };
class deriv1 : public base { public : void print() { cout <<"\nDERIV1"; } };
class deriv2 : public base { public : void print() { cout <<"\nDERIV2"; } };
void main() { base *p[3]; // matriz de ponteiro para a classe base
deriv0 dv0; // objeto da classe deriv0 deriv1 dv1; // objeto da classe
deriv1 deriv2 dv2; // objeto da classe deriv2
p[0] = &dv0; p[1] = &dv1; p[2] = &dv2;
for (int i = 0; i < 3; i++) p[i]-> print(); }
FUNÇÕES AMIGAS
Por default, os membros privados de uma classe somente podem ser acessados
por outros membros da mesma classe. Contudo, uma classe pode dar
permissão para uma função não membro desta classe
acessar os seus membros privados, mas não estará associada a um
objeto da classe. Isto é feito com a declaração friend.
Uma função amiga pode agir em duas ou mais classes diferentes,
fazendo o papel de elo de ligação entre as classes.
Exemplo :
#include <iostream.h>
class tempo
{
private :
long segundos;
public : tempo(long h, long m, long s) { segundos = h * 3600 + m * 60 +s; }
friend char *prntm(tempo); // declaração amiga
};
char *prntm(tempo tm) <
{
char * buff = new char[9]; // new executa uma alocação
dinâmica ao invés de ser alocado na pilha
int h = tm.segundos / 3600;
int resto = tm.segundos % 3600;
int m = resto / 60;
int s = (resto % 60);
buff[0] = h / 10 + '0';
buff[1] = h % 10 + '0';
buff[2] = ':';
buff[3] = m / 10 + '0';
buff[4] = m % 10 + '0';
buff[5] = ':';
buff[6] = s / 10 + '0';
buff[7] = s % 10 + '0';
buff[8] = '\0';
return buff;
}
void main()
{
tempo tm(5,8,20);
cout << "\n" << prntm(tm);
}
10 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
Exemplo:
#include <iostream.h>
class tempo
{
private : long h,m,s;
public : tempo (int hh,int mm,int ss) { h = hh; m = mm; s = ss; }
friend class data; //data é uma classe amiga
};
class data
{
private : int d,m,a;
public :
data (int dd,int mm,int aa) { d = dd; m = mm; a = aa;}
void prndt (tempo tm)
{
cout << "\nData: " <<d<<'/'<<m<<'/' <<a;
cout << "\nHora: " <<tm.h<< ':'<<tm.m<< ':' <<tm.s;
}
};
void main()
{
tempo tm(12,18,30);
tempo tm1 (13,22,10);
data dt(18,12,55);
dt.prndt(tm);
dt.prndt(tm1);
}
SOBRECARGA DE OPERADORES
À partir de agora, cada vez que o operador `+' for executado entre
dois objetos da classe matriz ele irá somá-las e atribuir
o resultado ´a uma terceira matriz.
11 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
#include <iostream.h>
class ponto
{
private : int x,y;
public :
ponto(int x1=0,int y1=0) // construtor { x = x1; y = y1;}
void operator ++() // função operadora prefixada { ++x; ++y; }
void printpt() const // imprime ponto { cout << "("
<< x << "," << y << ")"; }
};
void main()
{
ponto p1, p2(2,3), p3; // declara e inicializa
cout << "\n p1 = ";
p1.printpt();
cout << "\n p2 = ";
p2.printpt(); ++p1; //incrementa p1
++p2; // incrementa p2
cout << "\n ++p1 = ";
p1.printpt();
cout << "\n ++p2 = ";
p2.printpt();
p3 = p1;
cout << "\n p3 = ";
12 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
p3.printpt();
}
Resultado :
p1 = (0,0)
p2 = (2,3)
++p1 = (1,1)
++p2 = (3,4)
p3 = (1,1)
#include <iostream.h>
#include <iomanip.h>
class venda
{
private :
int npecas;
float preco;
public :
venda() {}
venda(int np, float p) // construtor com argumentos { npecas= np; preco = p; }
void getvenda()
{
cout << "Insira Numero de Pecas: ";
cin >> npecas;
cout << "Insira Preco : ";
cin >> preco;
}
venda operator + (venda v) const; // funçãooperador
void printvenda() const;
};
venda venda::operator + (venda v) const // soma duas vendas
{
int pec = npecas + v.npecas;
float pre = preco + v.preco;
return venda(pec,pre);
}
void venda::printvenda() const
{
cout << setiosflags(ios::fixed) // nao notaçãocientifica
<< setiosflags(ios::showpoint) // ponto decimal
<<setprecision(2) // duas casas decimais
<< setw(10) << npecas;
// tamanho do campo 10
cout << setw(10) << preco << "\n";
}
void main()
{
venda A(58,12734.53),B,C(30,6000.3),T,Total;
B.getvenda();
T = A + B;
Total = A + B + C; //somas múltiplas
cout << "Venda A ........";
A.printvenda();
cout << "Venda B ........";
B.printvenda();
cout << "Venda:A + B ....";
T.printvenda();
13 de 14 26/02/2013 15:12
PROGRAMAÇÃO ORIENTADA A OBJETOS - CONCEITOS BÁSICOS http://www.goulart.pro.br/ori_obj.html
BIBLIOGRAFIA
14 de 14 26/02/2013 15:12