【问题标题】:How to get a consistent hash/spectra of n points given a 32-byte md5 string如何在给定 32 字节 md5 字符串的情况下获得 n 点的一致哈希/谱
【发布时间】:2019-10-25 16:27:31
【问题描述】:

我想对一些内容进行 md5 哈希,然后生成一个可以说是 n 点的“曲线”或“频谱”。也就是说,要在从 0 到 1 的一条线上绘制 5、10 或 20 个点,以某种方式分布,使其对 md5 哈希是唯一的(碰撞并不重要)。基本上它看起来像一个原子发光光谱。

这些点(或光谱中的线)以某种方式基于提供的 md5 哈希生成,n 提供了说明您想要多少线。

所以它会是这样的:

function generateSpecrum(md5, n) { return [ ... ] }

默认情况下,它可以只返回 0 到 1 之间的值,但也许你给它一个开始和结束值来生成范围。

想知道如何做到这一点,用伪代码还是用 JS。

然而,标准 md5 散列有很多可能性。我会这样做:

var crypto = require('crypto')
var data = 'foo'
crypto.createHash('md5').update(data).digest('hex')
// acbd18db4cc2f85cedef654fccc4a4d8

所以是一个 32 字节的字符串。在我的情况下,它不需要产生全局唯一值,可能会有一些冲突,但如果有办法让它从不同的 md5 输入产生各种光谱,那就太酷了。

【问题讨论】:

  • 我想我明白你在这里想要做什么。 md5 哈希是 128 位或 16 字节。最好将它分成 8 位三元组来创建 RGB 颜色线,但 16 不能被 3 整除。因此,只需将 8 位字段中的两个重用于最后一个颜色三元组。这将为您提供 6 行代码。
  • 您当然可以通过选择更小的位域来创建更多颜色分辨率更低的线条。例如,使用 4 位字段可以有 11 行,使用 3 位字段可以有 15 行。
  • @JamesKPolk 或者您可以使用每行 8 位进行灰度(0 为黑色,255 为白色)。或者将 256 个值映射到 halftone palette
  • 想想看,你可以使用 5 位字段。这将为您提供 25 个不同的字段和 32 种不同的颜色,您可以将它们映射到 32 色半色调调色板。你会剩下三个比特。我想您可以将三个字段中的每个字段设为 6 位。或者有一个只能显示 8 种不同颜色的第 26 个字段。
  • 为什么不使用哈希作为随机种子并使用伪随机生成器生成任何内容?就像获取波长的数字,然后是波长 .... 从RGB values of visible spectrum 或从较差的 HSV 近似值计算波长的 RGB。 ...所以一切都归结为 1+n 随机调用

标签: string algorithm hash curve


【解决方案1】:

让我们忽略字符串数据是 md5 打印的部分,而是专注于如何为任意长度的十六进制字符串执行此操作,因此我们可以使用我们喜欢的任何摘要(从 CRC32 到 SHA-512):

  1. 从色调渐变背景开始(我们可以在 CSS 中做到这一点),
  2. 把字符串变成位打印(JS内置),然后
  3. 将对应于零位的任何区域涂黑。

作为一个可运行的 sn-p:

function hexstr2bin(stringinput) {
  // let's not be constrained by JS integer precision,
  // which is only good for 53 bits. Technically we don't
  // care what the "numbers" are here, we just want the
  // ones and zeros that the numbers turn into.
  return stringinput.split('').map(c => (
    parseInt(c, 16).toString(2).padStart(4,'0')
  )).join('');
}

function renderSpectrum(stringinput) {
  let cvs = document.createElement('canvas');
  let bits = Array.from(hexstr2bin(stringinput));

  cvs.width = bits.length;
  cvs.height = 1;
  ctx = cvs.getContext('2d');
  ctx.strokeStyle = 'black';
 
  bits.forEach( (bit,i) => {
    if (bit === "0") {
      ctx.moveTo(i,0);
      ctx.lineTo(i,1);
      ctx.stroke();
    }
  });

  document.body.appendChild(cvs);
};

renderSpectrum("acbd18db4fccc4a4d8");
renderSpectrum("c5887c91d0002f2a869a4b0772827701");
renderSpectrum("06956ff032d78e090d0d292aa9d8e7143ab08cf1ed444944529f79a4f937306a");
canvas {
  width: 100%;
  height: 40px;
  background: linear-gradient(
    to right,
    violet, blue, cyan, green, yellow, orange, red
  );
}

将画布拉伸到 100% 宽度意味着您可以免费进行模糊处理。奖金!

【讨论】:

    猜你喜欢
    • 2012-09-30
    • 1970-01-01
    • 2012-10-10
    • 1970-01-01
    • 2011-01-27
    • 1970-01-01
    • 2011-11-15
    • 1970-01-01
    • 2011-11-29
    相关资源
    最近更新 更多