[英]Using printf to print float pointer using %d
當我運行此代碼時,它會在第一個 printf 中打印 a 的地址,在第二個 printf 中打印 a 的值。
#include <stdio.h>
int main()
{
float a=7.999999;
float *b,*c;
b=&a;
c=b;
printf ( "\n%u %u %u", &a, b, c );
printf ("\n%f %f %f %f",a,*( &a ),*b,*c );
}
但是當我像這樣在第二個 printf 中將 %f 更改為 %d 時。
#include <stdio.h>
int main()
{
float a=7.999999;
float *b,*c;
b=&a;
c=b;
printf ( "\n%u %u %u", &a, b, c );
printf ("\n%d %d %d %d",a,*( &a ),*b,*c );
}
它在第二個 printf 中打印隨機值,請解釋原因。 浮點指針應該使用 %f 打印,但為什么不能使用 %d。
為什么要使用 %f 打印浮點指針,但為什么不能使用 %d 打印。
轉換規范( %d
或%f
)告訴printf
兩件事:
首先,現代處理器通常為 integer 數據和浮點數據提供不同的寄存器。 Due to this and related reasons, the rules for how arguments are passed to subroutines (part of the Application Binary Interface for a computing environment) typically say that the first few integer arguments are passed in certain integer registers and the first few floating-point arguments在浮點寄存器中傳遞。 (在最初的幾個 arguments 之后,通常在硬件堆棧上傳遞額外的 arguments。)
因此,當您告訴printf
使用%d
轉換數字但將其傳遞給浮點參數時, printf
可能會從某些 integer 寄存器中獲取值,但浮點參數不存在。 它在一些浮點寄存器中。 然后printf
打印出錯誤的值。
第二點,整數和浮點數的值以不同的位編碼。 %d
告訴printf
將這些位解釋為二進制數(以及一些表示負數的方案,最常見的是二進制補碼)。 %f
告訴printf
將這些位解釋為浮點格式的數字編碼。 此外,由於 C 歷史記錄,將 arguments float
到printf
作為double
傳遞。 最常見的double
精度浮點格式使用 1 位作為符號,11 位用於 2 的指數,52 位用於有效數部分。 (在普通科學記數法中,對於數字 -3.74•10 13 ,- 是符號,13 是指數,3.74 是有效數。)如果printf
確實采用了編碼double
精度的部分或全部位並根據到%d
,它將打印一個與浮點數的值非常不同的數字(除非非常罕見的巧合)。
另請注意,在printf ("\n%d %d %d %d",a,*( &a ),*b,*c );
. a
、 *( &a )
、 *b
和*c
都是a
。
在printf ( "\n%u %u %u", &a, b, c );
,指針打印不正確。 正確的代碼是printf("%p %p %p\n", (void *) &a, (void *) b, (void *) c);
. 在這里,我做了三個更改:
%p
是打印指針的正確轉換規范。 有時使用%u
打印會打印相同的值(盡管是十進制而不是十六進制),但是,如果發生這種情況,那只是因為指針在與unsigned int
相同的位置傳遞,它們的大小相同,並且錯誤確實不要與編譯器優化發生沖突。void *
以進行打印。 這確保它們在通過時采用通用形式,適用於%p
。\n
移動到字符串的末尾而不是開頭。 C 設計用於將換行符放在行尾而不是開頭,因為當有換行符時,它會立即將 output 發送到交互式設備,而不是將其保存在緩沖區中。 %d
要求參數是一個int
值。 (這就是你得到垃圾的原因)
如果要將浮點數打印為整數,請改用%0.0f
。 這將打印四舍五入到最接近的 integer 的值,並且沒有小數(我現在不確定這是否打印小數點,但如果是,請嘗試替代%0.0g
)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.