Notice: This page requires JavaScript to function properly.
Please enable JavaScript in your browser settings or update your browser.
Aprenda Estrutura de Dados Fila em Java | Estruturas de Dados Avançadas em Java
Practice
Projects
Quizzes & Challenges
Quizzes
Challenges
/
Estruturas de Dados em Java

bookEstrutura de Dados Fila em Java

Vamos começar com uma Queue. Imagine uma fila em uma loja durante uma promoção. Há 10 pessoas; a primeira pessoa está mais próxima das portas da loja do que as outras, e a décima pessoa está mais distante. Quando a primeira pessoa entra na loja, ela sai da fila, fazendo com que toda a fila avance uma posição. A Queue em Java funciona de maneira muito semelhante.

Dessa forma, é possível implementar diversos programas onde a lógica de fila é bem estruturada. Por exemplo, implementar um quadro com planos e tarefas.

Mas antes, vamos analisar os métodos básicos para trabalhar com uma Queue.

Queue é uma interface da qual a classe LinkedList herda, com a qual você já está familiarizado, então utilizaremos essa implementação.

Dessa forma, utiliza-se a interface como o tipo do objeto, mas a implementação do objeto será LinkedList, pois é uma implementação específica desse objeto. (Lembre-se de que não é possível criar objetos a partir de uma interface).

Exemplo:

Example.java

Example.java

copy
1234
// `LinkedList` as implementation of the `List` interface: List<T> list = new LinkedList<>(); // `LinkedList` as implementation of the `Queue` interface: Queue<T> queue = new LinkedList<>();

Dessa forma, é possível tornar a aplicação muito flexível ao utilizar várias implementações da mesma interface.

Mas vamos voltar aos métodos de trabalho com Queue.

Métodos

Alguns métodos principais da interface Queue são:

  • add(element): adiciona um elemento à fila, lançando uma exceção se a operação não for possível;
  • offer(element): adiciona um elemento à fila, retornando true se for bem-sucedido ou false caso contrário.

É possível notar que esses métodos basicamente fazem a mesma coisa. No entanto, a principal diferença está na segurança do método offer. Em caso de elemento adicionado de forma inadequada, o método offer não lançará uma exceção e não interromperá a execução do programa.

Porém, no momento, essa característica não é de grande interesse, pois uma Queue comum não possui limitações. No entanto, existe uma estrutura chamada BlockingQueue, que possui uma restrição quanto ao número de elementos; nesse caso, esses métodos terão uma diferença perceptível.

Vamos analisar um exemplo:

Main.java

Main.java

copy
1234567891011121314
package com.example; import java.util.concurrent.BlockingQueue; import java.util.concurrent.LinkedBlockingQueue; public class Main { public static void main(String[] args) { BlockingQueue<String> queue = new LinkedBlockingQueue<>(2); queue.add("One"); queue.add("Two"); queue.add("Three"); System.out.println("Queue: " + queue); } }

Como pode ser observado, ao utilizar o método add() e tentar adicionar um elemento que não cabe na fila, o programa lança um erro, encerrando a execução de forma inesperada.

Vamos tentar a mesma operação, mas com um método mais seguro — offer():

Main.java

Main.java

copy
1234567891011121314
package com.example; import java.util.concurrent.BlockingQueue; import java.util.concurrent.LinkedBlockingQueue; public class Main { public static void main(String[] args) { BlockingQueue<String> queue = new LinkedBlockingQueue<>(2); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); System.out.println("Queue: " + queue); } }

Como você pode ver, agora o elemento não foi adicionado à fila, mas também não lançou uma exceção. Portanto, podemos considerar que tratamos o erro de forma adequada.

Você pode tratar exceções de maneira diferente usando uma estrutura como try-catch, mas discutiremos isso mais adiante.

Métodos de Remoção

  • remove(): remove e retorna o elemento do início da fila, lançando uma exceção se a fila estiver vazia;
  • poll(): remove e retorna o elemento do início da fila, retornando null se a fila estiver vazia.

Esses métodos realizam exatamente a função como se a primeira pessoa da fila entrasse na loja e saísse da fila. É aqui que o princípio FIFO (First In, First Out) entra em ação. Ou seja, o elemento que foi adicionado primeiro à fila será o primeiro a ser removido.

