#include <stdio.h>
#include <stdlib.h>
typedef struct node{
    int dat;
    struct node *back,*next;
}LL;
struct node *first=NULL,*now=NULL,*end=NULL;
void view(void){
    putchar('\n');
    if(first==NULL){
        puts("linked list 中沒有項目");
        return;
    }
    LL* i;
    for(i=first ; i!=NULL  ; i=i->next){
        if(i == now){
            putchar('*');
        }
        printf("%d ",i->dat);
    }
    putchar('\n');
}
void createnew(int a){
    first=malloc(sizeof(LL));
    now=first;
    end=now;
    now->dat=a;
    now->back=NULL;
    now->next=NULL;
}
int main(){
    puts("linked list 模擬程式\n");
    int in;
    LL *tmp,*tmp2;
    while(1){
        view();
        printf(" 1 a:在後方插入一項\n"
               " 2 a:在前方插入一項\n"
               " 3 a:插入一項作為首項\n"
               " 4 a:插入一項作為尾項\n"
               " 5 d:刪除前一項\n"
               " 6 d:刪除後一項\n"
               " 7 d:刪除這一項\n"
               " 8 e:更改這一項\n"
               " 9 m:移到後一項\n"
               "10 m:移到前一項\n"
               "11 m:移到首項\n"
               "12 m:移到尾項\n"
               "13 r:刪除之後的所有項目\n"
               "14 r:刪除之前的所有項目\n"
               "請選擇:");
        if(scanf("%d",&in)!=1){
            puts("無效的輸入");
            fflush(stdin);
            continue;
        }
        /* 其實以下的內容可以透過函式來簡化,不過這個程式只是用來展示寫法,
         * 所以還是分開寫 */
        switch(in){
            case 1:
                printf("整數:");
                scanf("%d",&in);
                fflush(stdin);
                if(first==NULL){
                    createnew(in);
                    continue;
                }
                tmp=malloc(sizeof(LL));
                tmp->back=now;
                tmp->next=now->next;
                tmp->dat=in;
                now->next=tmp;
                if(tmp->next != NULL){
                    tmp->next->back=tmp;
                }else{
                    end=tmp;
                }
                break;
            case 2:
                printf("整數:");
                scanf("%d",&in);
                fflush(stdin);
                if(first==NULL){
                    createnew(in);
                    continue;
                }
                tmp=malloc(sizeof(LL));
                tmp->back=now->back;
                tmp->next=now;
                tmp->dat=in;
                now->back=tmp;
                if(tmp->back != NULL){
                    tmp->back->next=tmp;
                }else{
                    first=tmp;
                }
                break;
            case 3:
                printf("整數:");
                scanf("%d",&in);
                fflush(stdin);
                if(first==NULL){
                    createnew(in);
                    continue;
                }
                tmp=malloc(sizeof(LL));
                tmp->back=NULL;
                tmp->next=first;
                tmp->dat=in;
                first->back=tmp;
                first=tmp;
                break;
            case 4:
                printf("整數:");
                scanf("%d",&in);
                fflush(stdin);
                if(first==NULL){
                    createnew(in);
                    continue;
                }
                tmp=malloc(sizeof(LL));
                tmp->back=end;
                tmp->next=NULL;
                tmp->dat=in;
                end->next=tmp;
                end=tmp;
                break;
            case 5:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                if(now->back==NULL){
                    puts("\n*** 沒有前一項 ***");
                    continue;
                }
                tmp=now->back;
                now->back=now->back->back;
                if(now->back != NULL){
                    now->back->next=now;
                }else{
                    first=now;
                }
                free(tmp);
                break;
            case 6:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                if(now->next==NULL){
                    puts("\n*** 沒有後一項 ***");
                    continue;
                }
                tmp=now->next;
                now->next=now->next->next;
                if(now->next != NULL){
                    now->next->back=now;
                }else{
                    end=now;
                }
                free(tmp);
                break;
            case 7:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                tmp=now;
                if(tmp->back != NULL){
                    tmp->back->next=tmp->next;
                }else{
                    first=tmp->next;
                }
                if(tmp->next != NULL){
                    tmp->next->back=tmp->back;
                    now=tmp->next;
                }else{
                    now=tmp->back;
                    end=tmp->back;
                }
                free(tmp);
                break;
            case 8:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                printf("原先的值:%d\n",now->dat);
                printf("新的數值:");
                scanf("%d",&now->dat);
                fflush(stdin);
                break;
            case 9:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                if(now->next==NULL){
                    puts("\n*** 沒有後一項 ***");
                    continue;
                }
                now=now->next;
                break;
            case 10:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                if(now->back==NULL){
                    puts("\n*** 沒有前一項 ***");
                    continue;
                }
                now=now->back;
                break;
            case 11:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                now=first;
                break;
            case 12:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                now=end;
                break;
            case 13:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                for(tmp=end ; tmp!=now ; tmp=tmp2){
                    tmp2=tmp->back;
                    free(tmp);
                }
                end=now;
                now->next=NULL;
                break;
            case 14:
                if(first==NULL){
                    puts("\n*** linked list 是空的 ***");
                    continue;
                }
                for(tmp=first ; tmp!=now ; tmp=tmp2){
                    tmp2=tmp->next;
                    free(tmp);
                }
                first=now;
                now->back=NULL;
                break;
            default:
                puts("沒有這個選項");

        }
    }
    return 0;
}