How to do non-integrable queue checking in Java

I help my son with a programming class in college, and I think I need a class too. He completed the task, but I do not think that he is doing it in the best way. Unfortunately, I can't get it to work with my best way. This is clearly better because it is not working yet.

He is invited to implement some methods for a class that extends another class.

He was told that he should use the following class definition, and he could not change anything in ListQueue.

public class MyListQueue <AnyType extends Comparable<AnyType>> extends ListQueue<AnyType> 

Here is what is in ListQueue

 // Queue interface // // ******************PUBLIC OPERATIONS********************* // void enqueue( x ) --> Insert x // AnyType getFront( ) --> Return least recently inserted item // AnyType dequeue( ) --> Return and remove least recent item // boolean isEmpty( ) --> Return true if empty; else false // void makeEmpty( ) --> Remove all items // ******************ERRORS******************************** // getFront or dequeue on empty queue /** * Protocol for queues. */ 

OK. I am very good at navigating a linked list to Pascal or C (showing my age), but I have never worked in OOP before.

When I try something like this

 dummyQueue = this.front.next; 

I get the following error. * front has personal access to ListQueue *

I agree with this, but I am not deleting the object, how can I cross the list or otherwise access the front, back, next and previous, which are all in ListQueue.

Education will be appreciated.

Thanks David

+4
source share
3 answers

If I understand you correctly, you are doing something like this:

 MyListQueue<String> dummyQueue = new MyListQueue<String>(); dummyQueue = this.front.next; 

If so, one of the basic principles of OOP is encapsulation, i.e. data hiding. The idea is that users outside the class do not have access to the internal state of the class.

If you want to determine the size of the queue, and you cannot change the interface or implementation, then one thing you could do is create a delegate Queue that redefines the queue and deactivation to increase and decrease the counter.

+2
source

If you decide on the queue, you usually only want to insert and deactivate elements. You want to know if the queue is empty and want to look at the front element if you need it or leave it for someone else. A queue is a kind of buffer that avoids blocking if the sender is faster than the receiver. With the queue, the receiver can decide when to read the next record. A queue can implement some (priority-based) sorting and decide which element is the front element.

If you need other operations, such as moving the list, then the queue may not be the best choice. Look at other types of collections, possibly ArrayList.

Some things can be done, but you can subclass ListQueue and override some methods. Therefore, if you need an extra size() method, this might be the solution:

 public class MyListQueue <T extends Comparable<T>> extends ListQueue<T> { private size = 0; public void enqueue(T element) { size++; super.enqueue(element); } public T dequeue() { if (isEmpty()) { return null; // that a guess... } size--; super.dequeue(element); } public int size() { return size; } } 

I replaced AnyType with T, which is more common.

+1
source

You asked: "Besides deleting the object, how can I go through the list or otherwise access the front, back, next and previous, which are all in ListQueue."

In its purest form, you cannot.

An idealized queue of promises is just a few things:

  • Insert items in the back
  • Pop elements in front
  • (Possibly) Check the front element if it is not empty.
  • (possibly) A predicate of a definition space for pop and a check to determine if the queue is empty.

I assume at the moment that the queue is not intended for use with simultaneous readers (simultaneously with access to the front) or with simultaneous readers and writers (while turning back and forth).

Given this definition, there is no reason to want to look "inside" the queue. You put things on one side and take things on the other side. If you consider queue size limits, you might need an additional definition space predicate for the push operation to determine if the queue is full. "Being complete" only makes sense if the queue is limited. "Being empty" makes sense only if the call to the stream or check the stream do not want to block.

In addition, there is a pragmatic idea of โ€‹โ€‹a lineup. We can assume that this is a sequence of elements that - prohibiting concurrency problems - are of observable non-negative size and may even allow each element to be visited in the sequence. Some queues even go so far as to remove or reorder items at positions other than the front of the sequence. However, at this point we are no longer discussing the lineup. We discuss the sequence that underlies the queue. If we need such access, we do not need a queue. We need the sequence that we want to offer as a queue to other parts of the program.

This is why queues are usually not specific types in data structure libraries. In C ++, type std::queue - this is a decorator around another type of container. In Java, java.util.Queue is an interface. Scala use a different approach: class scala.collection.mutable.Queue is an extension of type MutableList . This is similar to the approach provided for in your sonโ€™s appointment, but it is unclear whether your ListQueue allowed outsiders (including subclasses) to use its โ€œlist natureโ€ - to penetrate the queue view to use the sequence inside.

Do you have a requirement to be able to visit anything other than the head of your lineup? The need for this limits your choice of which types of queues your consumer functions can use. It looks like we are learning the wrong lessons with this assignment.

0
source

Source: https://habr.com/ru/post/1300500/


All Articles