алгоритм — Как удалить элемент рядом с самым высоким найденным элементом в круговом списке в переполнении стека

У меня проблема с какой-то функцией / алгоритмом, и я надеюсь, что вы, ребята, сможете мне помочь. Задача состоит в том, чтобы написать функцию, которая удалит элемент, который находится сразу после самого высокого элемента (наибольшее значение) в одном связанном круговом списке. Я пытался нарисовать это так, чтобы это имело больше смысла для меня, но это все еще выглядит как темное искусство, но мне удалось придумать такую ​​функцию:

struct node
{
node * next;
double data;
};

void Insert_node(node * & head, double v)
{
node * p = new node;

p->data = v;
if(head)
{
p->next = head->next;
head->next = p;
}
else p->next = p;
head = p;
}void Delete_After_Max(node* & head)
{
node * tmp=head;
int counter=0,index=0;
double maximum=0;

if(tmp) // checking if the list is not empty
{
do
{
if(tmp->data>maximum)
{
maximum=tmp->data;
index=counter+1;
}
counter++;
tmp=tmp->next;
} while(tmp!=head);
}

cout<<"Biggest value on the list: "<<maximum<<endl;
cout<<"licznik:"<<counter<<"  "<<"indeks: "<<index<<endl;

if(counter==(index+1))
index=0;    //if last element is the maximum, first one will be deleted
else
index++; // incrementing to get index of the next element after maximum

node *tmp2=NULL;
//checking if the highest element was last(then we delete first one)
if(index==0)
{
index=counter;
}
// checking if the highest element was somewhere else

node *tmp3=NULL;

int position=0;

if((index>0)&& (index<=counter))
{
tmp2=head;

while(position<index-1)
{
tmp2=tmp2->next;
position++;
}

tmp3=tmp2->next;
tmp2->next=tmp3->next;

if(head==tmp3)
{
head=head->next;
}
delete tmp3;

}
}

Считаете ли вы этот алгоритм правильным? Я не уверен, правильно ли я понял идею, поэтому код, вероятно, совершенно неверен: /

Сначала я считаю все элементы в списке, нахожу самый высокий и его индекс, а затем я могу использовать его для удаления элемента после этого, увеличивая индекс, верно? Я думаю, что с этим моментом все в порядке, но после этого мне становится все труднее, если максимум был последним элементом, я должен удалить первый и «связать» последний со вторым? Но я не знаю, нормально ли это с круговым списком, поэтому, пожалуйста, кто-нибудь может подсказать мне, что я делаю неправильно? 😉

Я проверил это снова, и он компилируется, но он не работает должным образом, и я до сих пор не знаю, почему и как это сделать. Я не мог найти подобных проблем, на которых мог бы основываться, любая помощь была бы признательна, я новичок в этом, поэтому так много ошибок …

-1

Решение

В предлагаемом алгоритме небольшие ошибки дают неверный результат.

Ошибка 1 — самый большой, в последнем цикле tmp2 не инициализируется.

инициализировать tmp2 = head вместо tmp3 = head;,

tmp2 = head; // initialize tmp2
while (position<index - 1)
{
tmp2 = tmp2->next;
position++;
}
tmp3 = tmp2->next;

Ошибка 2 — начиная с position равный 1 остановит цикл слишком рано.

Используя сначала position = 1 с условием while (position < index
- 1)
уменьшить цикл на 2 шага.

int position = 0;

Ошибка печати — в if (index == 0) состояние, пропущенная полуколонна.

Код строки head = head->next не заканчивается ;,

В состоянии if (index == 0) либо выход из функции с return или предотвратить выполнение неожиданной операции, вставив последнюю часть в else { ... } состояние.

if (index == 0)
{
tmp2 = head;
head = head->next;
delete tmp2;
// EXIT by return
}

ДОБАВЛЕНО № 1 >>>>

Ошибка 3 — случай if (index == 0) это невозможно

Попробуйте удалить первый узел кругового связного списка, когда
Максимальное размещение в последнем узле невозможно.

  • Значение index = 0; возможно только тогда, когда if (counter == index), Но в do-while, просто после сохранения позиции максимума в index = counter; counter увеличивается counter++;,

Изменить следующим образом:

if (counter == (index+1)) // detecting the last position
index = 0;    //if last element is the maximum, first one will be deleted
else
index++; // incrementing to get index of the next element after maximum
  • Но чтобы удалить первый узел, предложенный алгоритм для if (index == 0) не работает, потому что необходимо сохранить предыдущий узел.

