1. 程式人生 > 其它 >做程式設計師是真的因為喜歡嗎?還是因為收入比較高?

做程式設計師是真的因為喜歡嗎?還是因為收入比較高?

目錄

目錄

1. question1

思路

由於是按補碼形式儲存,最高位為1 其他位全為0 ,直接將1 左移31 位即可得到

程式碼

int tmin(void) {

  	return 1<<31;
}

測試截圖

./dlc -e bits.c:

btest:

2. question2

思路

Tmax 的補碼錶示為最高位為0 其他位全為10x7fffffff ,可得Tmax+1=Tmin(0x80000000)

,同時

若 x= 0111 1111 1111 1111 1111 1111 1111 1111

x+1= 1000 0000 0000 0000 0000 0000 0000 0000

!(x^(x+1))=1

!(x+1)=0 !!(x+1)=1

所以當x0x7fffffff 時返回值為1,其餘返回值為0

程式碼

int isTmax(int x) {
  return !((~(x+1)^x))&!!(x+1);
}

測試截圖

./dlc -e bits.c:

btest :

3. question3

思路

最重要的是構造一個32 位並且奇數位為1 的數,若有一個數為a 其奇數位全為1 如果存在x 使得x&a==a 那麼x 就滿足條件

先構造8 位奇數位為1 的數之後左移與原狀態取或運算即可得到滿足條件的16 位數,以此類推變可得到32 位奇數位為1 的數,之後用x&a 若返回結果為x 則說明x 滿足條件,隨後和自身異或得到0 取非得到返回值1 ,執行成功。

程式碼

int allOddBits(int x) {
	int a=0xAA;
	int b=(a<<8)|a;
	int c=(b<<16)|b;
	return !((x&c)^(c));
}

測試截圖

./dlc -e bits.c:

btest:

4. question4

思路

函式理解為,當x!=0 時返回y 否則將返回z

,當首先將x 的範圍限制住,可以採用!x 來判斷是否為零

x 等於0 時,x1 最高位為1,其餘位為0-0,此時和y與運算得0 按位取反之後最高位為0 其餘為為1 ,和z 做與運算得到本來z 的值返回即可

x 不等於0x1 全為1,和y 與運算得到y 本身,按位取反之後為0z 相與之後為0 所以最後取和返回y

主要還是通過!x 來縮小x1 的範圍再進行判斷就方便很多

程式碼

int conditional(int x, int y, int z) {
  int x1=!x+~0;
	return (x1&y)+((~x1)&z);
}

測試截圖

./dlc -e bits.c:

bteat:

5. Nuaa_question5

思路

首先提取符號位sign和階碼exp ,情況如下:

若為inf 或者Nanexp==0xff 直接返回自身

若為非規格化數,exp==0 時,直接將尾數左移一位,但是注意恢復原來的符號位

若為規格化數,exp>0&&exp<0xff 直接將階碼加一即可,階碼加一後如果為0xff 就代表浮點數乘二會溢位,返回inf 主以依然要保留原來的符號位,如果不溢位就講符號,階碼,尾數三部分按照格式組合起來即可。

程式碼

unsigned float_twice(unsigned uf) {
	int exp = (uf>>23)&0xff;
	int sign = uf&(1<<31);
	if(exp==255) return uf;
	if(exp==0) return sign|(uf<<1);
	exp+=1;
	if(exp==255) return sign|0x7f800000;
   	return(uf&0x807fffff)|(exp<<23) ;
}

測試截圖

./dlc -e bits.c:

btest:

6. Nuaa_question6

思路

首先和第五題類似通過移位和& 運算取得符號位sign ,階碼exp 和尾數frac 實際上的階碼等於exp-127 ,關與於階碼:

exp<127 實際階碼小於零,浮點數的絕對值小於1,直接轉換為整數的零即可

exp>157 實際階碼大於30 ,此時浮點數的絕對值最小為2^31 如果是正數就會發生溢位返回0x80000000u ,但是如果為負數,-2^31 轉為整數並不溢位,結果為0x80000000u ,其他負數全部溢位,所以綜上所述返回值全部為0x80000000u

exp>=127&&exp<=150 時實際階碼大於等於0小於等於23,單獨提取出來的尾數相當於階碼為23 ,所以整數右移(127+23-exp) 位即可

exp>150&&exp<=157 時實際階碼大於等於23 小於等於30 相當於整體左移(exp-127-23) 即可

程式碼

int float_f2i(unsigned uf) {
	int exp,sign,frac,ans;
	exp=(uf>>23)&0xff;
    sign=(uf>>31)&1;
	frac=(uf&0x7fffff)|0x800000;
	if(exp<127)
		return 0;
	if(exp>157)
		return 0x80000000u;
	if(exp<150)
		ans=frac>>(150-exp);
	else
		ans=frac<<(exp-150);
	if(!sign)
		return ans;
	else
		return ((~ans)+1);
}

測試截圖

./dlc -e bits.c:

btest:

7. 最終結果

./driver.pl截圖:

挑戰教授截圖(161920214)

8. 備註