Bits Pic

题目

Background
A byte has 8 bits.

A UTF-8 code point has 1-4 bytes.

A byte can be considered as a left-to-right bit-stream pattern.

The bit-stream of multiple bytes can be concated so a UTF-8 code point can also be considered as a left-to-right bit-stream pattern.

A UTF-8 string has multiple UTF-8 code points so a UTF-8 string can also be considered as a left-to-right bit-stream pattern.

A bit-stream pattern can be visualized into a mono picture with each 0 as a white pixel and each 1 as a black pixel. Therefore, a 64-bytes string can be visualized into a 256-pixels (2561 or 648 or another consistent resolution) mono picture. We name such mono picture ‘Bits Pic’.

4 consecutive 0 bytes are used to indicate the end of string and only the content before these 4 bytes encountered for the first time is valid.

Samples
The bit-stream pattern of Byte ‘A’ is 01000001, ‘B’ is 01000010 and string “AB” is 0100000101000010.

This clip from Hamlet can be transformed into a Bits Pic like this:
在这里插入图片描述
This clip from Hamlet:

To be, or not to be, that is the question: Whether 'tis nobler in the
mind to suffer The slings and arrows of outrageous fortune, Or to take
Arms against a Sea of troubles, And by opposing end them: to die, to
sleep No more; and by a sleep, to say we end The heart-ache, and the
thousand natural shocks That Flesh is heir to? 'Tis a consummation
Devoutly to be wished. To die, to sleep, To sleep, perchance to Dream;
aye, there’s the rub, For in that sleep of death, what dreams may
come, When we have shuffled off this mortal coil, Must give us pause.
There’s the respect That makes Calamity of so long life: For who would
bear the Whips and Scorns of time, The Oppressor’s wrong, the proud
man’s Contumely, The pangs of dispised Love, the Law’s delay, The
insolence of Office, and the spurns That patient merit of th’unworthy
takes, When he himself might his Quietus make With a bare Bodkin? Who
would Fardels bear, To grunt and sweat under a weary life, But that
the dread of something after death, The undiscovered country, from
whose bourn No traveller returns, puzzles the will, And makes us
rather bear those ills we have, Than fly to others that we know not
of? Thus conscience does make cowards of us all, And thus the native
hue of Resolution Is sicklied o’er, with the pale cast of Thought, And
enterprises of great pitch and moment, With this regard their Currents
turn awry, And lose the name of Action. Soft you now, The fair
Ophelia? Nymph, in thy Orisons Be all my sins remember’d.

Question
Could you detect the valid UTF-8 string of this Bits Pic below?
在这里插入图片描述

答案

开始两个字母“To”

T : 84 :0101 0100
o : 111 :0110 1111

在这里插入图片描述
黑色:1 白色:0
像素点的颜色与之对应

可以用 java实现:

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

public class ImageText {
    public static void main(String[] args) throws Exception {
        System.out.println(getImageText("quiz5-tobe.png"));
        String s = getImageText("quiz5-abc.png");

        System.out.println(MD5(s));//43a58619d5acdf38bcfece771fc7b464
        System.out.println(s);
    }

    public static String getImageText(String image) throws Exception {
        int[] rgb=new int[3];
        File file=new File(image);
        BufferedImage bi=null;
        try {
            bi=ImageIO.read(file);
        } catch (Exception e) {
            e.printStackTrace();
        }
        int width=bi.getWidth();
        int height=bi.getHeight();
        int minx=bi.getMinX();
        int miny=bi.getMinY();
        byte[] bytes=new byte[height*width/8];
        int x=0;
        StringBuilder tmp=new StringBuilder();
        for (int j=miny; j < height; j++) {
            for (int i=minx; i < width; i++) {
                int pixel=bi.getRGB(i, j); // 下面三行代码将一个数字转换为RGB数字
                rgb[0]=(pixel & 0xff0000) >> 16;
                rgb[1]=(pixel & 0xff00) >> 8;
                rgb[2]=(pixel & 0xff);
                System.out.println("pixel=" + pixel + "i=" + i + ",j=" + j + ":(" + rgb[0] + ","
                        + rgb[1] + "," + rgb[2] + ")");

                if (pixel == -1) {
                    tmp.append('0');
                } else {
                    tmp.append('1');
                }
                if (tmp.length() == 8) {
                    bytes[x++]=(byte) Integer.parseInt(tmp.toString(), 2);// 补码
                    tmp.setLength(0);
                }
            }
        }
        int i=bytes.length - 1;
        for (; i >= 0; i--) {
            if (bytes[i] != 0) {
                break;
            }
        }
        return new String(bytes, 0, i, StandardCharsets.UTF_8);
        // 0:白 1:黑
    }

    private static String MD5(String input) {
        if (input == null || input.length() == 0) {
            return "";
        }
        try {
            MessageDigest md5=MessageDigest.getInstance("MD5");
            md5.update(input.getBytes());
            byte[] byteArray=md5.digest();
            StringBuilder sb=new StringBuilder();
            for (byte b : byteArray) {
                // 一个byte格式化成两位的16进制,不足两位高位补零
                sb.append(String.format("%02x", b));
            }
            return sb.toString();
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
        return "";
    }
}

解密得到

浔阳江头夜送客,枫叶荻花秋瑟瑟。
主人下马客在船,举酒欲饮无管弦。
醉不成欢惨将别,别时茫茫江浸月。
忽闻水上琵琶声,主人忘归客不发。
寻声暗问弹者谁,琵琶声停欲语迟。
移船相近邀相见,添酒回灯重开宴。
千呼万唤始出来,犹抱琵琶半遮面。
转轴拨弦三两声,未成曲调先有情。
弦弦掩抑声声思,似诉平生不得志。
低眉信手续续弹,说尽心中无限事。
轻拢慢捻抹复挑,初为霓裳后六幺。
大弦嘈嘈如急雨,小弦切切如私语。
嘈嘈切切错杂弹,大珠小珠落玉盘。
间关莺语花底滑,幽咽泉流冰下难。
冰泉冷涩弦凝绝,凝绝不通声暂歇。
别有幽愁暗恨生,此时无声胜有声。
银瓶乍破水浆迸,铁骑突出刀枪鸣。
曲终收拨当心画,四弦一声如裂帛。
东船西舫悄无言,唯见江心秋月白。
沉吟放拨插弦中,整顿衣裳起敛容。
自言本是京城女,家在虾蟆陵下住。
十三学得琵琶成,名属教坊第一部。
曲罢曾教善才服,妆成每被秋娘妒。
五陵年少争缠头,一曲红绡不知数。
钿头银篦击节碎,血色罗裙翻酒污。
今年欢笑复明年,秋月春风等闲度。
弟走从军阿姨死,暮去朝来颜色故。
门前冷落鞍马稀,老大嫁作商人妇。
商人重利轻别离,前月浮梁买茶去。
去来江口守空船,绕船月明江水寒。
夜深忽梦少年事,梦啼妆泪红阑干。
我闻琵琶已叹息,又闻此语重唧唧。
同是天涯沦落人,相逢何必曾相识!
我从去年辞帝京,谪居卧病浔阳城。
浔阳地僻无音乐,终岁不闻丝竹声。
住近湓江地低湿,黄芦苦竹绕宅生。
其间旦暮闻何物?杜鹃啼血猿哀鸣。
春江花朝秋月夜,往往取酒还独倾。
岂无山歌与村笛?呕哑嘲哳难为听。
今夜闻君琵琶语,如听仙乐耳暂明。
莫辞更坐弹一曲,为君翻作琵琶行。
感我此言良久立,却坐促弦弦转急。
凄凄不似向前声,满座重闻皆掩泣。
座中泣下谁最多?江州司马青衫湿。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值