Java - Introdução a
Coleções e Generics
Prof. Sérgio Souza Costa
Objetivo
• Prepararmos para entendermos como
funciona o “framework collection” do Java.
Capítulo de hoje: Um programador C/C++ precisa
lidar com coleções de dados em Java.
Para que estudar sobre o “framework
collection” do Java se eu posso
construir minhas próprias coleções ?
Aprendi nas aulas...
Olhem milha pilha.
Muito fácil

public class Pilha {
int v[];
int pos;
public Pilha (int n) {
v = new int [n];
pos = 0;
}
...
Ok. Falta fazer uns
testes, mas ....

public class Pilha {
int v[];
int pos;
public Pilha (int n) {
v = new int [n];
pos =...
Ok. Falta fazer uns
testes, mas ....

Quais testes ele
está se referindo ?
public class Pilha {
int v[];
int pos;
public P...
Testando minha
pilha. O que
acharam?

public class Teste {
public static void main(String[] args) {
Pilha p = new Pilha (5...
Para aulas de estrutura de
dados está ok, mas esta tua
pilha não é muito útil. Ela é
restrita a um tipo de dado (
inteiro)
Sim. Isso é por que Java é uma
linguagem que os métodos e
variáveis tem que ter tipos
definido estaticamente.
Em C, eu usava *void para
estruturas genéricas. Depois
bastava eu fazer um cast para
um tipo específico.
Será que Java não tem
algo similar ? O que
vocês acham ?
Yes. Como toda classe
em Java herda de
Object, este poderia ser
o tipo da minha pilha.
Pilha de Object
public class PilhaObjeto {
Object v[];
int pos;
public PilhaObjeto (int n) {
v = new Object [n];
pos = 0;
...
Resolvido. O que
acharam ?

public static void main(String[] args) {
PilhaObjeto p = new PilhaObjeto (5);
p.empilha("Joao"...
Mais um teste ...
public static void main(String[] args) {
PilhaObjeto p = new PilhaObjeto (5);
p.empilha("Joao");
p.empil...
Mais um teste ...
public static void main(String[] args) {
PilhaObjeto p = new PilhaObjeto (5);
p.empilha("Joao");
p.empil...
Esperava este
erro
public static void main(String[] args) {
PilhaObjeto p = new PilhaObjeto (5);
p.empilha("Joao");
p.empi...
Mas achava que estava
armazenando um int.
O que é este Integer?
public static void main(String[] args) {
PilhaObjeto p = n...
Esta solução funciona apenas
sobre objetos e não tipos
primitivos. O Integer é um objeto
equivalente ao Int.
Além disso, similar ao usar *void
em C, Object em Java pode gerar
problemas em tempo de
execução. Devido a inconsistência
...
DILEMA: Tipos garante
consistência nas operações mas
enrijece a definição dos meus
métodos. Como resolver?
Até 2004, antes da versão 1.5,
teríamos que nos contentar com
o uso de Object.
Porem com a versão 1.5 o Java
passou a suportar classes
genéricas, também conhecido
como polimorfismo
paramétrico.
Ok. Vou pesquisar.....
Generics em Java é
similar a templates
em C++.
Basicamente
substituo tipos por
um T genérico.
Não funcionou como
esperado. Java não
reconheceu o
construtor genérico

public class PilhaGeneric <T> {
T v[];
int pos;
pu...
Por que será ?
public class PilhaGeneric <T> {
T v[];
int pos;
public PilhaGeneric (int n) {
v = new T [n];
pos = 0;
}
pub...
Java utiliza um
mecanismo chamado
Erasure para gerar os
códigos finais.

public class PilhaGeneric <T> {
T v[];
int pos;
p...
Por enquanto saiba
que o Java não sabe
mapear um
construtor T genérico.

public class PilhaGeneric <T> {
T v[];
int pos;
p...
Solução é construir
Object[] e depois
fazer um Cast.
public class PilhaGeneric <T> {
T v[];
int pos;
@SuppressWarnings("un...
Agora podemos usar.

PilhaGeneric<Integer> p = new PilhaGeneric <Integer> (5);
p.empilha(10);
p.empilha("joao");

Causa um...
Além do array nativo
da linguagem Java,
existem coleções.
Esta tua classe pilha
poderia usar uma
coleção ao invés de
um array.
public class PilhaGeneric2 <T> {
private List<T> v;
p...
Então poderíamos
usar da seguinte
maneira.

PilhaGeneric2<Integer> p =
new PilhaGeneric2 <Integer> ();
p.empilha(10);
p.em...
E se sua pilha tivesse
que retornar o maior
valor?
Fácil, não é só
escrever o seguinte
método? O que
acham?

public T maior () {
T maior = v.get(0);
for (int i=0; i< v.size(...
Fácil, não é só
escrever o seguinte
método? O que
acham?

Será que o operador (>)
pode ser aplicado em
qualquer objeto?
pu...
Verdade, este método
não é tão genérico. O
objeto preciso saber
comparar.

public T maior () {
T maior = v.get(0);
for (in...
Em C++, basta eu
sobrecarregar o
operador (>). E em
Java?

public T maior () {
T maior = v.get(0);
for (int i=0; i< v.size...
Java não possui
sobrecarga de
operadores, somente
de métodos.
Existe um método que
equivale a
comparação:
compareTo
Posso usar este
método da seguinte
maneira

public T maior () {
T maior = v.get(0);
for (int i=0; i< v.size(); i++) {
if (...
Porém preciso dizer que a
minha pilha funciona com
qualquer T, desde que ele
“extenda” a classe Comparable

public class P...
A classe pilha ficaria
da seguinte maneira

public class PilhaGeneric3 <T extends
Comparable<T>> {
private List<T> v;
publ...
Na verdade, o Java provê
um framework completo
para lidar com coleções de
dados.
Entendi. Melhor
aprender usar o
“framework
collection”
Excelente apresentação sobre
Collections e Generics
Próximos SlideShares
Carregando em…5
×

Java - Introdução a Coleções e Generics

1.408 visualizações

Publicada em

0 comentários
2 gostaram
Estatísticas
Notas
  • Seja o primeiro a comentar

Sem downloads
Visualizações
Visualizações totais
1.408
No SlideShare
0
A partir de incorporações
0
Número de incorporações
80
Ações
Compartilhamentos
0
Downloads
69
Comentários
0
Gostaram
2
Incorporações 0
Nenhuma incorporação

Nenhuma nota no slide

Java - Introdução a Coleções e Generics

  1. 1. Java - Introdução a Coleções e Generics Prof. Sérgio Souza Costa
  2. 2. Objetivo • Prepararmos para entendermos como funciona o “framework collection” do Java.
  3. 3. Capítulo de hoje: Um programador C/C++ precisa lidar com coleções de dados em Java.
  4. 4. Para que estudar sobre o “framework collection” do Java se eu posso construir minhas próprias coleções ? Aprendi nas aulas de estrutura de dados ☺
  5. 5. Olhem milha pilha. Muito fácil public class Pilha { int v[]; int pos; public Pilha (int n) { v = new int [n]; pos = 0; } public void empilha(int x) { v[pos++] = x; } public int desempilha() { return v[--pos] ; } }
  6. 6. Ok. Falta fazer uns testes, mas .... public class Pilha { int v[]; int pos; public Pilha (int n) { v = new int [n]; pos = 0; } public void empilha(int x) { v[pos++] = x; } public int desempilha() { return v[--pos] ; } }
  7. 7. Ok. Falta fazer uns testes, mas .... Quais testes ele está se referindo ? public class Pilha { int v[]; int pos; public Pilha (int n) { v = new int [n]; pos = 0; } public void empilha(int x) { v[pos++] = x; } public int desempilha() { return v[--pos] ; } }
  8. 8. Testando minha pilha. O que acharam? public class Teste { public static void main(String[] args) { Pilha p = new Pilha (5); p.empilha(10); p.empilha(5); p.empilha(2); System.out.println(p.desempilha()); System.out.println(p.desempilha()); System.out.println(p.desempilha()); } }
  9. 9. Para aulas de estrutura de dados está ok, mas esta tua pilha não é muito útil. Ela é restrita a um tipo de dado ( inteiro)
  10. 10. Sim. Isso é por que Java é uma linguagem que os métodos e variáveis tem que ter tipos definido estaticamente.
  11. 11. Em C, eu usava *void para estruturas genéricas. Depois bastava eu fazer um cast para um tipo específico.
  12. 12. Será que Java não tem algo similar ? O que vocês acham ?
  13. 13. Yes. Como toda classe em Java herda de Object, este poderia ser o tipo da minha pilha.
  14. 14. Pilha de Object public class PilhaObjeto { Object v[]; int pos; public PilhaObjeto (int n) { v = new Object [n]; pos = 0; } public void empilha(Object x) { v[pos++] = x; } public Object desempilha() { return v[--pos] ; } }
  15. 15. Resolvido. O que acharam ? public static void main(String[] args) { PilhaObjeto p = new PilhaObjeto (5); p.empilha("Joao"); p.empilha("Jose"); p.empilha("Maria"); String nome = (String) p. desempilha(); System.out.println("nome:"+nome); }
  16. 16. Mais um teste ... public static void main(String[] args) { PilhaObjeto p = new PilhaObjeto (5); p.empilha("Joao"); p.empilha("Jose"); p.empilha(10); String nome = (String) p. desempilha(); System.out.println("nome:"+nome); }
  17. 17. Mais um teste ... public static void main(String[] args) { PilhaObjeto p = new PilhaObjeto (5); p.empilha("Joao"); p.empilha("Jose"); p.empilha(10); String nome = (String) p. desempilha(); System.out.println("nome:"+nome); } Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String at TesteObjeto.main(TesteObjeto.java:12)
  18. 18. Esperava este erro public static void main(String[] args) { PilhaObjeto p = new PilhaObjeto (5); p.empilha("Joao"); p.empilha("Jose"); p.empilha(10); String nome = (String) p. desempilha(); System.out.println("nome:"+nome); } Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String at TesteObjeto.main(TesteObjeto.java:12)
  19. 19. Mas achava que estava armazenando um int. O que é este Integer? public static void main(String[] args) { PilhaObjeto p = new PilhaObjeto (5); p.empilha("Joao"); p.empilha("Jose"); p.empilha(10); String nome = (String) p. desempilha(); System.out.println("nome:"+nome); } Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String at TesteObjeto.main(TesteObjeto.java:12)
  20. 20. Esta solução funciona apenas sobre objetos e não tipos primitivos. O Integer é um objeto equivalente ao Int.
  21. 21. Além disso, similar ao usar *void em C, Object em Java pode gerar problemas em tempo de execução. Devido a inconsistência em operações.
  22. 22. DILEMA: Tipos garante consistência nas operações mas enrijece a definição dos meus métodos. Como resolver?
  23. 23. Até 2004, antes da versão 1.5, teríamos que nos contentar com o uso de Object.
  24. 24. Porem com a versão 1.5 o Java passou a suportar classes genéricas, também conhecido como polimorfismo paramétrico.
  25. 25. Ok. Vou pesquisar.....
  26. 26. Generics em Java é similar a templates em C++.
  27. 27. Basicamente substituo tipos por um T genérico.
  28. 28. Não funcionou como esperado. Java não reconheceu o construtor genérico public class PilhaGeneric <T> { T v[]; int pos; public PilhaGeneric (int n) { v = new T [n]; pos = 0; } public void empilha(T x) { v[pos++] = x; } public T desempilha() { return v[--pos] ; } }
  29. 29. Por que será ? public class PilhaGeneric <T> { T v[]; int pos; public PilhaGeneric (int n) { v = new T [n]; pos = 0; } public void empilha(T x) { v[pos++] = x; } public T desempilha() { return v[--pos] ; } }
  30. 30. Java utiliza um mecanismo chamado Erasure para gerar os códigos finais. public class PilhaGeneric <T> { T v[]; int pos; public PilhaGeneric (int n) { v = new T [n]; pos = 0; } public void empilha(T x) { v[pos++] = x; } public T desempilha() { return v[--pos] ; } }
  31. 31. Por enquanto saiba que o Java não sabe mapear um construtor T genérico. public class PilhaGeneric <T> { T v[]; int pos; public PilhaGeneric (int n) { v = new T [n]; pos = 0; } public void empilha(T x) { v[pos++] = x; } public T desempilha() { return v[--pos] ; } }
  32. 32. Solução é construir Object[] e depois fazer um Cast. public class PilhaGeneric <T> { T v[]; int pos; @SuppressWarnings("unchecked") public PilhaGeneric (int n) { v = (T[]) new Object [n]; pos = 0; } public void empilha(T x) { v[pos++] = x; } public T desempilha() { return v[--pos] ; } }
  33. 33. Agora podemos usar. PilhaGeneric<Integer> p = new PilhaGeneric <Integer> (5); p.empilha(10); p.empilha("joao"); Causa um erro. A pilha é do tipo Integer. Mantem consistência.
  34. 34. Além do array nativo da linguagem Java, existem coleções.
  35. 35. Esta tua classe pilha poderia usar uma coleção ao invés de um array. public class PilhaGeneric2 <T> { private List<T> v; public PilhaGeneric2 () { v = new ArrayList<T>(); } public void empilha(T x) { v.add(x); } public T desempilha() { return v.remove(v.size()-1) ; } }
  36. 36. Então poderíamos usar da seguinte maneira. PilhaGeneric2<Integer> p = new PilhaGeneric2 <Integer> (); p.empilha(10); p.empilha(20); System.out.println(p.desempilha()); System.out.println(p.desempilha());
  37. 37. E se sua pilha tivesse que retornar o maior valor?
  38. 38. Fácil, não é só escrever o seguinte método? O que acham? public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i) > maior) maior = v.get(i); } return maior; }
  39. 39. Fácil, não é só escrever o seguinte método? O que acham? Será que o operador (>) pode ser aplicado em qualquer objeto? public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i) > maior) maior = v.get(i); } return maior; }
  40. 40. Verdade, este método não é tão genérico. O objeto preciso saber comparar. public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i) > maior) maior = v.get(i); } return maior; }
  41. 41. Em C++, basta eu sobrecarregar o operador (>). E em Java? public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i) > maior) maior = v.get(i); } return maior; }
  42. 42. Java não possui sobrecarga de operadores, somente de métodos.
  43. 43. Existe um método que equivale a comparação: compareTo
  44. 44. Posso usar este método da seguinte maneira public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i).compareTo(maior) > 0) maior = v.get(i); } return maior; }
  45. 45. Porém preciso dizer que a minha pilha funciona com qualquer T, desde que ele “extenda” a classe Comparable public class PilhaGeneric3 <T extends Comparable<T>> { … }
  46. 46. A classe pilha ficaria da seguinte maneira public class PilhaGeneric3 <T extends Comparable<T>> { private List<T> v; public PilhaGeneric3 () { v = new ArrayList<T>(); } public void empilha(T x) { v.add(x); } public T desempilha() { return v.remove(v.size()-1) ; } public T maior () { T maior = v.get(0); for (int i=0; i< v.size(); i++) { if (v.get(i).compareTo(maior) > 0) maior = v.get(i); } return maior; } }
  47. 47. Na verdade, o Java provê um framework completo para lidar com coleções de dados.
  48. 48. Entendi. Melhor aprender usar o “framework collection”
  49. 49. Excelente apresentação sobre Collections e Generics

×