Remove the first value for a doubly linked list
![Creative The name of the picture](https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgO9GURib1T8z7lCwjOGLQaGtrueEthgQ8LO42ZX8cOfTqDK4jvDDpKkLFwf2J49kYCMNW7d4ABih_XCb_2UXdq5fPJDkoyg7-8g_YfRUot-XnaXkNYycsNp7lA5_TW9td0FFpLQ2APzKcZ/s1600/1.jpg)
![Creative The name of the picture](https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhYQ0N5W1qAOxLP7t7iOM6O6AzbZnkXUy16s7P_CWfOb5UbTQY_aDsc727chyphenhyphen5W4IppVNernMMQeaUFTB_rFzAd95_CDt-tnwN-nBx6JyUp2duGjPaL5-VgNO41AVsA_vu30EJcipdDG409/s400/Clash+Royale+CLAN+TAG%2523URR8PPP.png)
up vote
5
down vote
favorite
You need to remove the first element which contains a given value from a doubly linked list.
I created two solutions since I find the edge case of removing the first element to be problematic. So I solved it using 2 approaches:
- using void function and ref
- using return value
using System;
using System.Diagnostics;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace LinkedListQuestions
//remove the first element in the list which equals to value
[TestClass]
public class DoublyLinkedListTest
private Node head;
[TestInitialize]
public void InitList()
head = new Node();
Node two = new Node();
Node three = new Node();
Node four = new Node();
head.Value = 1;
head.Next = two;
two.Value = 2;
two.Prev = head;
two.Next = three;
three.Value = 3;
three.Next = four;
three.Prev = two;
four.Value = 4;
four.Prev = three;
[TestMethod]
public void RemoveValueRefFromMiddleOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 3);
Assert.AreEqual(1, head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromMiddleOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 3);
Assert.AreEqual(1,head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueRefFromTopOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromTopOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
public class DoublyLinkedListHelper
public static void RemoveRefElement(ref Node head, int value)
if (head == null)
return;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
head = next;
break;
prev = curr;
curr = next;
next = curr.Next;
public static Node RemoveElement(Node head, int value)
if (head == null)
return null;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
return next;
else
return head;
break;
prev = curr;
curr = next;
next = curr.Next;
return head;
public class Node
public int Value get; set;
public Node Prev get; set;
public Node Next get; set;
c# unit-testing linked-list interview-questions comparative-review
add a comment |Â
up vote
5
down vote
favorite
You need to remove the first element which contains a given value from a doubly linked list.
I created two solutions since I find the edge case of removing the first element to be problematic. So I solved it using 2 approaches:
- using void function and ref
- using return value
using System;
using System.Diagnostics;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace LinkedListQuestions
//remove the first element in the list which equals to value
[TestClass]
public class DoublyLinkedListTest
private Node head;
[TestInitialize]
public void InitList()
head = new Node();
Node two = new Node();
Node three = new Node();
Node four = new Node();
head.Value = 1;
head.Next = two;
two.Value = 2;
two.Prev = head;
two.Next = three;
three.Value = 3;
three.Next = four;
three.Prev = two;
four.Value = 4;
four.Prev = three;
[TestMethod]
public void RemoveValueRefFromMiddleOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 3);
Assert.AreEqual(1, head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromMiddleOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 3);
Assert.AreEqual(1,head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueRefFromTopOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromTopOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
public class DoublyLinkedListHelper
public static void RemoveRefElement(ref Node head, int value)
if (head == null)
return;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
head = next;
break;
prev = curr;
curr = next;
next = curr.Next;
public static Node RemoveElement(Node head, int value)
if (head == null)
return null;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
return next;
else
return head;
break;
prev = curr;
curr = next;
next = curr.Next;
return head;
public class Node
public int Value get; set;
public Node Prev get; set;
public Node Next get; set;
c# unit-testing linked-list interview-questions comparative-review
add a comment |Â
up vote
5
down vote
favorite
up vote
5
down vote
favorite
You need to remove the first element which contains a given value from a doubly linked list.
I created two solutions since I find the edge case of removing the first element to be problematic. So I solved it using 2 approaches:
- using void function and ref
- using return value
using System;
using System.Diagnostics;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace LinkedListQuestions
//remove the first element in the list which equals to value
[TestClass]
public class DoublyLinkedListTest
private Node head;
[TestInitialize]
public void InitList()
head = new Node();
Node two = new Node();
Node three = new Node();
Node four = new Node();
head.Value = 1;
head.Next = two;
two.Value = 2;
two.Prev = head;
two.Next = three;
three.Value = 3;
three.Next = four;
three.Prev = two;
four.Value = 4;
four.Prev = three;
[TestMethod]
public void RemoveValueRefFromMiddleOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 3);
Assert.AreEqual(1, head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromMiddleOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 3);
Assert.AreEqual(1,head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueRefFromTopOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromTopOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
public class DoublyLinkedListHelper
public static void RemoveRefElement(ref Node head, int value)
if (head == null)
return;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
head = next;
break;
prev = curr;
curr = next;
next = curr.Next;
public static Node RemoveElement(Node head, int value)
if (head == null)
return null;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
return next;
else
return head;
break;
prev = curr;
curr = next;
next = curr.Next;
return head;
public class Node
public int Value get; set;
public Node Prev get; set;
public Node Next get; set;
c# unit-testing linked-list interview-questions comparative-review
You need to remove the first element which contains a given value from a doubly linked list.
I created two solutions since I find the edge case of removing the first element to be problematic. So I solved it using 2 approaches:
- using void function and ref
- using return value
using System;
using System.Diagnostics;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace LinkedListQuestions
//remove the first element in the list which equals to value
[TestClass]
public class DoublyLinkedListTest
private Node head;
[TestInitialize]
public void InitList()
head = new Node();
Node two = new Node();
Node three = new Node();
Node four = new Node();
head.Value = 1;
head.Next = two;
two.Value = 2;
two.Prev = head;
two.Next = three;
three.Value = 3;
three.Next = four;
three.Prev = two;
four.Value = 4;
four.Prev = three;
[TestMethod]
public void RemoveValueRefFromMiddleOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 3);
Assert.AreEqual(1, head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromMiddleOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 3);
Assert.AreEqual(1,head.Value);
Assert.AreEqual(2, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueRefFromTopOfListTest()
DoublyLinkedListHelper.RemoveRefElement(ref head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
[TestMethod]
public void RemoveValueFromTopOfListTest()
head = DoublyLinkedListHelper.RemoveElement(head, 1);
Assert.AreEqual(2, head.Value);
Assert.AreEqual(3, head.Next.Value);
Assert.AreEqual(4, head.Next.Next.Value);
public class DoublyLinkedListHelper
public static void RemoveRefElement(ref Node head, int value)
if (head == null)
return;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
head = next;
break;
prev = curr;
curr = next;
next = curr.Next;
public static Node RemoveElement(Node head, int value)
if (head == null)
return null;
Node curr = head;
Node prev = null;
Node next = head.Next;
while (curr != null)
if (curr.Value == value)
if (prev != null)
prev.Next = next;
if (next != null)
next.Prev = prev;
curr.Next = null;
curr.Prev = null;
if (curr == head)
return next;
else
return head;
break;
prev = curr;
curr = next;
next = curr.Next;
return head;
public class Node
public int Value get; set;
public Node Prev get; set;
public Node Next get; set;
c# unit-testing linked-list interview-questions comparative-review
c# unit-testing linked-list interview-questions comparative-review
edited Aug 9 at 1:38
![](https://i.stack.imgur.com/1f9W9.png?s=32&g=1)
![](https://i.stack.imgur.com/1f9W9.png?s=32&g=1)
200_success
124k14144401
124k14144401
asked Aug 8 at 6:39
![](https://i.stack.imgur.com/u6PCt.jpg?s=32&g=1)
![](https://i.stack.imgur.com/u6PCt.jpg?s=32&g=1)
Gilad
1,21121326
1,21121326
add a comment |Â
add a comment |Â
2 Answers
2
active
oldest
votes
up vote
6
down vote
accepted
The methods look fine to me. Reasonable variable names; no confusing control-flow; sensible enough signatures for what they are doing. (see t2chb0t's answer as to why I am wrong)
The tests could be more comprehensive. They should probably check the length of the list, and since the whole data-structure is exposed, you ought verify that the list isn't otherwise malformed (e.g. head.prev
should always be null
, especially worth checking in the special case of removing the head
from the list).
The 'edge case' you have is because you've got a quick-and-nasty definition of a linked list as just 'the head node' (or null
). The effect is that you are exposing a highly mutable data-structure which is easy to misuse. Much much better, would be to hide the Node
s away under a LinkedList
type, which provides a simple interface (e.g. Add(T)
, Remove(T)
, GetEnumerator()
) without exposing any implementation details.
public class LinkedList
private Node Head; // keep track of the head
public LinkedList()
// start empty...
Head = null;
Remove(int value)
RemoveRefElement(ref Head, value);
// some more public methods and helper methods...
Having such an interface solves your 'edge case' interface problem, because the edge case is now an implementation detail, and instead you have a nice interface. I'd argue that your Ref
version is better, because it is modifying the data-structure passed to it, which the return
version doesn't make entirely clear. Having a LinkedList
class with a nice Remove
member that returns nothing serves the same purpose, and allows you to pass the LinkedList
around (you can't pass the Head
node around as a mutable list, because if it is removed from the list, then everyone except the caller suddenly has a list with exactly one element in it). Having a well-defined interface also makes writing tests easier, because you don't have to think about whether the data-structure is 'correct' or not, just whether it does the job.
As an implementation detail, I'd maintain that the Ref
version would be better, but once something is private it matters less what it looks like.
Petty stuff:
Inline documentation (
///
) is always appreciatedThe
break
is redundant inRemoveElement
, and I'd personally make thebreak
inRemoveRefElement
areturn
(just makes it clearer that the method has ended)Personally I'd appreciate more empty lines. The back-to-back
if
s, for example, would be easier for me to scan if they were separated, since they are separate pieces of logic.A generic implementation would always be nice, and gives you a chance to demonstrate awareness of how to do comparisons effectively.
@thanks for the answer
â Gilad
Aug 8 at 11:35
add a comment |Â
up vote
6
down vote
Since this is an interview-question here's how I see it.
I'd accept your code for a position of a junior-developer without much criticism but I would reject it for anything higher than that.
If you were applying for a senior-developer position then I'm of a quite different opinion than @VisualMelon. The methods don't make a good impression on me because they do too much. Your task is to remove an item but what you are doing is not only that. You are also searching for it. The searching part should be moved to its own method. I also find the variable names should not be abbreviated and instead you should use full words like current
and previous
. I agree with other suggestions by @VisualMelon.
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members ofNode
are shortened... these most definitely should not be!)
â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
add a comment |Â
2 Answers
2
active
oldest
votes
2 Answers
2
active
oldest
votes
active
oldest
votes
active
oldest
votes
up vote
6
down vote
accepted
The methods look fine to me. Reasonable variable names; no confusing control-flow; sensible enough signatures for what they are doing. (see t2chb0t's answer as to why I am wrong)
The tests could be more comprehensive. They should probably check the length of the list, and since the whole data-structure is exposed, you ought verify that the list isn't otherwise malformed (e.g. head.prev
should always be null
, especially worth checking in the special case of removing the head
from the list).
The 'edge case' you have is because you've got a quick-and-nasty definition of a linked list as just 'the head node' (or null
). The effect is that you are exposing a highly mutable data-structure which is easy to misuse. Much much better, would be to hide the Node
s away under a LinkedList
type, which provides a simple interface (e.g. Add(T)
, Remove(T)
, GetEnumerator()
) without exposing any implementation details.
public class LinkedList
private Node Head; // keep track of the head
public LinkedList()
// start empty...
Head = null;
Remove(int value)
RemoveRefElement(ref Head, value);
// some more public methods and helper methods...
Having such an interface solves your 'edge case' interface problem, because the edge case is now an implementation detail, and instead you have a nice interface. I'd argue that your Ref
version is better, because it is modifying the data-structure passed to it, which the return
version doesn't make entirely clear. Having a LinkedList
class with a nice Remove
member that returns nothing serves the same purpose, and allows you to pass the LinkedList
around (you can't pass the Head
node around as a mutable list, because if it is removed from the list, then everyone except the caller suddenly has a list with exactly one element in it). Having a well-defined interface also makes writing tests easier, because you don't have to think about whether the data-structure is 'correct' or not, just whether it does the job.
As an implementation detail, I'd maintain that the Ref
version would be better, but once something is private it matters less what it looks like.
Petty stuff:
Inline documentation (
///
) is always appreciatedThe
break
is redundant inRemoveElement
, and I'd personally make thebreak
inRemoveRefElement
areturn
(just makes it clearer that the method has ended)Personally I'd appreciate more empty lines. The back-to-back
if
s, for example, would be easier for me to scan if they were separated, since they are separate pieces of logic.A generic implementation would always be nice, and gives you a chance to demonstrate awareness of how to do comparisons effectively.
@thanks for the answer
â Gilad
Aug 8 at 11:35
add a comment |Â
up vote
6
down vote
accepted
The methods look fine to me. Reasonable variable names; no confusing control-flow; sensible enough signatures for what they are doing. (see t2chb0t's answer as to why I am wrong)
The tests could be more comprehensive. They should probably check the length of the list, and since the whole data-structure is exposed, you ought verify that the list isn't otherwise malformed (e.g. head.prev
should always be null
, especially worth checking in the special case of removing the head
from the list).
The 'edge case' you have is because you've got a quick-and-nasty definition of a linked list as just 'the head node' (or null
). The effect is that you are exposing a highly mutable data-structure which is easy to misuse. Much much better, would be to hide the Node
s away under a LinkedList
type, which provides a simple interface (e.g. Add(T)
, Remove(T)
, GetEnumerator()
) without exposing any implementation details.
public class LinkedList
private Node Head; // keep track of the head
public LinkedList()
// start empty...
Head = null;
Remove(int value)
RemoveRefElement(ref Head, value);
// some more public methods and helper methods...
Having such an interface solves your 'edge case' interface problem, because the edge case is now an implementation detail, and instead you have a nice interface. I'd argue that your Ref
version is better, because it is modifying the data-structure passed to it, which the return
version doesn't make entirely clear. Having a LinkedList
class with a nice Remove
member that returns nothing serves the same purpose, and allows you to pass the LinkedList
around (you can't pass the Head
node around as a mutable list, because if it is removed from the list, then everyone except the caller suddenly has a list with exactly one element in it). Having a well-defined interface also makes writing tests easier, because you don't have to think about whether the data-structure is 'correct' or not, just whether it does the job.
As an implementation detail, I'd maintain that the Ref
version would be better, but once something is private it matters less what it looks like.
Petty stuff:
Inline documentation (
///
) is always appreciatedThe
break
is redundant inRemoveElement
, and I'd personally make thebreak
inRemoveRefElement
areturn
(just makes it clearer that the method has ended)Personally I'd appreciate more empty lines. The back-to-back
if
s, for example, would be easier for me to scan if they were separated, since they are separate pieces of logic.A generic implementation would always be nice, and gives you a chance to demonstrate awareness of how to do comparisons effectively.
@thanks for the answer
â Gilad
Aug 8 at 11:35
add a comment |Â
up vote
6
down vote
accepted
up vote
6
down vote
accepted
The methods look fine to me. Reasonable variable names; no confusing control-flow; sensible enough signatures for what they are doing. (see t2chb0t's answer as to why I am wrong)
The tests could be more comprehensive. They should probably check the length of the list, and since the whole data-structure is exposed, you ought verify that the list isn't otherwise malformed (e.g. head.prev
should always be null
, especially worth checking in the special case of removing the head
from the list).
The 'edge case' you have is because you've got a quick-and-nasty definition of a linked list as just 'the head node' (or null
). The effect is that you are exposing a highly mutable data-structure which is easy to misuse. Much much better, would be to hide the Node
s away under a LinkedList
type, which provides a simple interface (e.g. Add(T)
, Remove(T)
, GetEnumerator()
) without exposing any implementation details.
public class LinkedList
private Node Head; // keep track of the head
public LinkedList()
// start empty...
Head = null;
Remove(int value)
RemoveRefElement(ref Head, value);
// some more public methods and helper methods...
Having such an interface solves your 'edge case' interface problem, because the edge case is now an implementation detail, and instead you have a nice interface. I'd argue that your Ref
version is better, because it is modifying the data-structure passed to it, which the return
version doesn't make entirely clear. Having a LinkedList
class with a nice Remove
member that returns nothing serves the same purpose, and allows you to pass the LinkedList
around (you can't pass the Head
node around as a mutable list, because if it is removed from the list, then everyone except the caller suddenly has a list with exactly one element in it). Having a well-defined interface also makes writing tests easier, because you don't have to think about whether the data-structure is 'correct' or not, just whether it does the job.
As an implementation detail, I'd maintain that the Ref
version would be better, but once something is private it matters less what it looks like.
Petty stuff:
Inline documentation (
///
) is always appreciatedThe
break
is redundant inRemoveElement
, and I'd personally make thebreak
inRemoveRefElement
areturn
(just makes it clearer that the method has ended)Personally I'd appreciate more empty lines. The back-to-back
if
s, for example, would be easier for me to scan if they were separated, since they are separate pieces of logic.A generic implementation would always be nice, and gives you a chance to demonstrate awareness of how to do comparisons effectively.
The methods look fine to me. Reasonable variable names; no confusing control-flow; sensible enough signatures for what they are doing. (see t2chb0t's answer as to why I am wrong)
The tests could be more comprehensive. They should probably check the length of the list, and since the whole data-structure is exposed, you ought verify that the list isn't otherwise malformed (e.g. head.prev
should always be null
, especially worth checking in the special case of removing the head
from the list).
The 'edge case' you have is because you've got a quick-and-nasty definition of a linked list as just 'the head node' (or null
). The effect is that you are exposing a highly mutable data-structure which is easy to misuse. Much much better, would be to hide the Node
s away under a LinkedList
type, which provides a simple interface (e.g. Add(T)
, Remove(T)
, GetEnumerator()
) without exposing any implementation details.
public class LinkedList
private Node Head; // keep track of the head
public LinkedList()
// start empty...
Head = null;
Remove(int value)
RemoveRefElement(ref Head, value);
// some more public methods and helper methods...
Having such an interface solves your 'edge case' interface problem, because the edge case is now an implementation detail, and instead you have a nice interface. I'd argue that your Ref
version is better, because it is modifying the data-structure passed to it, which the return
version doesn't make entirely clear. Having a LinkedList
class with a nice Remove
member that returns nothing serves the same purpose, and allows you to pass the LinkedList
around (you can't pass the Head
node around as a mutable list, because if it is removed from the list, then everyone except the caller suddenly has a list with exactly one element in it). Having a well-defined interface also makes writing tests easier, because you don't have to think about whether the data-structure is 'correct' or not, just whether it does the job.
As an implementation detail, I'd maintain that the Ref
version would be better, but once something is private it matters less what it looks like.
Petty stuff:
Inline documentation (
///
) is always appreciatedThe
break
is redundant inRemoveElement
, and I'd personally make thebreak
inRemoveRefElement
areturn
(just makes it clearer that the method has ended)Personally I'd appreciate more empty lines. The back-to-back
if
s, for example, would be easier for me to scan if they were separated, since they are separate pieces of logic.A generic implementation would always be nice, and gives you a chance to demonstrate awareness of how to do comparisons effectively.
edited Aug 8 at 13:26
![](https://i.stack.imgur.com/xqpeq.jpg?s=32&g=1)
![](https://i.stack.imgur.com/xqpeq.jpg?s=32&g=1)
The6P4C
1031
1031
answered Aug 8 at 8:57
![](https://i.stack.imgur.com/w9Qba.png?s=32&g=1)
![](https://i.stack.imgur.com/w9Qba.png?s=32&g=1)
VisualMelon
2,589716
2,589716
@thanks for the answer
â Gilad
Aug 8 at 11:35
add a comment |Â
@thanks for the answer
â Gilad
Aug 8 at 11:35
@thanks for the answer
â Gilad
Aug 8 at 11:35
@thanks for the answer
â Gilad
Aug 8 at 11:35
add a comment |Â
up vote
6
down vote
Since this is an interview-question here's how I see it.
I'd accept your code for a position of a junior-developer without much criticism but I would reject it for anything higher than that.
If you were applying for a senior-developer position then I'm of a quite different opinion than @VisualMelon. The methods don't make a good impression on me because they do too much. Your task is to remove an item but what you are doing is not only that. You are also searching for it. The searching part should be moved to its own method. I also find the variable names should not be abbreviated and instead you should use full words like current
and previous
. I agree with other suggestions by @VisualMelon.
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members ofNode
are shortened... these most definitely should not be!)
â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
add a comment |Â
up vote
6
down vote
Since this is an interview-question here's how I see it.
I'd accept your code for a position of a junior-developer without much criticism but I would reject it for anything higher than that.
If you were applying for a senior-developer position then I'm of a quite different opinion than @VisualMelon. The methods don't make a good impression on me because they do too much. Your task is to remove an item but what you are doing is not only that. You are also searching for it. The searching part should be moved to its own method. I also find the variable names should not be abbreviated and instead you should use full words like current
and previous
. I agree with other suggestions by @VisualMelon.
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members ofNode
are shortened... these most definitely should not be!)
â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
add a comment |Â
up vote
6
down vote
up vote
6
down vote
Since this is an interview-question here's how I see it.
I'd accept your code for a position of a junior-developer without much criticism but I would reject it for anything higher than that.
If you were applying for a senior-developer position then I'm of a quite different opinion than @VisualMelon. The methods don't make a good impression on me because they do too much. Your task is to remove an item but what you are doing is not only that. You are also searching for it. The searching part should be moved to its own method. I also find the variable names should not be abbreviated and instead you should use full words like current
and previous
. I agree with other suggestions by @VisualMelon.
Since this is an interview-question here's how I see it.
I'd accept your code for a position of a junior-developer without much criticism but I would reject it for anything higher than that.
If you were applying for a senior-developer position then I'm of a quite different opinion than @VisualMelon. The methods don't make a good impression on me because they do too much. Your task is to remove an item but what you are doing is not only that. You are also searching for it. The searching part should be moved to its own method. I also find the variable names should not be abbreviated and instead you should use full words like current
and previous
. I agree with other suggestions by @VisualMelon.
answered Aug 8 at 9:22
![](https://i.stack.imgur.com/xKXSM.png?s=32&g=1)
![](https://i.stack.imgur.com/xKXSM.png?s=32&g=1)
t3chb0t
32.3k64298
32.3k64298
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members ofNode
are shortened... these most definitely should not be!)
â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
add a comment |Â
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members ofNode
are shortened... these most definitely should not be!)
â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members of
Node
are shortened... these most definitely should not be!)â VisualMelon
Aug 8 at 9:24
I must lend my support for this answer... I do rather focus on the public interface, and honestly I hadn't even noticed the variables were shortened... (arguably the bigger problem is that the members of
Node
are shortened... these most definitely should not be!)â VisualMelon
Aug 8 at 9:24
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@t3chb0t I had about 15 minutes to write the code, you seem like a harsh judge of code, since my goal is to learn, Can you please explain except the Generic Node what else would you expect from a senior developer to do in 15 minutes?
â Gilad
Aug 8 at 18:09
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
@Gilad from a senior-developer I wouldn't expect a working solution at all because I assume he can already write code. What I want to see is design/architecture - even pseudocode but clean, (maybe) modular, extendable (where appropriate), testable, resuable, with a clean API. In 15 minutes you cannot do anything but present a rough draft. Next time you have to share more information about your interview.
â t3chb0t
Aug 8 at 18:19
add a comment |Â
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
var $window = $(window),
onScroll = function(e)
var $elem = $('.new-login-left'),
docViewTop = $window.scrollTop(),
docViewBottom = docViewTop + $window.height(),
elemTop = $elem.offset().top,
elemBottom = elemTop + $elem.height();
if ((docViewTop elemBottom))
StackExchange.using('gps', function() StackExchange.gps.track('embedded_signup_form.view', location: 'question_page' ); );
$window.unbind('scroll', onScroll);
;
$window.on('scroll', onScroll);
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
StackExchange.ready(
function ()
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f201181%2fremove-the-first-value-for-a-doubly-linked-list%23new-answer', 'question_page');
);
Post as a guest
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
var $window = $(window),
onScroll = function(e)
var $elem = $('.new-login-left'),
docViewTop = $window.scrollTop(),
docViewBottom = docViewTop + $window.height(),
elemTop = $elem.offset().top,
elemBottom = elemTop + $elem.height();
if ((docViewTop elemBottom))
StackExchange.using('gps', function() StackExchange.gps.track('embedded_signup_form.view', location: 'question_page' ); );
$window.unbind('scroll', onScroll);
;
$window.on('scroll', onScroll);
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
var $window = $(window),
onScroll = function(e)
var $elem = $('.new-login-left'),
docViewTop = $window.scrollTop(),
docViewBottom = docViewTop + $window.height(),
elemTop = $elem.offset().top,
elemBottom = elemTop + $elem.height();
if ((docViewTop elemBottom))
StackExchange.using('gps', function() StackExchange.gps.track('embedded_signup_form.view', location: 'question_page' ); );
$window.unbind('scroll', onScroll);
;
$window.on('scroll', onScroll);
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Sign up or log in
StackExchange.ready(function ()
StackExchange.helpers.onClickDraftSave('#login-link');
var $window = $(window),
onScroll = function(e)
var $elem = $('.new-login-left'),
docViewTop = $window.scrollTop(),
docViewBottom = docViewTop + $window.height(),
elemTop = $elem.offset().top,
elemBottom = elemTop + $elem.height();
if ((docViewTop elemBottom))
StackExchange.using('gps', function() StackExchange.gps.track('embedded_signup_form.view', location: 'question_page' ); );
$window.unbind('scroll', onScroll);
;
$window.on('scroll', onScroll);
);
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password