雙向鏈表實現長整數運算

*問題描述:設計一個實現任意長的整數進行加法運算的演示程序。
*基本要求:利用雙向循環鏈表實現長整數的存儲,每個結點含一個整形變量。任何整形變量的範圍是 -(2^15 - 1)~ (2^15 - 1)。輸入和輸出形式:按中國對於長整數的表示習慣,每四位一組,組間用逗號隔開。 
*測試數據:
(1)0;0;應輸出“0”。
(2)-2345,6789;-7654,3211;應輸出“-1,0000,0000”。
(3)-9999,9999;1,0000,0000,0000;應輸出“999
(4)1,0001,0001;-1,0001,0001;應輸出“0”。
(5)1,0001,0001;-1,0001,0000;應輸出“1”。
(6)-9999,9999,9999;-9999,9999,9999;應輸出“1,9999,9999,9998”。

(7)1,0000,9999,9999;1;應輸出“1,0001,0000,0000”。


幫朋友寫的,略挫。。湊合看吧。。

再次重申VC6是渣中之渣,誰用誰掛東南枝。

#include <algorithm>
#include <iostream>
#include <sstream>
#include <cstring>
#include <cstdio>
#include <vector>
#include <string>
#include <queue>
#include <stack>
#include <cmath>
#include <set>
#include <map>
using namespace std;

typedef int DataType;
#define mem(a, n) memset(a, n, sizeof(a))
#define ALL(v) v.begin(), v.end()
#define si(a) scanf("%d", &a)
#define sii(a, b) scanf("%d%d", &a, &b)
#define siii(a, b, c) scanf("%d%d%d", &a, &b, &c)
#define pb push_back
#define eps 1e-8
const int Base = 10000, inf = 0x3f3f3f3f, N = 10000 + 5;

int T, cas = 0;
int n, m;
typedef struct DoubleNode {
    DataType data;
    struct DoubleNode *prior;
    struct DoubleNode *next;
}DLNode;
void InitNode(DLNode **head) {
    if((*head = (DLNode*)malloc(sizeof(DLNode))) == NULL) exit(1);
    (*head)->prior = NULL;
    (*head)->next = NULL;
}
void DestroyNode(DLNode **head) {
    DLNode *p, *tmp;
    p = (*head)->next;
    while(p != NULL) {
        tmp = p;
        p = p->next;
        free(tmp);
    }
    free(p);
    head = NULL;
}
// insert x
bool InsertNode(DLNode *head, DataType x) {
    DLNode *pNode, *newNode;
    int cnt = 0;
    if(head == NULL) {
        puts("插入錯誤");
        return false;
    }
    pNode = head;
    while(pNode->next != NULL)
        pNode = pNode->next;
    if((newNode = (DLNode *)malloc(sizeof(DLNode))) == NULL) exit(1);
    newNode->data = x;
    newNode->prior = pNode;
    newNode->next = NULL;
    pNode->next = newNode;
    return true;
}
void InsertNodePre(DLNode **head, DataType x) {
    DLNode *pNode = (DLNode *)malloc(sizeof(DLNode));
    pNode->data = x;
    pNode->next = (*head);
    pNode->prior = NULL;
    (*head)->prior = pNode;
    (*head) = pNode;
}

int Digit(int x) {
    int cnt = 0;
    while(x) {
        x /= 10;
        cnt ++;
    }
    return cnt;
}
void PrintNode(DLNode *head) {
    DLNode *p = head->next;
    if(head->data < 0) printf("-");
    while(p->data == 0 && p->next != NULL) p = p->next;
    printf("%d", p->data);
    p = p->next;
    while(p != NULL) {
        putchar(',');
        printf("%04d", p->data);
        p = p->next;
    } puts("");
}

int Compare(DLNode *a, DLNode *b) {
    int len1 = abs(a->data), len2 = abs(b->data);
    if(len1 > len2) return 1;
    else if(len2 > len1) return -1;
    else {
        DLNode *p1 = a, *p2 = b;
        while(p1->next != NULL) {
            p1 = p1->next, p2 = p2->next;
            if(p1->data == p2->data) continue;
            if(p1->data > p2->data) return 1;
            else return -1;
        }
    }
    return 0;
}

DLNode* add(DLNode *a, DLNode *b) {
    DLNode *p1 = a, *p2 = b, *head;
    InitNode(&head);
    while(p1->next != NULL) p1 = p1->next;
    while(p2->next != NULL) p2 = p2->next;
    int carry = 0, cnt = 0;
    int len1 = abs(a->data), len2 = abs(b->data);
    for(int i = 0; i < len1 || i < len2; i ++) {
        int x = 0, y = 0, num = 0;
        if(p1->prior != NULL) {
            x = p1->data;
            p1 = p1->prior;
        }
        if(p2->prior != NULL) {
            y = p2->data;
            p2 = p2->prior;
        }
        num = x + y + carry;
        carry = num / Base;
        num %= Base;
        if(!cnt) {
            InitNode(&head);
            head->data = num;
        } else {
            InsertNodePre(&head, num);
        }
        cnt ++;
    }
    if(carry > 0)
        InsertNodePre(&head, carry);
        

    DLNode *pNode = (DLNode *)malloc(sizeof(DLNode));
    pNode->next = head;
    pNode->prior = NULL;
    pNode->data = cnt;
    head->prior = pNode;
    return pNode;
}

DLNode* sub(DLNode *a, DLNode *b) {
    DLNode *p1 = a, *p2 = b, *head;
    InitNode(&head);
    while(p1->next != NULL) p1 = p1->next;
    while(p2->next != NULL) p2 = p2->next;
    int borrow = 0, cnt = 0, flag = 1;
    int len1 = abs(a->data), len2 = abs(b->data);
    for(int i = 0; i < len1 || i < len2; i ++) {
        int x = 0, y = 0, num = 0;
        if(p1->prior != NULL) {
            x = p1->data;
            p1 = p1->prior;
        }
        if(p2->prior != NULL) {
            y = p2->data;
            p2 = p2->prior;
        }
        num = x - y - borrow;
        borrow = 0;
        if(num < 0) {
            borrow = 1;
            num = (num + Base) % Base;
        }
        if(!cnt) {
            head->data = num;
        } else {
            InsertNodePre(&head, num);
        }
        cnt ++;
    }
    DLNode *pNode = (DLNode *)malloc(sizeof(DLNode));
    pNode->next = head;
    pNode->prior = NULL;
    pNode->data = cnt;
    head->prior = pNode;
    return pNode;
}
void Addition(DLNode *a, DLNode *b) {
    int len1 = abs(a->data), len2 = abs(b->data);
    int f1 = 1, f2 = 1, flag;
    DLNode *newNode = (DLNode *)malloc(sizeof(DLNode));
    if(a->data < 0) f1 = -1;
    if(b->data < 0) f2 = -1;
    if(f1 * f2 > 0) {
        newNode = add(a, b);
        flag = f1;
    } else {
        int ret = Compare(a, b);
        if(ret > 0) {
            flag = a->data;
            newNode = sub(a, b);
        } else if(ret < 0){
            flag = b->data;
            newNode = sub(b, a);
        } else {
            flag = 1;
            newNode = sub(a, b);
        }
    }
    newNode->data = flag;
    PrintNode(newNode);
}

void Subtraction(DLNode *a, DLNode *b) {
    int len1 = abs(a->data), len2 = abs(b->data);
    int f1 = 1, f2 = 1, flag;
    DLNode *newNode = (DLNode *)malloc(sizeof(DLNode));
    if(a->data < 0) f1 = -1;
    if(b->data < 0) f2 = -1;
    if(f1 * f2 < 0) {
        newNode = sub(a, b);
        flag = f1;
    } else {
        int ret = Compare(a, b);
        if(ret > 0) {
            newNode = add(a, b);
            flag = f1;
        } else if(ret < 0){
            newNode = add(b, a);
            flag = f2;
        } else {
            newNode = add(a, b);
            flag = 1;
        }
    }
    newNode->data = flag;
    PrintNode(newNode);
}

int InitNumber(DLNode *head, char *data) {
    int i = 0, x;
    head->data = 0;
    while(data[i] != ';') {
        x = 0;
        while(data[i] != ';' && data[i] != ',') {
            if(data[i] == '-') { i ++; continue; }
            x = x * 10 + data[i++] - '0';
        }
        if(data[i] == ',') i ++;
        InsertNode(head, x);
        head->data ++;
    }
    if(data[0] == '-') head->data = -(int)(head->data);
    return i + 1;
}

int main(){
#ifdef LOCAL
    freopen("/Users/apple/input.txt", "r", stdin);
    //	freopen("/Users/apple/out.txt", "w", stdout);
#endif
    
    char str[N];
    puts("輸入#退出");
    while(1) {
        DLNode *Number1, *Number2;
        InitNode(&Number1), InitNode(&Number2);
        printf("輸入數據:\n");
        scanf("%s", str);
        if(str[0] == '#') break;
        int index = 0;
        index = InitNumber(Number1, str + index);
        index = InitNumber(Number2, str + index);
        Addition(Number1, Number2);
        DestroyNode(&Number1);
        DestroyNode(&Number2);
    }    
    
    return 0;
}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章