Решение — Лучшее решение — заставить последний цикл while продолжить еще один шаг, выполнив следующие изменения:

if (index == 0)
{
index = counter;
}

Затем разрешите цикл while, когда (index == counter) с:

if ((index>0) && (index<=counter)) // allow for the last
{
tmp2 = head;
while (position<index - 1)

И до удаления tmp3 изменить узел head когда tmp3 == head:

    tmp3 = tmp2->next;
tmp2->next = tmp3->next;
if (head==tmp3) { // when the node to delete is the head
head = head->next; // shift head to the next node
}
delete tmp3;

ДОБАВЛЕНО N ° 2 >>>>

Выход — Вот результат, полученный при использовании предложенного списка значений.

Первый элемент 6 удаляется (следующий элемент последнего элемента
18 в круговом связанном списке).

[ 6, 9, 13, 12, 1, 10, 15, 4, 6, 18, ].
Biggest value on the list: 18
[ 9, 13, 12, 1, 10, 15, 4, 6, 18, ].

ДОБАВЛЕНО № 3 >>>>

Вот полный исходный код функции Delete_After_Max():

void Delete_After_Max(node* & head)
{
node * tmp = head;
int counter = 0, index = 0;
double maximum = -1;

if (tmp) // checking if the list is not empty
{
do
{
if (tmp->data>maximum)
{
maximum = tmp->data;
index = counter;
}
counter++;
tmp = tmp->next;
} while (tmp != head);
}

std::cout << "Biggest value on the list: " << maximum << "\n";
if (counter == (index+1))
index = 0;    //if last element is the maximum, first one will be deleted
else
index++; // incrementing to get index of the next element after maximum

node *tmp2 = NULL;
//checking if the highest element was last(then we delete first one)
if (index == 0)
{
tmp2 = head;
std::cout << tmp2->data << ", ";
index = counter;
//head = head->next;
//delete tmp2;
// EXIT
}
// checking if the highest element was somewhere else

node *tmp3 = NULL;

int position = 0; // ERROR 1;

// if ((index>0) && (index<counter))
if ((index>0) && (index<=counter))
{
// ERROR tmp3 = head;
tmp2 = head;
while (position<index - 1)
{
tmp2 = tmp2->next;
position++;
}
tmp3 = tmp2->next;
tmp2->next = tmp3->next;
if (head==tmp3) {
head = head->next;
}
delete tmp3;
}
}

ДОБАВЛЕНО N ° 4 >>>>

В обновленной функции Delete_After_Max() ниже показано логическое удаление узла, следующее за максимумом неверно.

bool Delete_After_Max(node* & head)
{
node *maxi=Find_Maximum(head);
std::cout << "Biggest value on the list: " << maxi->data << "\n";

if(!Is_Empty) // !Is_Empty because this function is not working properly so i had to negate it until i find out why ;)
{
cout<<"the list is empty";
return false;
}
else
{
node *tmp3=NULL;
node *tmp2=maxi->next;
tmp3=tmp2->next;
tmp2->next=tmp3->next;
if (head==tmp3) {
head = head->next;
}
delete tmp3;

cout<<"one element deleted";

return true;
}
}
  1. Если maxi указывает на узел, имеющий максимальное значение, удаляемый узел maxi->next (вместо звонка tmp2 мы назовем это node_to_delete).
  2. Перед удалением node_to_deleteнеобходимо подключить узел maxi с узлом, следующим за node_to_delete (вместо звонка tmp3 мы назовем это node_after_delete).
  3. В случае node_to_delete это headнеобходимо обновить head со следующим узлом перед удалением.

Затем новая часть удаления функции становится:

// Step 1
node *node_to_delete = maxi->next;
// Step 2
node *node_after_delete = node_to_delete->next;
maxi->next = node_after_delete;
// Step 3
if (node_to_delete == head) {
head = head->next;
}
delete node_to_delete;

Итак, логические ошибки в функции Delete_After_Max() являются:

  1. Плохая связь между узлом maxi и узел node_after_delete (tmp3) ==> maxi->next=tmp3; вместо tmp2->next=tmp3->next;,
  2. Плохое определение узла node_to_delete (tmp2) ==> if (head==tmp2) а также delete tmp2; вместо if (head==tmp3) а также delete tmp3;
0

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector