Форум программистов, компьютерный форум, киберфорум
C# для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 5.00/8: Рейтинг темы: голосов - 8, средняя оценка - 5.00
 Аватар для Pincd
0 / 0 / 0
Регистрация: 12.10.2020
Сообщений: 30

Метод, удаляющий последний добавленный элемент в списке

13.12.2020, 00:50. Показов 1749. Ответов 6

Студворк — интернет-сервис помощи студентам
Приветствую! Мне дана задача:

"Дана последовательность латинских букв, оканчивающаяся точкой.
Среди букв есть специальный символ, появление которого означает
отмену предыдущей буквы; n знаков подряд отменяют n
предыдущих букв, если такие есть. Учитывая вхождение этого
символа преобразовать последовательность. Использовать двусвязный список"

Решить задачу необходимо без использования стандартных библиотек

Мой код:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using ListCsharp2;
 
namespace ListCsharp2
{
    //-----------------------РЕАЛИЗАЦИЯ ПРОСТОГО АЛГОРИТМА СПИСКА--------------------------------------
 
    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>  // двусвязный список
    {
        DoublyNode<T> head; // головной/первый элемент
        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;
            }
            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;
            count++;
        }
 
        //удаление последнего элемента
        public bool RemoveLast(T data)
        {
            DoublyNode<T> current = head;
 
      
            if (current != null)
            {
                // если узел последний
                if (current.Next == null)
                {
                    tail = current.Previous; // nj переустанавливаем tail
                }
             
                return true;
            }
            return false;
        }
 
        // удаление
        public bool Remove(T data)
        {
            DoublyNode<T> current = head;
 
            // поиск удаляемого узла
            while (current != null)
            {
                if (current.Data.Equals(data))
                {
                    break;
                }
                current = current.Next;
            }
            if (current != null)
            {
                // если узел не последний
                if (current.Next != null)
                {
                    current.Next.Previous = current.Previous;
                }
                else
                {
                    // если последний, переустанавливаем tail
                    tail = current.Previous;
                }
 
                // если узел не первый
                if (current.Previous != null)
                {
                    current.Previous.Next = current.Next;
                }
                else
                {
                    // если первый, переустанавливаем head
                    head = current.Next;
                }
                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;
            while (current != null)
            {
                if (current.Data.Equals(data))
                    return true;
                current = current.Next;
            }
            return false;
        }
 
        IEnumerator IEnumerable.GetEnumerator()
        {
            return ((IEnumerable)this).GetEnumerator();
        }
 
        IEnumerator<T> IEnumerable<T>.GetEnumerator()
        {
            DoublyNode<T> current = head;
            while (current != null)
            {
                yield return current.Data;
                current = current.Next;
            }
        }
 
        public IEnumerable<T> BackEnumerator()
        {
            DoublyNode<T> current = tail;
            while (current != null)
            {
                yield return current.Data;
                current = current.Previous;
            }
        }
 
    }
}
 
class Program
{
    static int Main(string[] args)
    {
        DoublyLinkedList<char> letterS = new DoublyLinkedList<char>();
 
        char letter; //переменная для букв
        char spec; //переменная для спец символа
 
        Console.WriteLine("Enter spec symbol"); 
        spec = Convert.ToChar(Console.ReadLine()); //ввод спецсимвола
        Console.WriteLine("Enter any symbol");
 
        do
        {
            letter = Convert.ToChar(Console.ReadLine()); //ввод букв
           
            if (letter==spec) //если введенная буква равна ранее веденному спец символу
            {
 
                letterS.Remove(letter); //удалить введенный спец символ
                letterS.RemoveLast(letter); //удалить последнюю добавленную букву
                
            }
            else
            {
                letterS.Add(letter);
            }
 
           
        }
 
        while (letter != '.');
 
        foreach (char i in letterS)
        {
            Console.WriteLine(i);
        }
        Console.ReadLine();
 
       
    }
}
У меня не работает метод RemoveLast. Программа спокойно удаляет введенный спец символ, но последний добавленный элемент, который был добавлен до введения спец символа программа не удаляет

Подскажите, пожалуйста, в чем ошибка
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
13.12.2020, 00:50
Ответы с готовыми решениями:

Прокрутка ListBox на последний добавленный элемент
В общем, в программе у меня есть большое количество команд LogList.Items.Add(&quot;Выполнено&quot;); И окошло ListBox(LogList) в которое...

Метод, удаляющий элемент, расположенный в списке перед первым вхождением элемента со значением X
Добавить в шаблон класса CList метод, удаляющий элемент, расположенный в списке перед первым вхождением элемента со значением X. Ниже...

Предикат, удаляющий из списка последний элемент
Определить на языке ПРОЛОГ следующие рекурсивные предикаты: c) предикат, удаляющий из списка последний элемент.

6
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
13.12.2020, 13:13
Ваша реализация метода RemoveLast довольно странная.

Зачем этому методу параметр? Он лишний.

Сейчас ваш метод делает следующее: устанавливает в качестве "хвоста" предыдущую ноду от "головы" (у "головы" не может быть ссылки на предыдущую ноду, так как голова является первой в списке).
1
 Аватар для Pincd
0 / 0 / 0
Регистрация: 12.10.2020
Сообщений: 30
13.12.2020, 14:38  [ТС]
samana, можете написать как должен выглядеть метод RemoveLast в коде? Для меня код реализации этого списка сложный, я его брала из интернета, до конца не могу его понять. Поэтому мне не совсем ясно то, что вы мне написали
0
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
13.12.2020, 16:08
Цитата Сообщение от Pincd Посмотреть сообщение
можете написать как должен выглядеть метод RemoveLast в коде?
Наверно как-то так, но надо тестировать
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
public void RemoveLast()
{
    // если список пустой, то нет смысла что-то делать вообще, выходим из метода.
    if (count == 0) return;
 
 
    // если в списке один элемент (он же голова и хвост одновременно), то обнуляем данные полностью
    if (count == 1)
    {
        tail = null;
        head = null;
    }
    // если в списке больше чем 1 элемент, то..
    else
    {
        // новым хвостом становится предпоследний элемент из списка
        tail = tail.Previous;
        tail.Next = null;
    }
 
    count--;
}
1
Модератор
Эксперт .NET
 Аватар для Элд Хасп
16139 / 11263 / 2888
Регистрация: 21.04.2018
Сообщений: 33,108
Записей в блоге: 2
13.12.2020, 16:11
Лучший ответ Сообщение было отмечено Pincd как решение

Решение

Цитата Сообщение от Pincd Посмотреть сообщение
метод RemoveLast в коде?
В том числе ещё другие изменения:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
    //-----------------------РЕАЛИЗАЦИЯ ПРОСТОГО АЛГОРИТМА СПИСКА--------------------------------------
    public partial class DoublyLinkedList<T> // Вложенный приватный класс для узла
    {
        private class DoublyNode
        {
            public DoublyNode(T data)
            {
                Data = data;
            }
            public T Data { get; set; }
            public DoublyNode Previous { get; set; }
            public DoublyNode Next { get; set; }
        }
    }
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
    public partial class DoublyLinkedList<T> : IEnumerable<T>  // двусвязный список
    {
        DoublyNode head; // головной/первый элемент
        DoublyNode tail; // последний/хвостовой элемент
 
        // добавление элемента
        public void Add(T data)
        {
            DoublyNode node = new DoublyNode(data);
 
            if (head == null)
                head = node;
            else
            {
                tail.Next = node;
                node.Previous = tail;
            }
            tail = node;
            Count++;
        }
        public void AddFirst(T data)
        {
            DoublyNode node = new DoublyNode(data);
            node.Next = head;
            if (Count == 0)
                tail = node;
            else
                head.Previous = node;
            head = node;
            Count++;
        }
 
        //удаление последнего элемента
        public bool RemoveLast()
        {
            if (Count == 0)
                return false;
 
            if (head == tail)
            {
                if (Count != 1)
                    throw new Exception("Непредвиденная ошибка. head == tail, но count != 1");
 
                Count = 0;
                head = tail = null;
                return true;
            }
 
            tail = tail.Previous;
            tail.Next.Previous = null;
            tail.Next = null;
            Count--;
            return true;
        }
 
        // удаление
        public bool Remove(T data)
        {
            DoublyNode current = head;
 
            // поиск удаляемого узла
            while (current != null)
            {
                // Чтобы не было исключения при data=null надо использовать object.Equals
                if (object.Equals(current.Data, data))
                {
                    break;
                }
                current = current.Next;
            }
 
            if (current == null)
                return false;
 
            // если узел не последний
            if (current.Next != null)
            {
                current.Next.Previous = current.Previous;
            }
            else
            {
                // если последний, переустанавливаем tail
                tail = current.Previous;
            }
 
            // если узел не первый
            if (current.Previous != null)
            {
                current.Previous.Next = current.Next;
            }
            else
            {
                // если первый, переустанавливаем head
                head = current.Next;
            }
            Count--;
            return true;
        }
 
        public int Count { get; private set; }
        public bool IsEmpty => Count == 0;
 
        public void Clear()
        {
            head = null;
            tail = null;
            Count = 0;
        }
 
        public bool Contains(T data)
        {
            DoublyNode current = head;
            while (current != null)
            {
                // Чтобы не было исключения при data=null надо использовать object.Equals
                if (object.Equals(current.Data, data))
                    return true;
                current = current.Next;
            }
            return false;
        }
 
        IEnumerator IEnumerable.GetEnumerator() => GetEnumerator();
 
        public IEnumerator<T> GetEnumerator()
        {
            DoublyNode current = head;
            while (current != null)
            {
                yield return current.Data;
                current = current.Next;
            }
        }
 
        public IEnumerable<T> GetBackEnumerator()
        {
            DoublyNode current = tail;
            while (current != null)
            {
                yield return current.Data;
                current = current.Previous;
            }
        }
 
    }
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
        static void Main(string[] args)
        {
            DoublyLinkedList<char> letterS = new DoublyLinkedList<char>();
 
            char letter; //переменная для букв
            char spec; //переменная для спец символа
 
            Console.WriteLine("Enter spec symbol");
            spec = Convert.ToChar(Console.ReadLine()); //ввод спецсимвола
            Console.WriteLine("Enter any symbol");
 
            do
            {
                letter = Convert.ToChar(Console.ReadLine()); //ввод букв
 
                if (letter == spec) //если введенная буква равна ранее веденному спец символу
                {
 
                    letterS.Remove(letter); //удалить введенный спец символ
                    letterS.RemoveLast(); //удалить последнюю добавленную букву
 
                }
                else
                {
                    letterS.Add(letter);
                }
 
 
            }
 
            while (letter != '.');
 
            foreach (char i in letterS)
            {
                Console.WriteLine(i);
            }
            Console.ReadLine();
 
 
        }
1
 Аватар для samana
2639 / 1567 / 853
Регистрация: 23.02.2019
Сообщений: 3,876
13.12.2020, 17:48
Цитата Сообщение от Pincd Посмотреть сообщение
Среди букв есть специальный символ, появление которого означает
отмену предыдущей буквы; n знаков подряд отменяют n
предыдущих букв, если такие есть.
Здесь есть некоторые непонятные моменты

- нужно ли оставлять специальные символы в исходном наборе?
например abc//def/ должно стать a//de/ или ade?

- что должно получится, если специальных символов больше, чем букв перед ними?
например abc//d//// ?
1
 Аватар для Pincd
0 / 0 / 0
Регистрация: 12.10.2020
Сообщений: 30
13.12.2020, 18:00  [ТС]
samana,
- нужно ли оставлять специальные символы в исходном наборе?
например abc//def/ должно стать a//de/ или ade?
Сама не знаю! Об этом нигде не говорится. Но я хотела сделать такую логику:
C#
1
letter = Convert.ToChar(Console.ReadLine());
вводятся буквы
C#
1
if (letter==spec)
идет проверка является ли введенный символ спецсимволом
C#
1
letterS.Remove(letter);
если true, то спецсимвол удаляется
C#
1
letterS.RemoveLast(letter);
и удаляется последний добавленный символ до ввода спецсимвола

