Добавление элементов в конец списка

Пусть L обозначает кольцевой двунаправленный список с заглавным звеном. Описать функцию или процедуру, которая в конец непустого списка L добавляет все его элементы,располагая их в обратном порядке (например по списку из элемен¬тов 1, 2, 3 требуется построитьсписок из элементов 1,2,3,3,2,1). Задание №18 (Двунаправленные списки) (см. "Сборник задач для начинающего программиста").

Алгоритм:
1)Описываем структуру данных.
2)Создаем функцию для печати списка.
3)Создаем Функцию которая создает список из заданного количества элементов.
4)Создаем функцию которая копирует в конец списка все его элементы в обратном порядке.
5)Пишем int main в которой:
-Получаем размер списка
-Проверяем корректность значения
-Создаем список
-Печатаем созданный список
-Производим оперцию над списком
-Печатаем созданный список
-Удаляем список и освобождаем память

#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
 
// Описываем структуру данных - элемент списка
struct L
{
	int value;
	L* nextItem;
	L* prevItem;
};
 
// Функция печатает список
void printList(L* List)
{
	L *currentItem=List;
	L *firstItem=List; // Запоминаем первый элемент,что бы при просмотре списка не впасть в бесконечный цикл
	while(currentItem) 
	{
		printf("%d\n", currentItem->value);
		currentItem=currentItem->nextItem;
		if(currentItem==firstItem)
		{
			break;
		};
	};
}
 
// Функция создает список из заданного количества элементов
L* createList(int size)
{
	L* List=new L;
	L* currentItem=List;
 
	currentItem->value=rand();
 
	for(int num=2;num<=size;num++)
	{
		// Создаем новый элемент списка
		currentItem->nextItem=new L;
		currentItem->nextItem->value=rand();
		// Устанавливаем указатель на предыдущий элемент списка
		currentItem->nextItem->prevItem=currentItem;
		// Перемещаем указатель текущего элемента на только что созданный элемент списка
		currentItem=currentItem->nextItem;
		// Если это последний элемент списка,делаем список кольцевым
		if(num==size)
		{
			currentItem->nextItem=List;
			List->prevItem=currentItem;
		};
	};
	return List;
}
 
// Функция копирует в конец списка все его элементы в обратном порядке
L* changeList(L *List)
{
	L *currentItem1=List->prevItem;
	L *currentItem2=List->prevItem;
	L *lastItem=List->prevItem; // Запоминаем последний элемент,что бы при просмотре списка не впасть в бесконечный цикл
	while(currentItem1) 
	{
		// Добавляем элемент
		currentItem2->nextItem=new L;
		currentItem2->nextItem->value=currentItem1->value;
		currentItem2->nextItem->prevItem=currentItem2;
		currentItem2->nextItem->nextItem=NULL;
		//List->prevItem=currentItem2->nextItem;
 
		currentItem2=currentItem2->nextItem;
		//
		currentItem1=currentItem1->prevItem;
		if(currentItem1==lastItem)
		{
			// "Замыкаем" список - последний элемент указывает на первый
			currentItem2->nextItem=List;
			List->prevItem=currentItem2;
			break;
		};
	};
	return List;
}
 
 
int main()
{
	L* testList;
	int testListSize=0;
 
	std::cout<<"Vvedite razmer spiska:\t";
	// Получаем размер списка
	std::cin>>testListSize;
	// Проверяем корректность значения
	if(testListSize==0)
	{
		std::cout<<"Razmer ne vernyi!\n";
		getch();
		exit(0);
	}
	// Создаем список
	testList=createList(testListSize);
	// Печатаем созданный список
	std::cout<<"\n\n\nSpisok:\n\n";
	printList(testList);
	// Производим оперцию над списком
	testList=changeList(testList);
	// Печатаем созданный список
	std::cout<<"\n\n\nNovyi Spisok:\n\n";
	printList(testList);
	// Удаляем список и освобождаем память
	L* currentItem=testList;
	L *firstItem=testList;
	while(testList->nextItem)
	{
		currentItem=testList->nextItem;
		delete testList;
		testList=currentItem;
		if(currentItem==firstItem)
		{
			break;
		};
	};
	// Ожидаем от пользователя нажатия любой клавиши для выхода из программы
	getch();
}

Ключевые слова: 
двунаправленые списки, добавление элементов
ВложениеРазмер
List_2.rar62.61 кб