大数阶乘java实现

节点类

public class Node {
Node pre;
Node next;
int data;

public Node() {
    super();
    
}

public Node(int data) {
    super();
    this.data = data;
}

public Node(Node pre, int data, Node next) {
    super();
    this.pre = pre;
    this.next = next;
    this.data = data;
}

public Node getPre() {
    return pre;
}

public void setPre(Node pre) {
    this.pre = pre;
}

public Node getNext() {
    return next;
}

public void setNext(Node next) {
    this.next = next;
}

public int getData() {
    return data;
}

public void setData(int data) {
    this.data = data;
}

}

双向链表类

public class DblList {

private Node first;
private Node tail;
public void setFirst(Node first) {
    this.first = first;
}

public void setTail(Node tail) {
    this.tail = tail;
}
public DblList() {
    super();
    this.first=new Node();
}

public Node getTail() {
    return tail;
}

public Node getFirst() {
    return first;
}
private Node insert(int data) {
    Node firstnode =this.getFirst();
    //如果链表为空,需要设置尾结点为最先插入的节点
    if(firstnode.next==null) {
        //此时尾结点为空,tailnode不等于尾结点
        Node newNode=new Node(data);
        //设置尾结点
        this.tail=newNode;
        firstnode.next=newNode;
        newNode.pre=firstnode;
        return newNode;
    }
    else {
        Node next = firstnode.getNext();
        Node newNode = new Node(firstnode,data,next);
        next.pre=newNode;
        firstnode.next=newNode;
        return newNode;
    }
}


//大数阶乘核心函数,每个节点最多三位,不足三位的在输出的时候需要补0
public void fac(int n) throws Exception {
    if(n<0) {
        throw new Exception("输入参数不能小于0");
    }
    Node tailNode = this.tail;
    //每次取被乘数都是从后取,判断链表是否为空,为空则先要处理一下链表。确保能取出来节点
    if(tailNode==null) {
        this.insert(1);
        tailNode = this.tail;
    }
    
    //循环乘n次,每次乘都是从后往前遍历。乘数是从1-->n
    for (int i = 1; i < n+1; i++) {
        
        //存放余数,一定放在for循环后,不能之前,否则出错
        int remain=0;
        //设置成从后往前遍历的游标
        Node current=tailNode;
        int result=0;
        //遍历所有节点和乘数相乘
        while(current!=this.first) {
            result=current.data*i;
            //结果和余数相加再取余,结果保留三位
            result=result+remain;
            current.data=result%1000;
            remain=result/1000;
            
            //如果有余数且当前节点的前一个节点为头结点则创建一个节点
            if(remain!=0&&current.pre==this.first) {
                while(remain>999) {
                    //一定要注意取新插入节点为当前节点,否则current=current.pre;这句语句不会转到头结点去,而会到新插入节点去,则又进入第一个while循环
                    Node insertNode = this.insert(remain%1000);
                    current=insertNode;
                    remain=remain/1000;
                }
                Node insertNode = this.insert(remain);
                //一定要注意取新插入节点为当前节点,否则current=current.pre;这句语句不会转到头结点去,而会到新插入节点去,则又进入第一个while循环
                current=insertNode;
            }
            current=current.pre;
        }
    }
    
}
public String output() throws Exception {
    Node firstnode = this.getFirst();
    StringBuffer sb;
    if(firstnode.next==null) {
        throw new Exception("空链表");
    }
    else {
        Node current=firstnode.next;
        sb=new StringBuffer();
        while(current!=null) {
            sb.append(String.format("%3d",current.data ).replace(" ", "0") );
            current=current.next;
        }
    }
    return sb.toString();
    
}

}

测试类

import java.util.Scanner;
public class Test {
public static void main(String[] args) throws Exception {

for (int i = 20; i < 26; i++) {
    DblList dblList = new DblList();
    dblList.fac(i);
    System.out.println("i="+i+"结果如下");
    System.out.println(dblList.output());
    }
}

}
i=20结果如下
002432902008176640000
i=21结果如下
051090942171709440000
i=22结果如下
001124000727777607680000
i=23结果如下
025852016738884976640000
i=24结果如下
620448401733239439360000
i=25结果如下
015511210043330985984000000

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容