Blockchain (BlockChain) can be easily implemented with only java

Blockchain logic: Create a block according to the required information, and then use the defined hash value calculation method to continuously calculate until the desired result is achieved, and then pass layer-by-layer verification and add it to our blockchain.

1. Set the member properties

​
    //区块链
    List<Block> blockchain = new ArrayList<>();
    //哈希值,判断挖矿成功与否
    private String hash;
    //前块哈希值,便于之后验证成功与否
    private String previousHash;
    //所需存储数据
    private String data;
    //时间戳
    private long timeStamp;
    //用于判断”挖矿“成功的密码学数字
    private int nonce;
    //构析方法,得到所需信息
    public Block(String data,String previousHash,long timeStamp){
        this.data = data;
        this.previousHash = previousHash;
        this.timeStamp = timeStamp;
        this.hash = calculateBlockHash();
    }

2. Calculate the hash value method ("mining" method)

The so-called mining is to carry out continuous calculations until "mining", and we use the hash algorithm to complete this algorithm.

    //得到对应hash字符串
    //hash算法优势:输出格式一致,而且对数的变化十分敏感,对于之后验证挖矿成功与否作用巨大!
    public String calculateBlockHash(){
        //生成独属的字符串,方便之后转换
        String dataToHash = previousHash + Long.toString(timeStamp)
        + Integer.toString(nonce) + data;
        MessageDigest digest = null;
        byte[] bytes = null;
        try {
            //创建一个提供信息摘要算法的对象,初始化为SHA-256算法对象
            digest = MessageDigest.getInstance("SHA-256");
            //用对象调用,信息摘要计算方法,计算后获得字节数组
            //dataToHash.getBytes(UTF_8),将字符串转换为字节数组
            bytes = digest.digest(dataToHash.getBytes(UTF_8));
        } catch (Exception ex) {
            System.out.println(ex.getMessage());
        }
        //用缓存字符串
        StringBuffer buffer = new StringBuffer();
        for (byte b : bytes) {
            //延伸字符串
            //String.format("%02x", b),以十六进制输出,2为指定的输出字段的宽度.如果位数小于2,则左端补0
            buffer.append(String.format("%02x", b));
        }
        //返回字符串
        return buffer.toString();
    }

3. Set the conditions for successful mining

To be honest, the matter of "mining" itself is already very abstract, but we still need to follow this path to consider a situation of "mining". In the case where our "mining" is actually to calculate the hash value of the block, our idea is to find the hash value starting with four 0s.

    //定义了一个前缀4,这实际上意味着我们希望哈希以4个零开始。
   
    int prefix = 4;
    String prefixString = new String(new char[prefix]).replace('\0', '0');

4. "Dig to" method

This reflects the value of the hash algorithm. Just by giving nonce++, the hash value can be significantly changed, so that its prefix may reach "0000".

And since only the nonce value does not provide any information, there is no problem in assigning it.

    //开挖
    public String mineBlock(int prefix){
        //创建一个有perfix个的“0”的字符串
        String prefixString = new String(new char[prefix]).replace('\0','0');
        //找到开头有perfix多个0的字符串
        //substring方法是,从字符串几位读到几位
        while(!hash.substring(0,prefix).equals(prefixString)){
            //决定那个块
            nonce++;
            //通过nonce变化,更新hash值
            hash = calculateBlockHash();
        }
        //找到了
        return hash;
    }

5. Add a block

    //在区块链里添加一个块
    public void givenBlockchain_whenNewBlockAdded_thenSuccess() {
        //建立一个区块
        Block newBlock = new Block(
                "The is a New Block.",
                blockchain.get(blockchain.size() - 1).getHash(),
                new Date().getTime());
        //找到四个0的区块
        newBlock.mineBlock(prefix);
        //再次检验是否正确
        assertTrue(newBlock.getHash().substring(0, prefix).equals(prefixString));
        //添加一个区块
        blockchain.add(newBlock);
    }

6. Blockchain verification

In order to ensure the reliability of the block, we have conducted multiple verifications to ensure that it is absolutely correct.

Verification: Whether the hash value of the added block is equal to the result of the hash algorithm -->

Whether the hash value of the previous block of the added block is equal to the value of the previous block -->

Whether the hash value of the added block starts with "0000"

    //区块链验证
    public void givenBlockchain_whenValidated_thenSuccess() {
        boolean flag = true;
        for (int i = 0; i < blockchain.size(); i++) {
            //得到前区块的hash值
            String previousHash = i==0 ? "0" : blockchain.get(i - 1).getHash();
            //进行真伪判断
            //原理:判断hash是否等于计算的hash//判断储存的前区块hash是否等于真正的hash//判断是否满足“挖矿”成功的条件
            flag = blockchain.get(i).getHash().equals(blockchain.get(i).calculateBlockHash())
                    && previousHash.equals(blockchain.get(i).getPreviousHash())
                    && blockchain.get(i).getHash().substring(0, prefix).equals(prefixString);
            //一次不行就直接跳出
            if (!flag) break;
        }
        //进行正确性检验
        assertTrue(flag);
    }

Now that it's done, let's start making our own blockchain and add some private information so that no one else can know it!

Guess you like

Origin blog.csdn.net/AkinanCZ/article/details/126491849
Recommended