Двусвязный список: найти слово четной длины - C (СИ)
Формулировка задачи:
#include "stdafx.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct spisok
{
char spi[30];
struct spisok *next;
struct spisok *prior;
} spi;
void create(spi **end, char word[350], int n)
{
int i = 0, j = 0;
while(word[i] != '.')
{
if(word[i] != ' ')
{
(*end)->spi[j] = word[i];
i++;
j++;
(*end)->spi[j] = '\0';
}
else
{
spi *next;
next = (spi*)malloc(sizeof(spi));
(*end)->next = next;
next->prior = *end;
next->next = NULL;
*end = next;
i++;
j = 0;
}
}
}
void print(spi* head)
{
for(spi *p = head; p != NULL; p = p->next)
{
printf("%s ", p->spi);
}
}
int _tmain(int argc, _TCHAR* argv[])
{
int n, k;
char word[350];
spi *head;
spi *end;
head = (spi*)malloc(sizeof(spi));
head->prior = NULL;
head->next = NULL;
end = head;
printf("Enter string: ");
gets(word);
n = strlen(word);
create(&end, word, n);
printf("Before changing: \n");
print(head);
printf("\n\nAfter changing: \n");
for(spi *p = head; p->next != NULL; p = p->next)
{
}
print(head);
printf("\n\n");
return 0;
}Решение задачи: «Двусвязный список: найти слово четной длины»
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct spisok;
typedef struct spisok spi;
struct spisok {
char data[30];
struct spisok *next;
struct spisok *prior;
};
void create(spi **end, const char *word)
{
int i = 0, j = 0;
while(word[i] != '.') {
if(word[i] != ' ') {
(*end)->data[j] = word[i];
i++;
j++;
(*end)->data[j] = '\0';
}
else {
spi *next;
next = (spi*)malloc(sizeof(spi));
(*end)->next = next;
next->prior = *end;
next->next = NULL;
*end = next;
i++;
j = 0;
}
}
}
void print(spi* head) {
spi *p = head;
for(; p != NULL; p = p->next) {
printf("%s ", p->data);
}
}
int check(const char *word) {
return (strlen(word) & 0x01) == 0;
}
int main(int argc, char* argv[])
{
//int n;//, k;
char word[350];
spi *head;
spi *end;
head = (spi*)malloc(sizeof(spi));
head->prior = NULL;
head->next = NULL;
end = head;
printf("Enter string: ");
gets(word);
//n = strlen(word);
create(&end, word);
printf("Before changing: \n");
print(head);
printf("\n\nAfter changing: \n");
spi *p = head;
while (p!= NULL) {
if(check(p->data)) {
// BEGIN delete item from 2way list
spi* tmp = p;
if(p->prior)
p->prior->next = p->next;
if(p->next)
p->next->prior = p->prior;
if(p == head)
head = p->next;
if(p == end)
end = p->prior;
p = tmp->next;
free(tmp);
// END delete item from 2way list
}
else
p = p->next;
}
print(head);
printf("\n\n");
// BEGIN destroy 2way list
while(head) {
spi* tmp = head;
head = head->next;
free(tmp);
}
// END destroy 2way list
return 0;
}
Объяснение кода листинга программы
В этом коде реализуется двусвязный список, который заполняется данными из введённой пользователем строки. Затем код проверяет, является ли длина какого-либо элемента списка чётной, и если это так, то удаляет этот элемент из списка. Список реализуется с помощью структурного типа данных spi, который содержит указатель на следующий элемент списка и на предыдущий, а также сам элемент списка (массив символов). Функция create добавляет новый элемент в список. Если новый элемент — это последнее добавление в список, то он становится «головным» элементом списка (т.е. next указывает на него, а prior — на null). Функция print выводит все элементы списка на экран. Функция check проверяет, является ли длина строки чётной. В функции main создаётся новый список, в который добавляется строка, введённая пользователем. Затем выводится на экран исходный список, после чего из него удаляются все элементы с чётной длиной. В конце выводится на экран полученный список. Удаление элемента из списка реализуется с помощью свободной памяти, выделенной под этот элемент. Соответственно, если элемент — «головной» список, то его нужно «сбросить» на следующего в списке. То же самое — если элемент является последним в списке. Если же элемент — простой внутренний элемент, то его можно просто удалить.