四向链表构建--十字链表构建

面试不行,下来又行了系列,朗致算法笔试题,如果侵权联系删除

题目如下

定义一个四向链表,up,down,left, right ,val
分别代表上下左右及value,要求十分钟写一个算法,给定一个整数n,构建一个n*n的矩阵,例如 n=3,则矩阵 为

123
456
789

节点类

public class Node<T> {

    public T val;

    public Node<T> up;

    public Node<T> down;

    public Node<T> left;

    public Node<T> right;

    public Node(T t){
        this.val = t;
    }
}    

看了别人写的代码,大都是先把第一层写出来,然后套两个for循环做迭代,作为参考先写了第一个版本的,然后优化了一版,大家不喜勿喷。

第一个版本

    /**
     * 创建nxn的四向链表
     * @param n
     * @return
     */
    public Node<T> create4DicNode(int n){
        if(n<=0){
            return null;
        }
        Node head = null;
        //  先把第一行和第一列的节点都搞定
        head = createRight(head,n,1,1);
        head.down = createDown(head,n,1,2);
        Node colPoint = head;
        // 套两个for循环迭代
        for(int row=2;row<=n;row++){
            Node rowPoint = colPoint;
            for(int col=2;col<=n;col++){
                int value = (row-1)*n+col;
                Node newNode = new Node(value);

                Node up = rowPoint.right;
                Node left = rowPoint.down;

                up.down = newNode;
                newNode.up = up;

                left.right = newNode;
                newNode.left = left;

                rowPoint = rowPoint.right;
            }
            colPoint = colPoint.down;
        }
        return head;
    }

    public Node<T> createRight(Node head, int n , int col,int row){
        if(col>n){
            return null;
        }
        int value = (row-1)*n+col;
        Node newNode = new Node(value);
        if(head!=null){
            head.right = newNode;
            newNode.left = head;
        }
        createRight(newNode,n, ++col, row);
        return newNode;
    }

    public Node<T> createDown(Node head, int n , int col,int row){
         if(row>n){
             return null;
         }
         int value = (row-1)*n+col;
         Node newNode = new Node(value);
         if(head != null){
             head.down  = newNode;
             newNode.up = head;
         }
         createDown(newNode, n, col,++row);
         return newNode;
    }

第二个版本

    public Node create(int n){
        if(n<=0){
            return null;
        }
        // 先写头节点
        Node head = new Node(1);
        // 递归搞定
        create4DicNode(head, n, 1,1);
        return head;
    }


    public Node create4DicNode(Node node, int n,int col,int row){

        // 边界
        if(col>=n||row>=n){
            return null;
        }
        int value = (int) node.val;

        // 搞定右边节点
        Node<Integer> rightNode = node.right;
        if(rightNode == null){
            rightNode = new Node<>(value + 1);
            node.right = rightNode;
            rightNode.left = node;
        }

        // 搞定下边节点
        Node<Integer> downNode = node.down;
        if(downNode == null){
            downNode = new Node<>(value + n);
            node.down = downNode;
            downNode.up = node;
        }

        // 搞定斜下角节点,这个节点将right 和 down联系了起来
        Node<Integer> rightDownNode = new Node<>(value + n + 1);
        rightNode.down=rightDownNode;
        rightDownNode.up = rightNode;
        downNode.right = rightDownNode;
        rightDownNode.left = downNode;

        // 然后继续搞定down节点和right节点都 down,right,rightDown 节点,
        create4DicNode(rightNode,n,col+1,row);
        create4DicNode(downNode,n,col,row+1);

        // 最后返回
        return node;
    }

打印一下

	public void print(Node head){
        if(null==head){
            System.out.println("空节点");
            return;
        }
        Node s = head;
        while(s!=null){
            Node h = s;
            while(h!=null){
                System.out.print(h.val+" ");
                h=h.right;
            }
            s=s.down;
            System.out.println();
        }
    }

最后测试一下,加上边界值

n.print(n.create(0));
n.print(n.create(-1));
n.print(n.create(1));
n.print(n.create(3));

结果如下,验证没有问题:
空节点
空节点
1
1 2 3
4 5 6
7 8 9

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值