01/10/2018, 08:21

Pointer C. p++ và p>>=1;

Ai giải thích giúp e khi là khai báo 1 con trỏ : int *p;
rồi thực hiện : p++; và p>>=1; thì 2 thao tác này có nghĩa như nhau k ạ ? Nó có tác dụng chi tiết như nào ạ?

Nguyễn Xuân Phúc viết 10:23 ngày 01/10/2018

p >>= 1 là lệnh ghép của p = p >> 1, tức là đem p dịch phải 1 bit.
còn ++ là gì thì không cần phải nói rồi nhé

Nguyen Trong Dung viết 10:34 ngày 01/10/2018

vậy a có thể giải thích cho e code này hoạt động ntn k ạ ?

Trần Hoàn viết 10:25 ngày 01/10/2018

p >>= 1 tương đương với p = p >> 1
Cũng giống như p += 1 chính là p = p + 1, hay như các toán tử gán -=, *=, /=

Còn p++ thì nó hơi phức tạp hơn:
Mình không biết override operator trong C nên mình dùng thuật toán diễn tả hàm nhé:

int CongCong(int Input)
{
    int Output = Input;
    Input += 1; //Thay đổi biến đầu vào, tức là Input++ tương đương một hàm biến đổi Input
    return Output;
}

Giả sử có int x = 2. Nếu bạn chạy lệnh x++ thì ta có x == (int) 3. Tuy nhiên nếu bạn chạy lệnh int y = x++ thì ta sẽ có y == (int) 2x == (int) 3

Nguyễn Xuân Phúc viết 10:36 ngày 01/10/2018

thì như cái tên của hàm, in dãy bit của 1 biến float. Nhưng code này nó code tào lao rồi =)))

viết 10:35 ngày 01/10/2018

code bị ngược chỗ *temp >= 0 chứ in ra được đó

#include  <stdio.h>

void nhiphan(float n)
{
    int *temp = (int*)&n;
    printf("%x\n", *temp);
    for (int i = 0; i < sizeof(n)*8; ++i, (*temp)<<=1)
    {
        printf("%d", *temp < 0);
        if (i%4 == 3) printf(".");
        if (!i) printf("|");
        if (i == 8) printf("|");
    }
    printf("\n");
}

int main(void)
{
    nhiphan(1.0f);
    nhiphan(1.0f / 3);
}

in ra

3f800000
0|011.1111.1|000.0000.0000.0000.0000.0000.
3eaaaaab
0|011.1110.1|010.1010.1010.1010.1010.1011.

“ngon lành” mà.

Wiki:

3eaa aaab = 0 01111101 01010101010101010101011 ≈ 1/3

để biết bit đầu là 1 hay 0 bằng cách cast về int rồi so sánh < 0 là số âm tức bit đầu là bit 1, rồi cứ thế dịch bit trái từ từ hết 32 bit. Có nhiều cái nguy hiểm nhưng ko sao vì đây là C nổi tiếng nguy hiểm mà

Tao Không Ngu. viết 10:21 ngày 01/10/2018

Hi Nguyen Trong Dung.
Cái lõi của hàm này có 2 điểm.
1 Ép kiểu vung nhớ để chuyển vùng nhớ float thành 1 vùng nhớ nguyên để co thể thực hiện phép dịch bit trên đó.
2 Dùng bit dấu để xác đinh in ra là 1 hay 0 khi dich dần các bit.

rogp10 viết 10:25 ngày 01/10/2018

Thực ra nếu đã chơi bitmask thì người ta xài unsigned thôi chẳng qua là do dịch trái nên ko bị dính chưởng. Nhưng bài này xài signed lại nhanh, phải bookmark.

Còn nữa là cái này là đọc dạng IEEE chứ ko phải đổi số gì gì đâu.

p/s: câu đổi kiểu đấy C99 cho undefined rồi. Làm đúng thì phải ntn. http://stackoverflow.com/questions/11638091/getting-the-ieee-single-precision-bits-for-a-float

Bài liên quan
0