Aqui, você também pode observar a diferença entre esses dois métodos. O método poll() é utilizado com mais frequência do que o método remove() porque é mais seguro e não lança exceções.

Vamos analisar um exemplo:

Main.java

Main.java

copy
123456789101112131415
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); System.out.println("Queue: " + queue); queue.remove(); queue.remove(); System.out.println("Queue after removal operation: " + queue); } }

Como pode ser observado, o programa lança uma NoSuchElementException porque estamos tentando remover um elemento de uma fila vazia.

Para evitar essa exceção, é melhor utilizar o método poll():

Main.java

Main.java

copy
123456789101112131415
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); System.out.println("Queue: " + queue); queue.poll(); queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Agora, um elemento foi removido da fila de forma segura, e nenhuma exceção foi lançada ao tentar remover um elemento de uma lista vazia.

O recurso do poll() retornar null pode ser utilizado, por exemplo, em um laço while().

Veja um exemplo:

Main.java

Main.java

copy
1234567891011121314151617181920
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (queue.poll() != null) { queue.poll(); } System.out.println("Queue after removal operation: " + queue); } }

Dessa forma, é possível remover todos os elementos da fila utilizando um loop.

Lembre-se de que o primeiro elemento que entrou na fila é o que será removido! Por exemplo, no caso do exemplo acima, o elemento com o dado "One" foi removido primeiro.

O princípio FIFO é demonstrado abaixo:

Main.java

Main.java

copy
123456789101112131415161718
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Podemos avançar para os métodos que retornam o primeiro e o último elementos:

  • element(): retorna, mas não remove, o elemento do início da fila, lançando uma exceção se a fila estiver vazia;
  • peek(): retorna, mas não remove, o elemento do início da fila, retornando null se a fila estiver vazia.

Utilizar o método peek() é uma abordagem mais confiável e segura, pois ajuda a evitar possíveis exceções.

Veja um exemplo de uso:

Main.java

Main.java

copy
12345678910111213141516
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); System.out.println("Queue: " + queue); System.out.println("The first element in the queue: " + queue.peek()); System.out.println("Queue after the `peek()` method: " + queue); } }

É possível combinar este método com outros métodos da fila.

Se houver uma fila com cinco elementos e for necessário remover todos os elementos até o quarto (inclusive), veja a implementação dessa operação:

Main.java

Main.java

copy
123456789101112131415161718192021
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (!queue.peek().equals("Four")) { queue.poll(); } queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Você utilizou um loop com uma condição baseada no método peek().

É possível otimizar significativamente esse loop utilizando o método contains(). Esse método retorna true se o elemento especificado estiver presente na fila e false caso não esteja.

Vamos melhorar o código acima:

Main.java

Main.java

copy
1234567891011121314151617181920
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (queue.contains("Four")) { queue.poll(); } System.out.println("Queue after removal operation: " + queue); } }

Aqui, definimos uma única condição para o while loop. Conseguimos remover com sucesso todos os elementos até e incluindo o elemento "Four".

1. O que é uma Queue em Java?

2. Qual interface representa uma Queue no Java Collections Framework?

3. Qual é o propósito do método offer() na interface Queue?

4. O que o método poll() faz na interface Queue?

5. Qual classe no pacote java.util.concurrent do Java representa uma fila bloqueante limitada?

6. O que acontece se você tentar adicionar um elemento a uma fila cheia usando o método add()?

question mark

O que é uma Queue em Java?

Select the correct answer

question mark

Qual interface representa uma Queue no Java Collections Framework?

Select the correct answer

question mark

Qual é o propósito do método offer() na interface Queue?

Select the correct answer

question mark

O que o método poll() faz na interface Queue?

Select the correct answer

question mark

Qual classe no pacote java.util.concurrent do Java representa uma fila bloqueante limitada?

Select the correct answer

question mark

O que acontece se você tentar adicionar um elemento a uma fila cheia usando o método add()?

Select the correct answer

Tudo estava claro?

Como podemos melhorá-lo?

Obrigado pelo seu feedback!

Seção 2. Capítulo 1

Pergunte à IA

expand

Pergunte à IA

ChatGPT

Pergunte o que quiser ou experimente uma das perguntas sugeridas para iniciar nosso bate-papo

Suggested prompts:

Can you explain more about the difference between add() and offer() methods?

How does the FIFO principle work in a real-world queue?

What are some practical uses of the Queue interface in Java?

bookEstrutura de Dados Fila em Java

Deslize para mostrar o menu

Vamos começar com uma Queue. Imagine uma fila em uma loja durante uma promoção. Há 10 pessoas; a primeira pessoa está mais próxima das portas da loja do que as outras, e a décima pessoa está mais distante. Quando a primeira pessoa entra na loja, ela sai da fila, fazendo com que toda a fila avance uma posição. A Queue em Java funciona de maneira muito semelhante.

Dessa forma, é possível implementar diversos programas onde a lógica de fila é bem estruturada. Por exemplo, implementar um quadro com planos e tarefas.

Mas antes, vamos analisar os métodos básicos para trabalhar com uma Queue.

Queue é uma interface da qual a classe LinkedList herda, com a qual você já está familiarizado, então utilizaremos essa implementação.

Dessa forma, utiliza-se a interface como o tipo do objeto, mas a implementação do objeto será LinkedList, pois é uma implementação específica desse objeto. (Lembre-se de que não é possível criar objetos a partir de uma interface).

Exemplo:

Example.java

Example.java

copy
1234
// `LinkedList` as implementation of the `List` interface: List<T> list = new LinkedList<>(); // `LinkedList` as implementation of the `Queue` interface: Queue<T> queue = new LinkedList<>();

Dessa forma, é possível tornar a aplicação muito flexível ao utilizar várias implementações da mesma interface.

Mas vamos voltar aos métodos de trabalho com Queue.

Métodos

Alguns métodos principais da interface Queue são:

  • add(element): adiciona um elemento à fila, lançando uma exceção se a operação não for possível;
  • offer(element): adiciona um elemento à fila, retornando true se for bem-sucedido ou false caso contrário.

É possível notar que esses métodos basicamente fazem a mesma coisa. No entanto, a principal diferença está na segurança do método offer. Em caso de elemento adicionado de forma inadequada, o método offer não lançará uma exceção e não interromperá a execução do programa.

Porém, no momento, essa característica não é de grande interesse, pois uma Queue comum não possui limitações. No entanto, existe uma estrutura chamada BlockingQueue, que possui uma restrição quanto ao número de elementos; nesse caso, esses métodos terão uma diferença perceptível.

Vamos analisar um exemplo:

Main.java

Main.java

copy
1234567891011121314
package com.example; import java.util.concurrent.BlockingQueue; import java.util.concurrent.LinkedBlockingQueue; public class Main { public static void main(String[] args) { BlockingQueue<String> queue = new LinkedBlockingQueue<>(2); queue.add("One"); queue.add("Two"); queue.add("Three"); System.out.println("Queue: " + queue); } }

Como pode ser observado, ao utilizar o método add() e tentar adicionar um elemento que não cabe na fila, o programa lança um erro, encerrando a execução de forma inesperada.

Vamos tentar a mesma operação, mas com um método mais seguro — offer():

Main.java

Main.java

copy
1234567891011121314
package com.example; import java.util.concurrent.BlockingQueue; import java.util.concurrent.LinkedBlockingQueue; public class Main { public static void main(String[] args) { BlockingQueue<String> queue = new LinkedBlockingQueue<>(2); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); System.out.println("Queue: " + queue); } }

Como você pode ver, agora o elemento não foi adicionado à fila, mas também não lançou uma exceção. Portanto, podemos considerar que tratamos o erro de forma adequada.

Você pode tratar exceções de maneira diferente usando uma estrutura como try-catch, mas discutiremos isso mais adiante.

Métodos de Remoção

  • remove(): remove e retorna o elemento do início da fila, lançando uma exceção se a fila estiver vazia;
  • poll(): remove e retorna o elemento do início da fila, retornando null se a fila estiver vazia.

Esses métodos realizam exatamente a função como se a primeira pessoa da fila entrasse na loja e saísse da fila. É aqui que o princípio FIFO (First In, First Out) entra em ação. Ou seja, o elemento que foi adicionado primeiro à fila será o primeiro a ser removido.

Aqui, você também pode observar a diferença entre esses dois métodos. O método poll() é utilizado com mais frequência do que o método remove() porque é mais seguro e não lança exceções.

