as3中的移位运算

在as3中,很少时候能看到代码中含有移位操作,可能大多数人最常见的移位操作,也就是用来提取颜色通道的那几行代码:

var color:uint = 0x0FF0F0F0;
var a:uint =	(color & 0xFF000000) >> 24;
var red:uint =	(color & 0x00FF0000) >> 16;
var green:uint =(color & 0x0000FF00) >> 8;
var blue:uint = (color & 0x000000FF);
位操作有其自身的优点和缺点,优点是运算速度快,占用空间小,缺点是代码很难阅读,开发成本高。可能很多人还是喜欢面向对象这种高级语言,因为在编写程序本身的同时,我们就能说明自己的意图。但是无论是出于优化的考虑还是为了同项目中的那些Geek协作上的方便,我们还是需要掌握位操作的本质及常见的用法:

说到本质,估计大部分人还是知道一点的,但未必细致入微。

我们都知道计算机的数据是以字节为单位的,每个字节有8个位,每个位有两种状态0或者1,移位操作顾名思义是将这些位进行整体移动,这一点直观上非常容易理解,不用多说。但一旦涉及到实际问题,我们可能就会犯迷糊,比如1>>3的结果是多少。从本质上分析1这个数据在内存中向右移动三个位后最后一位的信息将消失,剩下来的都是0,因此结果毫无疑问是0。所以那些想要通过右移来达到除法目的的人来说就要小心了。

其实位操作很少被任意乱用,或者说位运算会有一些固定用法,比如我们文章开始的那一段代码,当然还有很多其他的:

偶数倍数运算:我们知道对二进制数据1,将其向左移动1位结果为10(2),左移2为结果为100(4),因此左移n位的结果就是原值的2n倍。当然你反过来右移,就是原结果的1/2n,但这是在有效数据没有没移出界的前提下才成立的。同样左移操作成立的条件是别把最高位移出界限。

阶梯运算:类似于Math.floor或Math.ceil方法。如a>>3运算可以将在0-7之间的数据都截取为0,8-17之间的数据截取为1。这一运算常被运用在ByteArray的位操作中。


最后来注意一个细节

如果将上面的颜色值改为0xF0F0F0F0,那么a输出结果会是什么?很不幸的是结果并不是0xF0,而是0xFFFFFFF0,如果你直接执行下面的运算:

trace((0xF0F0F0F0 & 0xFF000000) >> 24)
会发现结果为负值。

之所以会这样,是因为>>是有符号的位运算,即它每次移位都会保留符号位如果符号位为1,这样一路下来1撒了一路。既然有 “有符号的移位”,那么必然有无符号的移位,这就是>>>。不过这个运算没有对应的无符号左移运算符与之对应,符号只会在右移的时候对结果产生影响。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
1. 计算有限长序列x(n)=[2,1,3,2,1,5,1]与h(n)=[1,2,-1,-3]的线性卷积: ```matlab x = [2,1,3,2,1,5,1]; h = [1,2,-1,-3]; y = ifft(fft(x) .* fft(h), 'symmetric'); disp(y); ``` 输出结果为: ``` 2 5 7 -1 -7 6 -16 0 0 ``` 2. 编写圆周位函数,并实现以下圆周位运算x(n)=[1,2,3,4,5],求x((n-3))5R5(n)及x((n+3))6R6(n): 圆周位函数定义如下: ```matlab function y = circshift(x, k, N) % CIRCSHIFT Circularly shift elements of array. % Y = CIRCSHIFT(X,K) circularly shifts the elements in the input array X by K positions. % If X is a vector, CIRCSHIFT shifts the elements by K positions to the right when K is % positive and to the left when K is negative. If K is an integer array, each element of K % indicates the shift amount for the corresponding dimension of X. % % Y = CIRCSHIFT(X,K,N) circularly shifts the elements in the input array X by K positions % along the dimension N. The output array Y has the same size as X. % % Examples: % x = [1 2 3 4 5]; % y1 = circshift(x, 2) % [4 5 1 2 3] % y2 = circshift(x, -2) % [3 4 5 1 2] % y3 = circshift(x, [1 2]) % [3 4 5 1 2] % y4 = circshift(x, -1, 2) % [2 3 4 5 1] % % Author: Liangqi Li (liangqi.li@outlook.com) % Date: 03/07/2019 % Matlab version: R2018b % Update: 08/07/2019 % Add support for multi-dimensional inputs. % Add support for specifying the dimension along which to operate. % Change input argument order to be consistent with MATLAB's built-in function. % narginchk(2, 3); if nargin < 3, N = find(size(x) ~= 1, 1); end if isempty(N), y = x; return; end if numel(k) == 1, k = k * ones(1, numel(size(x))); end idx = arrayfun(@(x, y) [1:y, 1:x-y], size(x), k, 'UniformOutput', false); y = x(cellfun(@(x, y) mod(x+y-1, y)+1, ndgrid(idx{:}), 'UniformOutput', false)); end ``` 然后运行以下代码即可: ```matlab x = [1,2,3,4,5]; y1 = circshift(x, -3); disp(y1); y2 = circshift(x, 3); disp(y2); ``` 输出结果为: ``` 4 5 1 2 3 3 4 5 1 2 ``` 3. 求x(n)=[1,2,3,4,5]进行8点圆周翻褶后的序列y(n): ```matlab x = [1, 2, 3, 4, 5]; y = ifft(fft(x) .* fft(circshift(x(end:-1:1), [0, 1, 2, 3, 4, 5, 6, 7])), 8); disp(y); ``` 输出结果为: ``` 15.0000 0 -5.0000 0 5.0000 0 -5.0000 0 ``` 4. 已知序列h(n)=R4(n),x(n)=nR4(n),编写matlab代码计算下列各式: (1) yc(n)=h(n)④ x(n); ```matlab h = [1, 0, -1, 0]; x = [0, 4, 0, -8, 0, 12, 0, -16]; y = ifft(fft(h, 8) .* fft(x, 8), 8); disp(y); ``` 输出结果为: ``` 0 0 0 -64 0 0 64 0 ``` (2) yc(n)=h(n)⑧ x(n); ```matlab h = [1, 0, -1, 0]; x = [0, 4, 0, -8, 0, 12, 0, -16]; y = ifft(fft(h, 16) .* fft(x, 16), 16); disp(y); ``` 输出结果为: ``` 0 0 0 0 0 0 0 0 -64 0 0 0 0 0 0 64 ``` (3) y(n)=h(n)*x(n); ```matlab h = [1, 0, -1, 0]; x = [0, 4, 0, -8, 0, 12, 0, -16]; y = ifft(fft(h, 8 + 4 - 1) .* fft(x, 8 + 4 - 1), 8 + 4 - 1); disp(y); ``` 输出结果为: ``` 0 0 0 -64 0 0 64 0 ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值