11package com .bobocode .linked_list ;
22
3-
4- import com .bobocode .util .ExerciseNotCompletedException ;
3+ import java .util .NoSuchElementException ;
4+ import java .util .Objects ;
5+ import java .util .stream .Stream ;
56
67/**
78 * {@link LinkedList} is a list implementation that is based on singly linked generic nodes. A node is implemented as
1011 * @param <T> generic type parameter
1112 */
1213public class LinkedList <T > implements List <T > {
14+ private Node <T > head ;
15+ private Node <T > tail ;
16+ private int size ;
1317
1418 /**
1519 * This method creates a list of provided elements
@@ -19,7 +23,9 @@ public class LinkedList<T> implements List<T> {
1923 * @return a new list of elements the were passed as method parameters
2024 */
2125 public static <T > List <T > of (T ... elements ) {
22- throw new ExerciseNotCompletedException (); // todo: implement this method
26+ LinkedList <T > linkedList = new LinkedList <>();
27+ Stream .of (elements ).forEach (linkedList ::add );
28+ return linkedList ;
2329 }
2430
2531 /**
@@ -29,7 +35,7 @@ public static <T> List<T> of(T... elements) {
2935 */
3036 @ Override
3137 public void add (T element ) {
32- throw new ExerciseNotCompletedException (); // todo: implement this method
38+ add ( size , element );
3339 }
3440
3541 /**
@@ -41,7 +47,51 @@ public void add(T element) {
4147 */
4248 @ Override
4349 public void add (int index , T element ) {
44- throw new ExerciseNotCompletedException (); // todo: implement this method
50+ Node <T > newNode = Node .valueOf (element );
51+ if (index == 0 ) {
52+ addAsHead (newNode );
53+ } else if (index == size ) {
54+ addAsTail (newNode );
55+ } else {
56+ add (index , newNode );
57+ }
58+ size ++;
59+ }
60+
61+ private void addAsHead (Node <T > newNode ) {
62+ newNode .next = head ;
63+ head = newNode ;
64+ if (head .next == null ) {
65+ tail = head ;
66+ }
67+ }
68+
69+ private void addAsTail (Node <T > newNode ) {
70+ tail .next = newNode ;
71+ tail = newNode ;
72+ }
73+
74+ private void add (int index , Node <T > newNode ) {
75+ Node <T > node = findNodeByIndex (index - 1 );
76+ newNode .next = node .next ;
77+ node .next = newNode ;
78+ }
79+
80+ private Node <T > findNodeByIndex (int index ) {
81+ Objects .checkIndex (index , size );
82+ if (index == size - 1 ) {
83+ return tail ;
84+ } else {
85+ return nodeAt (index );
86+ }
87+ }
88+
89+ private Node <T > nodeAt (int index ) {
90+ Node <T > currentNode = head ;
91+ for (int i = 0 ; i < index ; i ++) {
92+ currentNode = currentNode .next ;
93+ }
94+ return currentNode ;
4595 }
4696
4797 /**
@@ -53,7 +103,8 @@ public void add(int index, T element) {
53103 */
54104 @ Override
55105 public void set (int index , T element ) {
56- throw new ExerciseNotCompletedException (); // todo: implement this method
106+ Node <T > node = findNodeByIndex (index );
107+ node .value = element ;
57108 }
58109
59110 /**
@@ -65,7 +116,8 @@ public void set(int index, T element) {
65116 */
66117 @ Override
67118 public T get (int index ) {
68- throw new ExerciseNotCompletedException (); // todo: implement this method
119+ Node <T > node = findNodeByIndex (index );
120+ return node .value ;
69121 }
70122
71123 /**
@@ -76,7 +128,8 @@ public T get(int index) {
76128 */
77129 @ Override
78130 public T getFirst () {
79- throw new ExerciseNotCompletedException (); // todo: implement this method
131+ checkElementsExist ();
132+ return head .value ;
80133 }
81134
82135 /**
@@ -87,20 +140,44 @@ public T getFirst() {
87140 */
88141 @ Override
89142 public T getLast () {
90- throw new ExerciseNotCompletedException (); // todo: implement this method
143+ checkElementsExist ();
144+ return tail .value ;
145+ }
146+
147+ private void checkElementsExist () {
148+ if (head == null ) {
149+ throw new NoSuchElementException ();
150+ }
91151 }
92152
93153 /**
94154 * Removes an elements by its position index. In case provided index in out of the list bounds it
95155 * throws {@link IndexOutOfBoundsException}
96156 *
97157 * @param index element index
158+ * @return an element value
98159 */
99160 @ Override
100161 public void remove (int index ) {
101- throw new ExerciseNotCompletedException (); // todo: implement this method
162+ if (index == 0 ) {
163+ Objects .checkIndex (index , size );
164+ removeHead ();
165+ } else {
166+ Node <T > previousNode = findNodeByIndex (index - 1 );
167+ previousNode .next = previousNode .next .next ;
168+ if (index == size - 1 ) {
169+ tail = previousNode ;
170+ }
171+ }
172+ size --;
102173 }
103174
175+ private void removeHead () {
176+ head = head .next ;
177+ if (head == null ) {
178+ tail = null ;
179+ }
180+ }
104181
105182 /**
106183 * Checks if a specific exists in he list
@@ -109,7 +186,14 @@ public void remove(int index) {
109186 */
110187 @ Override
111188 public boolean contains (T element ) {
112- throw new ExerciseNotCompletedException (); // todo: implement this method
189+ Node <T > currentNode = head ;
190+ while (currentNode != null ) {
191+ if (currentNode .value .equals (element )) {
192+ return true ;
193+ }
194+ currentNode = currentNode .next ;
195+ }
196+ return false ;
113197 }
114198
115199 /**
@@ -119,7 +203,7 @@ public boolean contains(T element) {
119203 */
120204 @ Override
121205 public boolean isEmpty () {
122- throw new ExerciseNotCompletedException (); // todo: implement this method
206+ return head == null ;
123207 }
124208
125209 /**
@@ -129,14 +213,28 @@ public boolean isEmpty() {
129213 */
130214 @ Override
131215 public int size () {
132- throw new ExerciseNotCompletedException (); // todo: implement this method
216+ return size ;
133217 }
134218
135219 /**
136220 * Removes all list elements
137221 */
138222 @ Override
139223 public void clear () {
140- throw new ExerciseNotCompletedException (); // todo: implement this method
224+ head = tail = null ;
225+ size = 0 ;
226+ }
227+
228+ static class Node <T > {
229+ private T value ;
230+ private Node <T > next ;
231+
232+ private Node (T value ) {
233+ this .value = value ;
234+ }
235+
236+ public static <T > Node <T > valueOf (T value ) {
237+ return new Node <>(value );
238+ }
141239 }
142240}
0 commit comments