百度360必应搜狗淘宝本站头条
当前位置:网站首页 > 技术教程 > 正文

跟着老廖(廖雪峰)学习区块链(4)教程:私钥

suiw9 2024-10-24 15:50 25 浏览 0 评论

在比特币中,私钥本质上就是一个256位的随机整数。我们以JavaScript为例,演示如何创建比特币私钥。

在JavaScript中,内置的Number类型使用56位表示整数和浮点数,最大可表示的整数最大只有9007199254740991。其他语言如Java一般也仅提供64位的整数类型。要表示一个256位的整数,只能使用数组来模拟。bitcoinjs使用bigi这个库来表示任意大小的整数。

下面的代码演示了通过ECPair创建一个新的私钥后,表示私钥的整数就是字段d,我们把它打印出来:

const bitcoin = require('bitcoinjs-lib');

let keyPair = bitcoin.ECPair.makeRandom();
// 打印私钥:
console.log('private key = ' + keyPair.d);
// 以十六进制打印:
console.log('hex = ' + keyPair.d.toHex());
// 补齐32位:
console.log('hex = ' + keyPair.d.toHex(32));

要在线运行代码,请点击阅读原文并用浏览器访问网页版本

注意:每次运行上述程序,都会生成一个随机的ECPair,即每次生成的私钥都是不同的。

256位的整数通常以十六进制表示,使用toHex(32)我们可以获得一个固定64字节的十六进制字符串。注意每两个十六进制字符表示一个字节,因此,64字符的十六进制字符串表示的是32字节=256位整数。

想要记住一个256位的整数是非常困难的,并且,如果记错了其中某些位,这个记错的整数仍然是一个有效的私钥,因此,比特币有一种对私钥进行编码的方式,这种编码方式就是带校验的Base58编码。

对私钥进行Base58编码有两种方式,一种是非压缩的私钥格式,一种是压缩的私钥格式,它们分别对应非压缩的公钥格式和压缩的公钥格式。

具体地来说,非压缩的私钥格式是指在32字节的私钥前添加一个0x80字节前缀,得到33字节的数据,对其计算4字节的校验码,附加到最后,一共得到37字节的数据:

计算校验码非常简单,对其进行两次SHA256,取开头4字节作为校验码。

对这37字节的数据进行Base58编码,得到总是以5开头的字符串编码,这个字符串就是我们需要非常小心地保存的私钥地址,又称为钱包导入格式:WIF(Wallet Import Format),整个过程如下图所示:

可以使用wif这个库实现WIF编码:

const wif = require('wif');

// 十六进制表示的私钥:
let privateKey = '0c28fca386c7a227600b2fe50b7cae11ec86d3bf1fbe471be89827e19d72aa1d';
// 对私钥编码:
let encoded = wif.encode(
        0x80, // 0x80前缀
        Buffer.from(privateKey, 'hex'), // 转换为字节
        false // 非压缩格式
);
console.log(encoded);

另一种压缩格式的私钥编码方式,与非压缩格式不同的是,压缩的私钥格式会在32字节的私钥前后各添加一个0x80字节前缀和0x01字节后缀,共34字节的数据,对其计算4字节的校验码,附加到最后,一共得到38字节的数据:

对这38字节的数据进行Base58编码,得到总是以K或L开头的字符串编码,整个过程如下图所示:

通过代码实现压缩格式的WIF编码如下:

const wif = require('wif');

// 十六进制表示的私钥:
let privateKey = '0c28fca386c7a227600b2fe50b7cae11ec86d3bf1fbe471be89827e19d72aa1d';
// 对私钥编码:
let encoded = wif.encode(
        0x80, // 0x80前缀
        Buffer.from(privateKey, 'hex'), // 转换为字节
        true // 压缩格式
);
console.log(encoded);

目前,非压缩的格式几乎已经不使用了。bitcoinjs提供的ECPair总是使用压缩格式的私钥表示:

const
    bitcoin = require('bitcoinjs-lib'),
    BigInteger = require('bigi');

let
    priv = '0c28fca386c7a227600b2fe50b7cae11ec86d3bf1fbe471be89827e19d72aa1d',
    d = BigInteger.fromBuffer(Buffer.from(priv, 'hex')),
    keyPair = new bitcoin.ECPair(d);
// 打印WIF格式的私钥:
console.log(keyPair.toWIF());

小结

比特币的私钥本质上就是一个256位整数,对私钥进行WIF格式编码可以得到一个带校验的字符串。

使用非压缩格式的WIF是以5开头的字符串。

使用压缩格式的WIF是以K或L开头的字符串。

相关推荐

Qt编程进阶(99):使用OpenGL绘制三维图形

一、Qt中的OpenGL支持...

OpenGL基础图形编程(七)建模(opengl教程48讲)

七、OpenGL建模  OpenGL基本库提供了大量绘制各种类型图元的方法,辅助库也提供了不少描述复杂三维图形的函数。这一章主要介绍基本图元,如点、线、多边形,有了这些图元,就可以建立比较复杂的模型了...

ffmpeg cv:Mat编码成H265数据流(ffmpeg编码mp4视频)

流程下面附一张使用FFmpeg编码视频的流程图。使用该流程,不仅可以编码H.264的视频,而且可以编码MPEG4/MPEG2/VP8等等各种...

986g超轻酷睿本,联想ThinkPad X1 Carbon 2025 Aura评测

今年3月份,联想首发了搭载Intel酷睿Ultra移动平台的ThinkPadX1CarbonGen12轻薄本,其续航表现令人惊喜。时隔9个月,IT之家收到了ThinkPad...

拆解五六年前的国产平板,这做工!

之前在论坛有幸运得被抽到奖,就是猎奇手机镜头,到手的时候玩了下鱼眼和广角微距,效果见图,用手机拍的那么就进入正题来说下拆鸡过程,外壳我就不拍出来了,免得打广告之嫌,拆出背面外壳就出现了一个裸板。第...

什么是闭合GOP和开放GOP?(闭合式和开放式区分)

翻译|Alex技术审校|李忠本文来自OTTVerse,作者为KrishnaRaoVijayanagar。...

拆解五六年前的国产平板(国产平板怎么拆开)

之前在论坛有幸运得被抽到奖,就是猎奇手机镜头,到手的时候玩了下鱼眼和广角微距,效果见图,用手机拍的那么就进入正题来说下拆鸡过程,外壳我就不拍出来了,免得打广告之嫌,拆出背面外壳就出现了一个裸板。第...

如何使用PSV播放MP4 视频自动退出怎么办

作者:iamwin来源:巴士论坛(点此进入)看到有很多同学在为psv无法播放视频而困扰,自己研究了下,发一个可以解决PSV出现播放视频播放到一半就跳出的问题。就是这个问题:首先,请大家先升级到版本≥1...

2023-03-21:音视频解混合(demuxer)为MP3和H264...

2023-03-21:音视频解混合(demuxer)为MP3和H264,用go语言编写。答案2023-03-21:...

FFmpeg解码H264及swscale缩放详解

本文概要:...

CasaOS保姆级喂饭教程!网心云OEC-Turbo安装CasaOS系统固件!

本内容来源于@什么值得买APP,观点仅代表作者本人|作者:柒叶君...

Firefox 33将整合思科开源编解码器OpenH264

思科去年在BSD许可证下开源了支持H.264编解码的OpenH264,Mozilla则在当时宣布将在Firefox中整合思科的二进制模块。现在,最新的FirefoxNightly(Firefox3...

为什么传输视频流的时候需要将YUV编码成H.264?

首先开始的时候我们借用一张雷神的图帮助大家理解一下从上图可以看出我们要做的,就是将像素层的YUV格式,编码出编码层的h264数据。...

FFmpeg学习(1)开篇(ffmpeg开发教程)

FFmpeg学习(1)开篇...

喜欢看视频必须了解 AV1编码那点事

喜欢看视频的小伙伴大概都有点感觉,AV1这个不太熟悉的视频格式,最近闹出的事情可不少,比如视频网站为了节约带宽偷偷默认使用AV1格式,让电脑狂转;比如Intel专门给旧CPU发布了相关工具;再比如GP...

取消回复欢迎 发表评论: