voidポインタとは?実行結果について知りたい

このQ&Aのポイント
  • mac osx環境でのvoidポインタの使い方について教えてください。
  • あるサンプルコードを実行した結果が予想外だったので、その原因を教えてください。
  • 実行結果とdの値について、環境の影響かどうか教えてください。
回答を見る
  • ベストアンサー

voidポインタ

教えて頂けますか? 環境は mac osx です。 とあるページのサンプルコード #include <stdio.h> void outString(void *); int main() { int i = 65 ; double d = 10.101; outString(&i); outString(&d); outString("Kitty on your lap"); return 0; } void outString(void *text) { char *str = (char *)text; printf("%s\n" , str); } を実行した次のように表示されました A \301ʡE\2663$@\234\367\377\277A Kitty on your lap 二行目はどういう事になっているのでしょう? ちなみに d = 65.0; で実行しましたが A とは表示されませんでした。 自分の環境のせいでしょうか? よろしくお願いします

質問者が選んだベストアンサー

  • ベストアンサー
  • nda23
  • ベストアンサー率54% (777/1415)
回答No.3

printfに対して、"%s"を指示したので、パラメータは文字列への ポインタであると解釈します。文字列はnull(0x00)を終端とする というルールがあるので、ポインタの位置から、nullまでの文字列を 標準出力に出力しました。 "Kitty on your lap"は実際には"Kitty on your lap"+"\x00"になって います。 int i=65; は4バイトの領域に0x41、0x00、0x00、0x00となっています。 つまり、"A"+"\x00"+"\x00"+"\x00"です。だから"A"と表示されます。 doubleは8バイトの領域で、53ビットの仮数(1ビットは仮想)、11ビット の指数、1ビットの符号から成り立っています。10.101をバイト列に すると、"\xC1"+"\xCA"+"\xA1"+"\x45"+"\xB6"+"\x33"+"\x24"+"\x40" となります。これがどんな文字列になるかは・・・ですね。因みに65は "\x00"+"\x00"+"\x00"+"\x00"+"\x00"+"\x40"+"\x50"+"\x40"です。 これも"A"でないことは御理解願えると思います。 voidポインタはチェックがウルサクなったため出てきたものです。 ポインタやそれが指し示す先のデータ内容まで熟知していないならば 使用すべきではありません。

psychesine
質問者

お礼

ありがとうございます 理解できました

その他の回答 (2)

  • php504
  • ベストアンサー率42% (926/2160)
回答No.2

そのとあるページに解説は書いてないでしょうか 何を言いたいサンプルなのかが不明ですね 間違ったプログラムと言いたいのだとは思いますが。

  • black2005
  • ベストアンサー率32% (1968/6046)
回答No.1

ポインタの理解が出来ていません。 また”文字列の最後尾はnull”というルールも理解できていないようです。 intやdoubleの変数に値をセットして、そのポインタを文字列の先頭ポインタとして扱い、正しく動作するはずがありません。 C言語の基礎から勉強する必要があると思います。

関連するQ&A

  • void型ポインタについて

    -------------------------------- #include<stdio.h> void uni_disp(void *p,int typ); int main() { int idt=123456; double ddt=56.789; char ss[]="abcdef"; uni_disp(&idt,'I'); uni_disp(&ddt,'D'); uni_disp(ss,'S'); uni_disp("STRING",'S'); return 0; } void uni_disp(void *p,int typ) { if(typ=='I'){ printf("%d\n",*(int *)p); } else if(typ=='D'){ printf("%f\n",*(double *)p); } else if(typ=='S'){ printf("%s\n",(char *)p); } } ----------------------------------- 以上のプログラム等で、void型ポインタをint型ポインタ、double型ポインタとみなす場合の、「*(int *)p」や「*(double *)p」の表記がどういう仕組みになっているか分かりません。 「*(int)p」などはエラーが出るのですが、やはり表記の意味を理解していないため何故か分かりません。 「*(int *)p」などの表記を分解して教えていただけると嬉しいです。

  • ポインタについて

    下記<コード1>ではエラーが出ないのに、 <コード2>のように変更すると、 ”error C2105: '++' には左辺値が必要です。” とエラーが出ます。 どうしてなのか教えて下さい。 <コード1> char *str_copy(char *d , const char *s){ char *t=s2; while(*d++=*s++) ; return (t); } int main(void) { char s1[128]="ABCD"; char s2[128]="EFGH"; str_copy(s2,s1); <コード2> int main(void) { char s1[128]="ABCD"; char s2[128]="EFGH"; // str_copy(s2,s1); while(*s2++=*s1++) ;

  • 文字列とポインタの問題です。

    #include<stdio.h> int f(char *s); int main(void){ char*str="nasida Institute of Technology"; int i; i=f(str); printf("%s:%d\n",str,i); return 0; } int f(char *s) { int j=0; while(*s!='\0'){ if(*s=='t'){ j++; } s++; } return j; } このプログラムの答えが3になるんですが、if文のとこの動作がよく分からないので、よろしくお願いします。

  • ポインタについての質問です。

    write関数を使用して文字の表示を行おうと思っています。 int main(void){ char *str0; char a,b,c; str0 = &a; a = '1'; str0++; str0 = &b; b = '2'; str0++; str0 = &c; c = '3'; write(fd,str0,3);//(1) write(fd,"help",4);//(2) str0--; str0--; write(fd,str0,3);//(3) return 0; } 上記プログラムを実行させた結果 (1)321 (2)help (3)出力なし となりました。 (1)ではアドレスの大きい方から出力されているのに対し、(2)ではplehにはならず、helpの順番に出力されています。 また、(3)では出力なしとなってしまいましたがなぜ'1'が出力されないのでしょうか。 それぞれどのような動作を行っているのでしょうか。

  • void **(char や intのアドレス混在)について

    printf("%d",voidd[0]);にてほしい値が表示されません。 どうすればいいですか? よろしくお願いします。 #include<stdio.h> int main() { /* Calc.StringExpressionGet("1+((2+34)*2-111*77)*5-67*8/90"); Calc.StringExpressionResolve(); Calc.Print(); */ int num[3]; num[0]=111; num[1]=222; num[2]=333; char str[4]="ABC"; void **voidd; voidd=new void*[6]; voidd[0]=(void *)&num[0]; voidd[1]=(void *)&str[0]; voidd[2]=(void *)&num[1]; voidd[3]=(void *)&str[1]; voidd[4]=(void *)&num[2]; voidd[5]=(void *)&str[2]; printf("%d",voidd[0]); getchar(); return 0; }

  • ポインタ配列

    ポインタ配列によるひとつのプログラムを組もうと思っています。 で、以下のようなプログラムを作ってみました。 1:#include<stdio.h> 2:#define NUM 5 3:main(void){ 4: char *str[NUM]; 5: int i; 6: for(i=0;i<NUM;i++){ 7: printf("string --->"); 8: scanf("%s",str[i]); 9: } 10: for(i=0;i<NUM;i++){ 11: printf("str[%d] --> %c\n",i,str[i]); 12: } 13:} これなのですが、8行目のscanf文でコンパイルエラーではなく、実行エラーが出ます。どのようにすれば動くようになるのでしょうか? 入力する文字は、9文字以下を想定しています。

  • 文字列 数 変換

    数字列を数に変換できなかった男です。 以下はコンパイルエラー patn.c: In function 'input': patn.c:9:3: warning: function returns address of local variable [-Wreturn-local- addr] return (str); ^ 以下は実行後、 数を入力してください。 123.456 ・・,( 0.000000 0 0 以下は書いたプログラムです。 #include<stdio.h> #include<stdlib.h> char *input(void){ char str[100]; printf("数を入力してください。\n"); scanf("%s",str); return (str); } int main(void){ char *a; double d; int i; long l; a=input(); printf("%s\n",a); d=atof(a); i=atoi(a); l=atol(a); printf("%f %d %ld",d,i,l); return(0); } 関数input()にchar *str2; str2=str; return(str2);としても、実行後の表示はおかしいです。 123.456 123 123.456と表示したいです。御指摘お願いします。

  • C言語の、ポインターの問題を教えて下さい

    C言語の、ポインターを使って大文字と小文字を入れ替えるプログラムを教えて下さい。 作ったのですが、うまくいかず困っています。 分かる方、訂正してください。 よろしくお願いいたします。 #include<stdio.h> void reverse(char *str) { int i; for(i=0;str[i]!='\0';i++) { if(str[i]>=0x61) {str[i]-0x20;} if(0x40<str[i]<0x5B) {str[i]+0x20;} } return(str); } int main(void) { int num; char *str="AddsssEEEEwwwJojoHoih"; printf("Before reverse %s \n",str) str=reverse(str); printf("After reverse %s \n",str); return 0; }

  • ポインタで分からないことがあります。

    つい最近C言語の勉強を始め、現在ポインタの勉強をしています。 過去の質問を検索したり、サイトを見てみましたが、一人の力では解決できませんでしたので質問させていただきます。 ポインタのプログラムで、下記のプログラムについて分からないことがありました。 ――――――――――――――――――――――――――――――――― #include <stdio.h> int main (void) { char *str = "abc"; printf ("%s %d %d\n", str, &str, &(*str)); str = "日本語"; printf ("%s %d %d\n", str, &str, &(*str)); return 0; } ――――――――――――――――――――――――――――――――― このプログラムで、「char *str = "abc";」の部分でstrには abcのアドレスが入っていると思っていたのですが、 1度目の「printf ("%s %d %d\n", str, &str, &(*str));」で、 結果が「abc 1245064 4235560」となっているのを見ると 私の見解は間違っている気がします。 「char *str = "abc";」の部分では一体なにが行われているのでしょうか? また、このプログラムをコンパイルして実行した結果が、 abc 1245064 4235560 日本語 1245064 4235574 となったのですが、なぜstrのアドレスは同じなのに、 &(*str)のアドレスは異なるのでしょうか? 質問をまとめますと、以下の2つです。 1.「char *str = "abc";」の部分では一体なにが行われているのでしょうか? 2.「abc」と「日本語」のstrのアドレスは同じなのに、&(*str)のアドレスは異なるのでしょうか? 初心者ですので言葉の足らない部分があるかもしれませんが、ご教授のほどよろしくおねがいします。

  • ポインタ スペースを数えるプログラム

    入力した文章のスペースを数えるプログラムを作ってみました. ポインタをまだしっかり理解していないのですが,ポインタを使用 する場合,以下のようなプログラムで正しいですか? (オーバーフローなどについては対処していません.) #include<stdio.h> int main(void) { char str[80],*p; int i,count=0; gets(str); p=str; for(i=0;i<80;i++) { if(p[i]==' ') { count++; } } printf("%d",count); return 0; }

専門家に質問してみよう