Adding elements to cyclic Single Linked Lists - java

I am trying to add an element to the end of a cyclic Single Linked List for my homework
assignment. But for some reason I am having a lot of problems.
I have a _tail pointer, and _dummy. The add method in JUnit test says that when checking the add method it returns null instead of 1. (1 being what was added to list)
Here is my code
private static class Node<T>{
Node<T> next;
T data;
public Node(T data, Node<T> next){
this.next = next;
this.data = data;
}
}
private Node<T> _tail;
private int _count;
private int _version;
private Node<T> _dummy;
public CyclicLinkedList(){
_dummy = new Node<T>(null, null);
_dummy.next = _dummy;
_tail = _dummy;
_count = 0;
assert _wellFormed();
}
and here is my add method
#Override
public boolean add(T x){
assert _wellFormed();
Node<T> n = new Node<T>(x, _tail.next);
_tail.next = n;
_tail = n;
++_version;
++_count;
assert _wellFormed();
return true;
}
The assertWellformed states that the linked list is wrongly cyclic. The _wellFormed() method has already been implemented by the class instructor so that is not the problem. Need some pointers! Thanks. Here is the test to see if the test is wrongly cyclic.
// check for cycles:
Node<T> fast = _tail.next;
for (Node<T> p = _tail; fast != null && fast.next != null && fast != _tail && fast.next != _tail; p = p.next) {
if (p == fast) return _report("list is wrongly cyclic");
fast = fast.next.next;
}

_tail.next = n;
_tail = n;
You should add one more line at the start of that code in add method:-
n.next = _tail.next;
So, your code becomes: -
n.next = _tail.next;
_tail.next = n;
_tail = n;
You need to make your new node point to the first node, to make it cyclic.
And since, _tail.next I assume must be pointing to the first element, before adding a new node to the List, so assign _tail.next to n.next before adding it to the list to make n also now point to the first node.
So, at the first line, both your nodes: - n node and _tail node, point to the first node. Now, detach your _tail node from first node, and make it point to the n node. And at last, make your n node as _tail node.

Related

how pointer works in singly linked list?

i have this code for singly linked list and it works. I understand theoretically the principle of singly linked list, but when it comes to code I dont understand how the pointer works. my problem is in this two lines code which is part of the code mentioned in the last
p.next = new Node<>(a[i], null);
p = p.next;
why we call next by p and create new node then assign null to next at the same time through parameter.? then giving p value of p.next which supposed to be null? i tried to print out p.next and next to see if they are the same or there is difference and I got in console an address for p.next and null for next. how they differ from each other ? I need some explanation in this part of code and how the node and the pointer is created.
public class EnkeltLenketListe<T> implements Liste<T> {
private static final class Node<T>
{
private T value;
private Node<T> next;
private Node(T value, Node<T> next)
{
this.next = next;
this.value = value;
}
}
private Node<T> head, tail;
private int counter;
public EnkeltLenketListe(T[] a)
{
this();
int i = 0; for (; i < a.length && a[i] == null; i++);
if (i < a.length)
{
head = new Node<>(a[i], null);
Node<T> p = head;
counter = 1;
for (i++; i < a.length; i++)
{
if (a[i] != null)
{
p.next = new Node<>(a[i], null);
p = p.next;
counter++;
}
}
tail = p;
}
}
There are two pointers here to think about.
Pointer p pounts to the current node, which is the last node in the list.
p.next points to what will be the next node if there will be a new node added.
p.next = new Node<>(a[i], null);
This line creates a new node in the next spot (you are adding a node to the end of the list).
p = p.next;
This line tells the current pointer p to point to the newly created node at the end of the list (it is not null, you just created a new node there).

BST - counting nodes with left and right children

As stated in the title, I'm trying to solve this problem by only counting nodes in a BST that have both left and right children. I'm struggling to think of the logic to solve this.
I thought of something like this.
First, check if the root is null or if it has any null children. Next, traverse the tree going right and continue to check the children, increment a counter when the conditions are met. But what happens when I reach the end node and need to go back to a node that had a left child to traverse? I had a temp node to keep track of the most previous parent, but what about when I need to go up more than one level? I'm assuming the answer to this problem is to recursively solve it, but I don't even know where to begin.
Here's what I have:
public int fullNodes() {
int count = 0;
Node n = root;
Node temp = null;
if (n == null || n.left == null && n.right == null) return count;
count++; //increment count, since the root has children on both sides
temp = n; //hold the previous place
n = n.right; //go right
//Now what?
return count;
}
I'm still struggling to think recursively when problem solving, in addition to my question, how do you learn to think recursively? Just a ton of practice, or is there some tricks and tips that you use to solve problems?
Rather than using a temp variable to hold the previous node -- which would only work for a depth of 1 -- call the same function on the child nodes.
Recursive tree traversal might look something like this:
public int countSomething (Node node) {
// Self;
//
int result = 1; // use your required logic here
// Children;
//
if (node.left != null)
result += countSomething( node.left);
if (node.right != null)
result += countSomething( node.right);
// done.
return result;
}
// example usages
int treeTotal = countSomething( rootNode);
int subtreeTotal = countSomething( subtree);
The execution callstack will then hold recursive invocations of the function, each with their appropriate context. When the top-level call returns, it will have summed the answer for the entire tree/ or subtree it was called on.
Put appropriate logic for your BST "node has both left & right children" in, instead of the constant 1.
First let us create representation of your Node class
class Node {
public Node left;
public Node right;
public Node(){}
public Node(Node left, Node right) {
this.left = left;
this.right = right;
}
}
Then we write our recusrive function and client that uses your function
public class Main {
public static int countNodes(Node root) {
if(root!=null && root.left!=null && root.right!=null) {
return 1+countNodes(root.left)+countNodes(root.right);
}
return 0;
}
public static void main(String[] args) {
Node right = new Node();
Node left = new Node();
Node root = new Node(left, right);
root.right = new Node(new Node(), new Node());
System.out.println(countNodes(root));
}
}

Will my Circular LinkedList work correctly?

So I am currently trying to create a circle linked list (double linked list with each value having a previous, and a next value not equal to null), and I am not sure if I am properly creating it. My goal is to be able to create a LinkedList of values, and then when I iterate through the list, hasNext() should always return true (no null values). I think there is something wrong with the way I am adding values, but I am not sure. Here is the code, with the CircularList class having an inner node class:
public class CircularList<E> {
//I decided to still have heads and tails, to link them together
private Node<E> first = null;
private Node<E> last = null;
private Node<E> temp;
private int size;
//inner node class
private static class Node<E>{ //In this case I am using String nodes
private E data; //matching the example in the book, this is the data of the node
private Node<E> next; //next value
private Node<E> prev; //previous value
//Node constructors, also since in this case this is a circular linked list there should be no null values for previous and next
private Node(E data, Node<E> next, Node<E> prev){
this.data = data;
this.next = next;
this.prev = prev;
}
}
//end of inner node class
public void addValue(E item){
Node<E> n = new Node<E>(item, first, last);
if(emptyList() == true){ //if the list is empty
//only one value in the list
first = n;
last = n;
}
else{ //if the list has at least one value already
temp = first;
first = n;
first.next = temp;
last.next = first;
}
size++;
}
public boolean emptyList(){
boolean result = false;
if(first == null && last == null){ //if there is no values at all
result = true;
}
return result;
}
}
Just did a quick scan but this is the bit where it goes wrong:
Node<E> n = new Node<E>(item, first, last);
if(emptyList() == true) {
//if the list is empty
//only one value in the list
first = n;
last = n;
}
The prev and next item inside node are still null here. You should set those too.
else {
//if the list has at least one value already
temp = first;
first = n;
first.next = temp;
last.next = first;
}
Additionally you're not updating prev here.
Also consider using a linked list internally as a backing data structure rather then your own node structure. Then you only have to create the circular iterator.

Ordered LinkedList logic in Java, LinearNode head is being reassigned each time

I have a generic ordered Linked List class. For some reason, LinearNode head is being reassigned every single time I run add(). Any ideas? Why would head be changed each time I run this? I'm not even touching it. I can provide the other classes for testing, if needed.
public class myOrLiList<T extends Comparable<T>> {
public LinearNode head;
public int count;
public myOrLiList() {
head = null;
count = 0;
}
// LinearNode INNER CLASS
public class LinearNode {
public LinearNode next;
public T item;
public LinearNode(T thisitem) {
this.next = null;
this.item = thisitem;
}
}
public boolean isEmpty() {
return (head == null);
}
public void add(T thisItem) {
LinearNode newNode = new LinearNode(thisItem);
if (isEmpty()) {
head = newNode;
System.out.println("head filled!");
} else {
LinearNode compareNode = head;
do {
if (thisItem.compareTo(compareNode.item) < 0) {
newNode.next = compareNode;
break;
} else if ((thisItem.compareTo(compareNode.item) < 0)
|| (thisItem.compareTo(compareNode.item) == 0)) {
newNode.next = compareNode.next;
compareNode.next = newNode;
break;
} else {
compareNode = compareNode.next;
}
} while (compareNode.next != null);
}
System.out.println("Added!");
count++;
}
Thanks for your help.
The reason that your head is changing is because of this line:
compareNode = compareNode.next;
Earlier you did this:
LinearNode compareNode = head;
You're literally saying that compareNode IS your head object. You're setting the Object reference that points to head to also point to compareNode. Any actions you take on compareNode will affect head the exact same way.
Because you set compareNode = head, these two lines do the same thing to the same object reference:
compareNode.next = null;
head.next = null;
I see a couple of other things wrong. I'll try and go over them one by one.
Your logic for when the LinkedList is empty appears to be correct...
However,
if you add a second node when the list's size is 1, you're going to have some problems...
if (thisItem.compareTo(compareNode.item) < 0) you call this code and then break out:
newNode.next = compareNode;
break;
What are you doing with newNode after that? The answer is nothing. Since you didn't update head, nothing has changed. You created a LinearNode, set it's next value equal to the head, and then left it to die.
What I think you want to do is get a reference to the old node stored at head, save it, then set your head variable equal to your new node. Then you'll set newNode.next (where newNode is now head) equal to your OLD head node, which you saved. So you'll have something like this:
LinearNode oldHead = head;
head = newNode;
head.next = oldHead;
Now for the next part. You have an
if ((thisItem.compareTo(compareNode.item) < 0) || (thisItem.compareTo(compareNode.item) == 0))
You already covered the case where compareNode.item < 0, so why are you checking it again? It won't mess up your logic, but it's redundant.
Essentially, what you're trying to do is place your newNode before the current node if it compares to be < 0, place your newNode after the current node if it compares to be > 0, and either replace or do nothing if the currentElement ends up being == 0.
I've covered the < 0 case, so you should try and figure out how to do the greater than and equal cases.
While this class has some errors (Thanks for the tips, Michael!) the question I asked did not come from these errors.
In the new object class I had created for T, I had declared static properties. So, each time a new T thisItem was being created, all of the properties of all objects were being changed.

Invert linear linked list

a linear linked list is a set of nodes. This is how a node is defined (to keep it easy we do not distinguish between node an list):
class Node{
Object data;
Node link;
public Node(Object pData, Node pLink){
this.data = pData;
this.link = pLink;
}
public String toString(){
if(this.link != null){
return this.data.toString() + this.link.toString();
}else{
return this.data.toString() ;
}
}
public void inc(){
this.data = new Integer((Integer)this.data + 1);
}
public void lappend(Node list){
Node child = this.link;
while(child != null){
child = child.link;
}
child.link = list;
}
public Node copy(){
if(this.link != null){
return new Node(new Integer((Integer)this.data), this.link.copy());
}else{
return new Node(new Integer((Integer)this.data), null);
}
}
public Node invert(){
Node child = this.link;
while(child != null){
child = child.link;
}
child.link = this;....
}
}
I am able to make a deep copy of the list. Now I want to invert the list so that the first node is the last and the last the first. The inverted list has to be a deep copy.
I started developing the invert function but I am not sure. Any Ideas?
Update: Maybe there is a recursive way since the linear linked list is a recursive data structure.
I would take the first element, iterate through the list until I get to a node that has no child and append the first element, I would repeat this for the second, third....
I sometimes ask this question in interviews...
I would not recommend using a recursive solution, or using a stack to solve this. There's no point in allocating O(n) memory for such a task.
Here's a simple O(1) solution (I didn't run it right now, so I apologize if it needs some correction).
Node reverse (Node current) {
Node prev = null;
while (current != null) {
Node nextNode = current.next;
current.next = prev;
prev = current;
current = nextNode;
}
return prev;
}
BTW: Does the lappend method works? It seems like it would always throw a NullReferenceException.
There's a great recursive solution to this problem based on the following observations:
The reverse of the empty list is the empty list.
The reverse of a singleton list is itself.
The reverse of a list of a node N followed by a list L is the reverse of the list L followed by the node N.
You can therefore implement the reverse function using pseudocode along these lines:
void reverseList(Node node) {
if (node == null) return; // Reverse of empty list is itself.
if (node.next == null) return; // Reverse of singleton list is itself.
reverseList(node.next); // Reverse the rest of the list
appendNodeToList(node, node.next); // Append the new value.
}
A naive implementation of this algorithm runs in O(n2), since each reversal requires an append, which requires an O(n) scan over the rest of the list. However, you can actually get this working in O(n) using a clever observation. Suppose that you have a linked list that looks like this:
n1 --> n2 --> [rest of the list]
If you reverse the list beginning at n2, then you end up with this setup:
n1 [reverse of rest of the list] --> n2
| ^
+------------------------------------------+
So you can append n1 to the reverse of the rest of the list by setting n1.next.next = n1, which changes n2, the new end of the reverse list, to point at n1:
[reverse of the rest of the list] --> n2 --> n1
And you're golden! Again more pseudocode:
void reverseList(Node node) {
if (node == null) return; // Reverse of empty list is itself.
if (node.next == null) return; // Reverse of singleton list is itself.
reverseList(node.next); // Reverse the rest of the list
node.next.next = node; // Append the new value.
}
EDIT: As Ran pointed out, this uses the call stack for its storage space and thus risks a stack overflow. If you want to use an explicit stack instead, you can do so like this:
void reverseList(Node node) {
/* Make a stack of the reverse of the nodes. */
Stack<Node> s = new Stack<Node>();
for (Node curr = node; node != null; node = node.next)
s.push(curr);
/* Start unwinding it. */
Node curr = null;
while (!s.empty()) {
Node top = s.pop();
/* If there is no node in the list yet, set it to the current node. */
if (curr == null)
curr = top;
/* Otherwise, have the current node point to this next node. */
else
curr.next = top;
/* Update the current pointer to be this new node. */
curr = top;
}
}
I believe that this similarly inverts the linked list elements.
I would treat the current list as a stack (here's my pseudo code):
Node x = copyOf(list.head);
x.link = null;
foreach(node in list){
Node temp = copyOf(list.head);
temp.link = x;
x = temp;
}
At the end x will be the head of the reversed list.
I more fammiliar whit C, but still let me try. ( I just do not sure if this runs in Java, but it should)
node n = (well first one)
node prev = NULL;
node t;
while(n != NULL)
{
t = n.next;
n.next = prev;
prev = n;
n = t;
}
Reversing a single-linked list is sort of a classic question. It's answered here as well (and well answered), it does not requires recursion nor extra memory, besides a register (or 2) for reference keeping.
However to the OP, I guess it's a school project/homework and some piece of advice, if you ever get to use single linked list for some real data storage, consider using a tail node as well. (as of now single linked lists are almost extinct, HashMap buckets comes to mind, though).
Unless you have to check all the nodes for some condition during 'add', tail is quite an improvement. Below there is some code that features the reverse method and a tail node.
package t1;
public class SList {
Node head = new Node();
Node tail = head;
private static class Node{
Node link;
int data;
}
void add(int i){
Node n = new Node();
n.data = i;
tail = tail.link =n;
}
void reverse(){
tail = head;
head = reverse(head);
tail.link = null;//former head still links back, so clear it
}
private static Node reverse(Node head){
for (Node n=head.link, link; n!=null; n=link){//essentially replace head w/ the next and relink
link = n.link;
n.link = head;
head = n;
}
return head;
}
void print(){
for (Node n=head; n!=null;n=n.link){
System.out.println(n.data);
}
}
public static void main(String[] args) {
SList l = new SList();
l.add(1);l.add(2);l.add(3);l.add(4);
l.print();
System.out.println("==");
l.reverse();
l.print();
}
}
I was wondering something like that(I didnt test it, so):
invert(){
m(firstNode, null);
}
m(Node v, Node bef){
if(v.link != null)
m(v.link,v);
else
v.link=bef;
}
Without much testing,
Node head = this;
Node middle = null;
Node trail = null;
while (head != null) {
trail = middle;
middle = head;
head = head.link;
middle.link = trail;
}
head = middle;
return head;
public ListNode Reverse(ListNode list)
{
if (list == null) return null;
if (list.next == null) return list;
ListNode secondElem = list.next;
ListNode reverseRest = Reverse(secondElem);
secondElem.Next = list;
return reverseRest;
}
Hope this helps.

Categories