Я так пыталась реализовать, но у меня кривой метод RemoveLast
- что должно получится, если специальных символов больше, чем букв перед ними?
например abc//d//// ?
В задаче сказано:
"n знаков подряд отменяют n
предыдущих букв, если такие есть"
Тоесть если будет abc//de, то, судя по задаче, должно выходить так: "ade", т.е. два слэша убрали b и c, ну и сами слэши убрались. Но, еще раз, в условии не сказано должны оставаться слэши или нет, это я решила их не оставлять.
А по вашему примеру "abc//d////" получается, что вообще ничего не останется

Спасибо за ваш предыдущий ответ! Буду пытаться внедрить, но, если у вас появилась идея другого кода, то буду рада увидеть!
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
13.12.2020, 18:00
Помогаю со студенческими работами здесь

Предикат, удаляющий последний элемент из списка, если он не равен нулю.
Определите предикат udp, удаляющий последний элемент из списка, если этот элемент не равен нулю, например, истинно udp ( , ).

Как сделать так, чтобы последний добавленный элемент в комбо боксе, появлялся сверху
Как сделать так, чтобы последний добавленный элемент в комбо боксе, появлялся сверху Добавлено через 8 минут как использовать...

Словарь в списке. Последний элемент словаря в списке
Есть следующий список: namelis=( Как можно обратиться к последнему элементу данного списка? Если names то выводит {'name':...

Как удалить последний элемент в списке?
Создал односвязный линейный список.Как написать функцию для удаления последнего элемента? typedef struct node { char firm; ...

Удалить последний элемент в односвязном списке
приведите пример удаления последнего элементы в односвязном списке в интернете находил вот это void DeleteLast(LIST *head) { ...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
7
Ответ Создать тему
Новые блоги и статьи
Модульный подход на примере F#
DevAlt 06.03.2026
В блоге дяди Боба наткнулся на такое определение: В этой книге («Подход, основанный на вариантах использования») Ивар утверждает, что архитектура программного обеспечения — это структуры,. . .
Управление камерой с помощью скрипта OrbitControls.js на Three.js: Вращение, зум и панорамирование
8Observer8 05.03.2026
Содержание блога Финальная демка в браузере работает на Desktop и мобильных браузерах. Итоговый код: orbit-controls-threejs-js. zip. Сканируйте QR-код на мобильном. Вращайте камеру одним пальцем,. . .
SDL3 для Web (WebAssembly): Синхронизация спрайтов SDL3 и тел Box2D
8Observer8 04.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-sync-physics-sprites-sdl3-c. zip На первой гифке отладочные линии отключены, а на второй включены:. . .
SDL3 для Web (WebAssembly): Идентификация объектов на Box2D v3 - использование userData и событий коллизий
8Observer8 02.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-collision-events-sdl3-c. zip Сканируйте QR-код на мобильном и вы увидите, что появится джойстик для управления главным героем. . . .
Реалии
Hrethgir 01.03.2026
Нет, я не закончил до сих пор симулятор. Эта задача сложнее. Не получилось уйти в плавсостав, но оно и к лучшему, возможно. Точнее получалось - но сварщиком в палубную команду, а это значит, в моём. . .
Ритм жизни
kumehtar 27.02.2026
Иногда приходится жить в ритме, где дел становится всё больше, а вовлечения в происходящее — всё меньше. Плотный график не даёт вниманию закрепиться ни на одном событии. Утро начинается с быстрых,. . .
SDL3 для Web (WebAssembly): Сборка библиотек: SDL3, Box2D, FreeType, SDL3_ttf, SDL3_mixer и SDL3_image из исходников с помощью CMake и Emscripten
8Observer8 27.02.2026
Недавно вышла версия 3. 4. 2 библиотеки SDL3. На странице официальной релиза доступны исходники, готовые DLL (для x86, x64, arm64), а также библиотеки для разработки под Android, MinGW и Visual Studio. . . .
SDL3 для Web (WebAssembly): Реализация движения на Box2D v3 - трение и коллизии с повёрнутыми стенами
8Observer8 20.02.2026
Содержание блога Box2D позволяет легко создать главного героя, который не проходит сквозь стены и перемещается с заданным трением о препятствия, которые можно располагать под углом, как верхнее. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru