00:00
各位,我们现在呢,已经完成了数据的压缩,现在呢,反过来,反过来我们还要去完成数据的解压。那什么叫数据的解压呢?我们先把它的一个概念做一个介绍。我们用前面的霍夫曼编码得到了它的一个压缩过后的字节数组,也就是这个数组,还记得吧?那现在呢?我们要求使用赫夫曼编码进行解码,也就是说把原先这个BY的数组。叫什么呢?把它转成我们这个字符串。这就是我们这个所谓的数据解压。这个过程,那么这个数据解压的过程,其实就是我们编码的一个逆向操作,大家是不是是不是这样理解的,好,这样子我们上来。下面我们就来给大家讲解一下这个数据解码的过程。那同学们来看一下。
01:02
同学们来看一下我们这个步骤应该怎么做的问题是不是好,我们把这个思路捋一捋,就是现在完成什么呢?完成这个数据的解压。好,我的思路大致是这样子的,同学们想第一步。第一步,我们先将这个数组。同学们,现在这个不是你。处理过后的这个赫夫曼的这么一个呃,字节数组吗,就是将。Hoffman。Man cold。的一个一个BY的这个数组。说白了,就他。干什么?你先要将这个数组追星,先将这个数组。要把它接,要把它转成重新,你该这样说啊,重新先。
02:00
先转成哪个呢?重新先要把它转成这个字符串,不是转成这个字符串啊,你第一步应该先把它转成这个德行。是不是要把它转成一个赫夫曼的?赫夫曼,赫夫曼编码对应的一个二进制。对不对,二进制的一个字符串是不是,这肯定是你第一次要第一步要做的事。那后面我就不写那么多了啊,同学们,因为这个太长了。大家知道我想做什么事就可以。我点点点。然后第二步,第二步将赫夫曼编码对应的这一个二进制字符串。去干什么呢?去对应对照,对照什么呢?AK对照我们赫夫曼编码和。赫夫曼编码,把它重新给转成哪一个,重新给转成我们的这个字符串。
03:03
也就是刚才同学们看到的这个尺寸。它的步骤其实应该分两步。是不是因为你你在进行压缩的时候,是不是也是先将这个字符串转成赫夫曼对应的二进制字符串,然后再转成它的。字节数组的。是不是好,那现在我们应该把它写成两个方法,那我写两个方法,同学们,现在我们完成第一个干什么呢?我们写这么一个方法,同学们注意看private。Private static,然后呢,返回一个string。哦,返回一个string,然后呢,我们叫做bits。Two。啊,或者叫bit吧,Bit to,因为它是把一个字节转成一个呢,Bit。就是二进制的一个字符串,那你给我传一个什么过来呢?各位你传一个BBY就行了,我先把这个方法做一个解释,解释这个该方法呢,是完成什么呢,将。
04:06
一个bit bit转成。一个二进制的。什么呢字串。字不。就这么一个意思,就这么一个意思,好,那现在我们来写一写,看看大家能不能理解老师写的这个东西啊,首先呢,同学们,我们想法肯定是这样做的,如果你给我一个。B,我用它直接转成一个二进制最好了,但是我们发现呢,Be。这个是没包装类是没有一个two by。By string,呃,Bay string的这个方法,但是呢,Inegger有,大家看inegger它有一个方法叫To Ba string,但是呢,他就要传的是一个int,所以说我们上来过后可以这么过,这么这么做啊,注意听。
05:01
我呢,用一个变量,使用一个变量保存,保存什么呢?保存这个BOK,那temp等于V,其实这样子就是将什么呢?将这个B转成了一个int。这个大家理解啊好,既然转成了个,那下面呢,我就可以把temp传进去。好,这么穿进去过后呢,同学们看到我把这一个实卷返回去就可以了,按理说就这么简单对不对,但实际上没有这么简单啊,那我先把这个给他写出来,我们一点点的完善。好,同学们,现在我们来试一试这个方法能不能用,能不能用好,我在这个地方呢,把string给各位朋友打出来,你们看一下跟我们想的是否一样。来,我先调一调。我在这里做一下测试,同学们,我们测试一把我们那个to。To什么呀,Bit To Bit string这个方法。
06:04
同学们看看这个方法好不好用,然后呢,我们再逐一的对它进行一个完善,走bit to string,然后呢,我传一个。我穿一个,同学们看啊,我穿一个负一进去。我穿一个负一,当然你负一呢,因为它接受失败的,所以说你要转一下,好我们运行一把。各位同学我们看一看,非常的非常的遗憾,你发现没有,因为你在把这一个B,呃,BAT转成一个int过后呢,他就按照int的这一个补码给你返回的,注意它返回的是补码啊,我在这说一下。这一点我要强调,因为很多同学呢,对这个二进制学的不是很到位,所以说我这强调一下,注意这个地方返回的,返回的是temp对应的什么呀。二进制的补码,二进制二进制的补码。
07:00
所以说你看到它返回的,刚才同学们看到负一返回的呢,是这个样子的东西,并不是你想象的1000000000001,不是这个啊,这个是in,这个是int类型的负一的补码,其实我们要的也就是这个,这就出现了一个问题,什么问题呢?其实你要不了这么多。其实你是要不了,所以说你这存在一个截取的问题,大家明白我的意思吗?啊,所以说我们现在呢,首先要对这个方法进行一个改造,怎么改造呢。各位同学看啊,各位同学看,按理说呢,我们应该这样对对他进行一个处理,呃,就是说我们在返回的时候啊,我们在返回这个字符串的时候呢,应该来一个点substre。是不是我们应该从哪里呢,从哪里开始去减呢?是不是相当于说用你10G这个长度。点N减八。大家知道这是什么意思吗?这个就是相当于取我们后面的八位。
08:06
是不是因为你时间减去八,就是相当于说从那个索引倒数的第八个位置,所以说这个应该返回了,就应该有点像我们的东西了,你看这时我们返回的就这个东西了。也就是说你你对这个进行处理的,你返回的是这这个值,那如果说我要看的话,就是这个值,好这个这个我也不要了啊,我在上面打印了已经同学们看,现在你返回的就是负一的补码。但是这这个地方有一个问题。有一个什么问题吗?我们还存在一个麻烦事。大家看啊,如果我这减一,但是呢,很遗憾我把这个负一改成一了,这个地方呢,就会抛出一个。Index out of range的一个问题,大家知道这是为什么吗?好,这还是二进制的知识点,我告诉大家啊,如果说注意听。
09:02
如果说我们现在用用的是一个正数,比如说你你放了一个一过去,那么他他在这打出一个字符串,其实是多少呢?是一个一说说你还存在一个补位的问题,我不知道大家听听清楚我在说什么没有。好,我给你打出这个原始的十菌,你们就会看到这个十菌如果是正数的话,它返回的其实就只有一位。大家看这里。其实这个时候呢,你不但不能减,你还要补。你还要补位。是不是这个道理啊,所以说你这个地方这样做呢,是存在风险的,因此我们现在还存在一个这样的问题,什么呢?就是需要补位,就是如我们如果是正数。正数我们啊,我们还存在一个补补高位的问题,补高位的问题能理解我的意思吧,好,那么怎么样让他补高位呢?其实也非常简单,只要让这个痛啊,理论上说磨磨一下,大家看啊磨。
10:10
等256就可以了,哎,为什么这样就可以了呢?好,这样为什么就可以呢?我们来理解一下啊temp如果等于一。那么它的补码应该是多少呢?是0000。哦,假,假如说这个你你你放过来是个大树啊,假如是个大树。好,那么这个时候它呃呃,这个我们先看255是多少吧,你这个temp处理完了,我们先运行一下吧,干脆这样运行过后,大家大家看起来就比较清晰了,看啊走。你看这个时候呢,他反正不报错了,你看这个时候它返回的是000,为什么是这样的呢?我给大家简单的说一下,因为你这个255这个是暗卫暗卫语。暗卫,有可能有些同学能看懂啊。
11:01
暗卫语。安慰语的话呢,假这个255是多少呢?255其实这个。2552256啊,256是100000000,好,那么如果你传进来是个一,好,因为你是一,你是一的话呢,它的第一位是不是就这样子一个值啊,就是一。他是这样子,0000。00001。好,你这样一磨,各位你这样安慰语,安慰语语的话。同学们这样一语,这个结果就变成了同学们看到的1000000001,好,这样就可以了。所以说这里面有个。雨的问题,这样一个雨的问题,但是我们这样做就对了吗?我们还有一个麻烦事,说老师为什么这么麻烦呢?呃,就是这样的麻烦的,他还有一个问题,就是同学们有没有考虑我们现在每次都在按八位来处理,其实按理按这样子说,我们认为我们总是按八位来处理的,但是有一个问题,我们最后这一位。
12:14
就是我们最后这个28,他其实并不需要八位,打个比方,比如说我们最后对应的这个串串可能只有。1100。是不是有这种可能,就是你最后这一位有可能是不不满八位的,明白我在说什么吗?就是你最后这位有可能不满八位,如果你不满八位,其实你这个地方存在一个问题,说你你这个这个语没有意义。就是你安慰与没有意义,所以说既然如此,我们还存在一个变量要给他分析出来是什么呢?我写一下啊,Boing flag,这个稍微是有点麻烦同学们,主要是跟二进制有关,那这样子的话呢,我们就这样写啊,如果flag。
13:03
他传进来是真就是他需要来进行这个。这个与我们就写进去,如果他语了过后,好,这个时候呢,我们在截取的时候,这个代码就应该变成这样子了,来老师给他写一下if,如果flag是等于真的。OK,我们呢,就这样返回。是不是这样的道理,A20呢,好,那就按原封不动的形式返回就可以了,因为你有可能不需要说把这个高位补齐嘛,你有可能不需你你是因为最后这位是不需要的,因此我的代码就变成这个样子了,大家看能不能看懂。看不看懂,好,我把这几个参数再给他补一补啊,再给补一补。好,那我这再加一个参数。ADD parameter,那这里面这个flag表示什么意思呢?表示表示标识啊,标识什么呢?标识是否需要补高位。
14:02
不到位,如果为针,如果你传进来是个针触TE。T。如。对啊,如果。如果是处表示。表示需要补高位。OK,如果是false,如果是false,表示表示不补好,就这么一个含义,最后返回的是什么呢?各位同学,呃,这个B是你传入的。传入的这个一个bit。一个bit值,这里面返回的是什么呢?是该bit,注意听啊,是该bitt这个B对应的二进制。的那个字符串。哦,注意是按补码返回的,注意注意听,注意是按补码。不麻返返回,而我们,而我们本身原先编码的时候呢,本身也是按不骂的形式来编码的,还记不记得我是不是讲过你第一个这个11118位,前八位还记得吧,我们当时就是以这个推断,负的88是因为他是按补骂的形式来看,如果你如果你是按照源码来看,其他根本不是负,负的88。
15:20
对不对,所以说你其实这个地方它是都是按补码来操作的,这个大家记一下就行了。啊,也就说你这个10101000,其实这个是按照补码才是负的88。明白我的意思吧,OK,按照补码推回去啊,他按照补码推回去,它真实对应的。就是这个补码对应的真实的源码的值才是负的,88明明白的意思吧,好,那这块你实在看实在不明白,我说了啊,大家如果这块有点不明白呢,也不要着急,因为这个跟我们数据结构和算法没有太多关系,但是我这讲到这呢,我就提一下,如果看不懂,如果看不懂看不懂。
16:05
啊,可以参考参考我讲的讲的这个Java基础的部分,Java基础我讲过什么呢?讲讲过二进制的这个分析二。二进制的这个,呃,源码。源码、反码、补码。的一个剖析。补码的一个分析,好,有兴趣的可以去看一下,如果确实你这找不到我的,你在网上看一下就可以了,好,这个bit To Bit To Bit尺寸我们就讲完了,这个方法就说完了。大家看理不理理理不理解好,有了这个方法过后呢,同学们,各位同学啊,我们现在其实已经拥有一个最主要的能力,下面呢,我们就来真实的进行这个解码了,因为这个方法很重要。
我来说两句