I'm trying to remove a Node from LinkedList by it's value however it doesn't seem to work.
LinkedList class (with node):
public class Node<T>
{
private T info;
private Node<T> next;
public Node(T x, Node<T> next)
{
this.info = x;
this.next = next;
}
public Node<T> GetNext()
{
return this.next;
}
public void SetNext(Node<T> next)
{
this.next = next;
}
public T GetInfo()
{
return this.info;
}
public void SetInfo(T x)
{
this.info = x;
}
public override string ToString()
{
return this.info.ToString();
}
}
public class List<T>
{
private Node<T> first;
public List()
{
this.first = null;
}
public Node<T> GetFirst()
{
return this.first;
}
public Node<T> Add(Node<T> pos, T x)
{
Node<T> temp = new Node<T>(x, null);
if (pos == null)
{
temp.SetNext(this.first);
this.first = temp;
}
else
{
temp.SetNext(pos.GetNext());
pos.SetNext(temp);
}
return temp;
}
public Node<T> Remove(Node<T> pos)
{
if (this.first == pos)
this.first = pos.GetNext();
else
{
Node<T> prevPos = this.GetFirst();
while (prevPos.GetNext() != pos)
prevPos = prevPos.GetNext();
prevPos.SetNext(pos.GetNext());
}
Node<T> nextPos = pos.GetNext();
pos.SetNext(null);
return nextPos;
}
public override string ToString()
{
string str = "[";
Node<T> pos = this.first;
while (pos != null)
{
str += pos.GetInfo().ToString();
if (pos.GetNext() != null)
str += ", ";
pos = pos.GetNext();
}
str += "]";
return str;
}
}
That's the function:
public void Del(string info)
{
Node<T> previousNode = null, obsoleteNode = null, nextNode = null;
Node<T> pos = this.first;
while (pos != null)
{
if (pos == this.first && this.first.GetInfo().ToString() == info)
{
Node<T> temp = pos;
this.first = this.first.GetNext();
temp = null;
}
else
{
previousNode = pos;
if (previousNode != null)
obsoleteNode = previousNode.GetNext();
if (nextNode == null)
nextNode = pos.GetNext().GetNext();
if (obsoleteNode != null)
{
if (obsoleteNode.GetInfo().ToString() == info)
previousNode.SetNext(nextNode);
}
}
pos = pos.GetNext();
}
}
In VS autos it shows that obsoleteNode is actually null but i can't understand why.
All other values are okay, except pos, it gets somehow the last node in the list instead of first but the this.first himself is okay.
What can be the problem?
Related
I have the next class:
using System.Drawing;
using System.Windows.Forms;
namespace course_project
{
internal class Pike<T> : Fish
{
Brush brush = new SolidBrush(Color.Green);
public PictureBox aquarium = new AquariumForm().aquarium_picturebox;
public Pike(T data) {
Data = data;
Draw((int[])(object)data);
}
public T Data { get; set; }
public Pike<T> Next { get; set; }
protected override void Draw(int[] coordinates)
{
Graphics graphics = Graphics.FromImage(aquarium.Image);
graphics.FillEllipse(brush, coordinates[0], coordinates[1], 40, 40);
aquarium.Refresh();
}
}
}
Linked List:
using System.Collections;
using System.Collections.Generic;
namespace course_project
{
internal class PikeFlock<T> : IEnumerable<T>
{
Pike<T> head;
Pike<T> tail;
int count;
public void Add(T data)
{
Pike<T> pike = new Pike<T>(data);
if (head == null)
head = pike;
else
tail.Next = pike;
tail = pike;
count++;
}
public bool Remove(T data)
{
Pike<T> current = head;
Pike<T> previous = null;
while (current != null)
{
if (current.Data.Equals(data))
{
if (previous != null)
{
previous.Next = current.Next;
if (current.Next == null)
{
tail = previous;
}
}
else
{
head = head.Next;
if (head == null)
tail = null;
}
count--;
return true;
}
previous = current;
current = current.Next;
}
return false;
}
public int Count { get { return count; } }
public bool isEmpty { get { return count == 0; } }
public void Clear()
{
head = null;
tail = null;
count = 0;
}
public bool Contains(T data)
{
Pike<T> current = head;
while (current != null)
{
if (current.Data.Equals(data))
return true;
current = current.Next;
}
return false;
}
public void AppendFirst(T data)
{
Pike<T> pike = new Pike<T>(data);
pike.Next = head;
head = pike;
if (count == 0)
{
tail = head;
}
count++;
}
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable)this).GetEnumerator();
}
IEnumerator<T> IEnumerable<T>.GetEnumerator()
{
Pike<T> current = head;
while (current != null)
{
yield return current.Data;
current = current.Next;
}
}
}
}
Button click event:
private void add_pike_button_Click(object sender, EventArgs e)
{
PikeFlock<int[]> pikeFlock = new PikeFlock<int[]>();
int[] coords = { 1, 2 };
pikeFlock.Add(coords);
}
Form1_Load:
private void Form1_Load(object sender, EventArgs e)
{
Bitmap bitmap = new Bitmap(aquarium_picturebox.Width, aquarium_picturebox.Height);
Graphics graphics = Graphics.FromImage(bitmap);
graphics.Clear(Color.Blue);
aquarium_picturebox.Image = bitmap;
aquarium_picturebox.Refresh();
}
But when you click the button an ArgumentNullException (System.ArgumentNullException: "The value cannot be undefined.
Parameter name: image".) is thrown because the Image property of the PictureBox element is empty for some reason.
How can it be solved? Please don't throw tomatoes, I just started to learn C# :)
I am writing a term paper and am having trouble checking it. The point of this work is to create a circular two-way array of Client class objects. I sent it to the manager, and he said that some aspects of the program are not correct. He said:
Why does the Сlient class use an array of references private Operation[] operations; instead of an array of objects of the Operation class?
Why is the Bank class using an address list private DoublyLinkedList<Client> arrayClient; instead of an array-queue?
// Operation class
using System;
namespace DepositLibrary
{
// Класс операции
public class Operation
{
// Дата операции
public DateTime date;
// Депозит операции
public decimal deposit;
public Operation(DateTime dateIn, decimal depositIn)
{
date = dateIn;
deposit = depositIn;
}
// Получение даты операции
public DateTime GetDateTime { get => date; }
// Получение депозита операции
public decimal GetDeposit { get => deposit; }
}
}
// Client class
using System;
using System.Collections.Generic;
namespace DepositLibrary
{
//Класс клиент
public class Client
{
//Фамилия клиента
public string surname;
//Текущий депозит лицевого счета
public decimal currentDeposit;
// Совершенные операции клиента
private Operation[] operations;
public Client(string surnameIn)
{
surname = surnameIn;
operations = new Operation[0];
}
//Получить фамилию
public string GetSurname { get => surname; }
//Получить все совершенные операции
public Operation[] Operations { get => operations; }
//Получить текущий депозит лицевого счета
public decimal GetDeposit { get => currentDeposit; }
}
}
// Bank class
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
namespace DepositLibrary
{
// Класс банк
public class Bank
{
// Наименование банка
private string nameBank;
// Клиентские банковские книги
private DoublyLinkedList<Client> arrayClient;
public Bank(string _nameBank)
{
nameBank = _nameBank;
arrayClient = new DoublyLinkedList<Client>();
}
//Получить наименование банка
public string GetBankName { get => nameBank; }
//Получить клиентские банковские книги
public DoublyLinkedList<Client> GetListClients { get => arrayClient; }
}
public class DoublyNode<T>
{
public DoublyNode(T data)
{
Data = data;
}
public T Data { get; set; }
public DoublyNode<T> Previous { get; set; }
public DoublyNode<T> Next { get; set; }
}
public class DoublyLinkedList<T> : IEnumerable<T> // двусвязный список
{
public DoublyNode<T> head; // головной/первый элемент
public DoublyNode<T> tail; // последний/хвостовой элемент
int count; // количество элементов в списке
// добавление элемента
public void Add(T data)
{
DoublyNode<T> node = new DoublyNode<T>(data);
if (head == null)
head = node;
else
{
tail.Next = node;
node.Previous = tail;
// for looped array
node.Next = head;
head.Previous = node;
}
tail = node;
count++;
}
public void AddFirst(T data)
{
DoublyNode<T> node = new DoublyNode<T>(data);
DoublyNode<T> temp = head;
node.Next = temp;
head = node;
if (count == 0)
tail = head;
else
{
temp.Previous = node;
// for looped
tail.Next = node;
node.Previous = tail;
}
count++;
}
// удаление
public bool Remove(T data)
{
DoublyNode<T> current = head;
// поиск удаляемого узла
do
{
if (current.Data.Equals(data))
{
break;
}
current = current.Next;
} while (!current.Data.Equals(head.Data));
if (current != null)
{
// если узел не последний
if (!current.Next.Data.Equals(head.Data))
{
current.Next.Previous = current.Previous;
}
else
{
// если последний, переустанавливаем tail
tail = current.Previous;
// for looped
tail.Next = head;
}
// если узел не первый
if (!current.Previous.Data.Equals(tail.Data))
{
current.Previous.Next = current.Next;
}
else
{
// если первый, переустанавливаем head
head = current.Next;
// for looped
head.Previous = tail;
}
count--;
return true;
}
return false;
}
public int Count { get { return count; } }
public bool IsEmpty { get { return count == 0; } }
public void Clear()
{
head = null;
tail = null;
count = 0;
}
public bool Contains(T data)
{
DoublyNode<T> current = head;
do
{
if (current.Data.Equals(data))
return true;
current = current.Next;
} while (!current.Data.Equals(head.Data));
return false;
}
IEnumerator GetEnumerator()
{
return ((IEnumerable)this).GetEnumerator();
}
IEnumerator<T> IEnumerable<T>.GetEnumerator()
{
DoublyNode<T> current = head;
do
{
yield return current.Data;
current = current.Next;
} while (!current.Data.Equals(head.Data));
}
public IEnumerable<T> BackEnumerator()
{
DoublyNode<T> current = tail;
do
{
yield return current.Data;
current = current.Previous;
} while (!current.Data.Equals(tail.Data));
}
IEnumerator IEnumerable.GetEnumerator()
{
throw new NotImplementedException();
}
}
}
I tried for a very long time to understand what he wants from me, but didn't come to a normal result. I would be grateful for any help and advice. Thank you!
Hi guys help me please.
I wrote the code for a binary search tree, but for some reason I'm wildly stupid in post-traverse and searching. Can someone help with writing a postorder and search.
Thank you and sorry for bad english. Thank you very much again.
I don't show you my Remove and Contains method because it does not important. If you want to see them , i can show it.
My BinaryTreeNode class
public class BinaryTreeNode<T> : IComparable<T>
where T : IComparable
{
public BinaryTreeNode(T value)
{
Value = value;
}
public BinaryTreeNode<T> Left { get; set; }
public BinaryTreeNode<T> Right { get; set; }
public T Value { get; }
public int CompareTo(T other)
{
return Value.CompareTo(other);
}
public IEnumerator<T> GetEnumerator()
{
var leftEnumerable = (IEnumerable<T>) Left ?? new T[0];
var rightEnumerable = (IEnumerable<T>) Right ?? new T[0];
return leftEnumerable.Concat(new[] {Value})
.Concat(rightEnumerable)
.GetEnumerator();
}
}
My BinaryTree class :
public class BinaryTree<T>
where T : IComparable
{
private BinaryTreeNode<T> _head;
public int Count { get; private set; }
public void Add(T value)
{
if (_head == null)
_head = new BinaryTreeNode<T>(value);
else
AddTo(_head, value);
Count++;
}
private void AddTo(BinaryTreeNode<T> node, T value)
{
if (value.CompareTo(node.Value) < 0)
{
if (node.Left == null)
node.Left = new BinaryTreeNode<T>(value);
else
AddTo(node.Left, value);
}
else
{
if (node.Right == null)
node.Right = new BinaryTreeNode<T>(value);
else
AddTo(node.Right, value);
}
}
public IEnumerable<T> Preorder(BinaryTreeNode<T> root)
{
var stack = new Stack<BinaryTreeNode<T>>();
stack.Push(root);
while (stack.Count > 0)
{
var node = stack.Pop();
yield return node.Value;
if (node.Right != null)
stack.Push(node.Right);
if (node.Left != null)
stack.Push(node.Left);
}
}
public IEnumerable<T> InOrder(BinaryTreeNode<T> root)
{
var stack = new Stack<BinaryTreeNode<T>>();
while (root != null)
{
while (root.Left != null)
{
stack.Push(root);
root = root.Left;
}
yield return root.Value;
while (root.Right == null && stack.Count > 0)
{
root = stack.Pop();
yield return root.Value;
}
root = root.Right;
}
}
public IEnumerator<T> GetEnumerator()
{
return _head.GetEnumerator();
}
public void Clear()
{
_head = null;
Count = 0;
}
}
I have a custom queue class that is implemented via linked list, but I can't figure out how ot implement IEnumerable for something that is not array.
It's easy to implement it using Dequeue(), but I don't want enumeration to mutate my collection.
Here is my code for DQueue class:
class DQueue<Item> : IEnumerable<Item>
{
private Node<Item> startNode;
private Node<Item> lastNode;
private int _size;
public DQueue()
{
_size = 0;
}
public void Enqueue(Item item)
{
_size++;
if (startNode == null) {
startNode = new Node<Item>();
startNode.data = item;
lastNode = startNode;
} else {
Node<Item> temp = new Node<Item>();
temp.data = item;
lastNode.next = temp;
lastNode = temp;
}
}
public Item Dequeue()
{
Item temp = startNode.data;
startNode = startNode.next;
_size--;
return temp;
}
public bool IsEmpty()
{
return startNode == null;
}
public int Size()
{
return _size;
}
private class Node<InnerItem>
{
public InnerItem data;
public Node<InnerItem> next;
public Node()
{
next = null;
}
}
// IEnumerable
public IEnumerator<Item> GetEnumerator()
{
Node<Item> current;
for (int i = 0; i < _size; i++) {
//yield return values[i];
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
Suggest next solve, iteration from start node:
public IEnumerator<Item> GetEnumerator()
{
for (Node<Item> item = startNode; item != null; item = item.next)
{
yield return item.data;
}
}
I need the albums that appear in the listbox, to have a search function that passes through the AVL Tree or Binary Search Tree.
This is my code for the AVLTree class
class AVLTree<T> : BSTree<T> where T : IComparable
{
public new void InsertItem(T item)
{
insertItem(item, ref root);
}
private void insertItem(T item, ref Node<T> tree)
{
if (tree == null)
tree = new Node<T>(item);
else if (item.CompareTo(tree.Data) < 0)
insertItem(item, ref tree.Left);
else if (item.CompareTo(tree.Data) > 0)
insertItem (item, ref tree.Right);
tree.balanceFactor = Height(tree.Left)-Height(tree.Right);
if (tree.balanceFactor <= -2)
rotateLeft(ref tree);
if (tree.balanceFactor >= 2)
rotateRight(ref tree);
}
private void rotateLeft(ref Node<T> tree)
{
if (tree.Right.balanceFactor > 0)
rotateRight(ref tree.Right);
Node<T> pivot = tree.Right;
tree.Right = pivot.Left;
pivot.Left = tree;
tree = pivot;
}
private void rotateRight(ref Node<T> tree)
{
if (tree.Left.balanceFactor > 0)
rotateLeft(ref tree.Left);
Node<T> pivot = tree.Left;
tree.Left = pivot.Right;
pivot.Right = tree;
tree = pivot;
}
}
}
FormClass:
//search button
private void Search_Click(object sender, EventArgs e) //BASIC SEARCH NOT SUITABLE YET
{
listBox1.ClearSelected();
int index = listBox1.FindString(SearchText.Text);
if (index <0)
{
MessageBox.Show("Item not found.");
SearchText.Text = String.Empty;
}
else
{
listBox1.SelectedIndex = index;
}
.
//ARTIST CLASS
{
class Artist : IComparable
{
public String name; //changed to public
public String member;
public LinkedList<String> Album;
public Artist(String artistname, String members, String[] albName)
{
name = artistname;
member = members;
Album = new LinkedList<String>(albName);
}
public LinkedList<String> getAlbum()
{
return Album;
}
public int CompareTo(object obj)
{
if (obj is Artist) //Artist name comparison
{
Artist other = (Artist)obj;
return name.CompareTo(other.name);
}
if (obj is string) //Album comparison
{
Artist other = (Artist)obj;
return name.CompareTo(other.Album);
}
else
return -999; //Comparison can not be made
}
}
}
//ALBUM CLASS
class Album
{
private String title;
private String daterel;
public Album(String aTitle, String saleDate)
{
daterel = saleDate;
title = aTitle;
}
}
}
Provided this is Winforms, you could add the items in listbox1 to an array, then iterate through them calling your search function on each.