Vamos analisar um exemplo:

Main.java

Main.java

copy
123456789101112131415
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); System.out.println("Queue: " + queue); queue.remove(); queue.remove(); System.out.println("Queue after removal operation: " + queue); } }

Como pode ser observado, o programa lança uma NoSuchElementException porque estamos tentando remover um elemento de uma fila vazia.

Para evitar essa exceção, é melhor utilizar o método poll():

Main.java

Main.java

copy
123456789101112131415
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); System.out.println("Queue: " + queue); queue.poll(); queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Agora, um elemento foi removido da fila de forma segura, e nenhuma exceção foi lançada ao tentar remover um elemento de uma lista vazia.

O recurso do poll() retornar null pode ser utilizado, por exemplo, em um laço while().

Veja um exemplo:

Main.java

Main.java

copy
1234567891011121314151617181920
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (queue.poll() != null) { queue.poll(); } System.out.println("Queue after removal operation: " + queue); } }

Dessa forma, é possível remover todos os elementos da fila utilizando um loop.

Lembre-se de que o primeiro elemento que entrou na fila é o que será removido! Por exemplo, no caso do exemplo acima, o elemento com o dado "One" foi removido primeiro.

O princípio FIFO é demonstrado abaixo:

Main.java

Main.java

copy
123456789101112131415161718
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Podemos avançar para os métodos que retornam o primeiro e o último elementos:

  • element(): retorna, mas não remove, o elemento do início da fila, lançando uma exceção se a fila estiver vazia;
  • peek(): retorna, mas não remove, o elemento do início da fila, retornando null se a fila estiver vazia.

Utilizar o método peek() é uma abordagem mais confiável e segura, pois ajuda a evitar possíveis exceções.

Veja um exemplo de uso:

Main.java

Main.java

copy
12345678910111213141516
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); System.out.println("Queue: " + queue); System.out.println("The first element in the queue: " + queue.peek()); System.out.println("Queue after the `peek()` method: " + queue); } }

É possível combinar este método com outros métodos da fila.

Se houver uma fila com cinco elementos e for necessário remover todos os elementos até o quarto (inclusive), veja a implementação dessa operação:

Main.java

Main.java

copy
123456789101112131415161718192021
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (!queue.peek().equals("Four")) { queue.poll(); } queue.poll(); System.out.println("Queue after removal operation: " + queue); } }

Você utilizou um loop com uma condição baseada no método peek().

É possível otimizar significativamente esse loop utilizando o método contains(). Esse método retorna true se o elemento especificado estiver presente na fila e false caso não esteja.

Vamos melhorar o código acima:

Main.java

Main.java

copy
1234567891011121314151617181920
package com.example; import java.util.LinkedList; import java.util.Queue; public class Main { public static void main(String[] args) { Queue<String> queue = new LinkedList<>(); queue.offer("One"); queue.offer("Two"); queue.offer("Three"); queue.offer("Four"); queue.offer("Five"); System.out.println("Queue: " + queue); while (queue.contains("Four")) { queue.poll(); } System.out.println("Queue after removal operation: " + queue); } }

Aqui, definimos uma única condição para o while loop. Conseguimos remover com sucesso todos os elementos até e incluindo o elemento "Four".

1. O que é uma Queue em Java?

2. Qual interface representa uma Queue no Java Collections Framework?

3. Qual é o propósito do método offer() na interface Queue?

4. O que o método poll() faz na interface Queue?

5. Qual classe no pacote java.util.concurrent do Java representa uma fila bloqueante limitada?

6. O que acontece se você tentar adicionar um elemento a uma fila cheia usando o método add()?

question mark

O que é uma Queue em Java?

Select the correct answer

question mark

Qual interface representa uma Queue no Java Collections Framework?

Select the correct answer

question mark

Qual é o propósito do método offer() na interface Queue?

Select the correct answer

question mark

O que o método poll() faz na interface Queue?

Select the correct answer

question mark

Qual classe no pacote java.util.concurrent do Java representa uma fila bloqueante limitada?

Select the correct answer

question mark

O que acontece se você tentar adicionar um elemento a uma fila cheia usando o método add()?

Select the correct answer

Tudo estava claro?

Como podemos melhorá-lo?

Obrigado pelo seu feedback!

Seção 2. Capítulo 1
some-alt