
wParamは、unsigned int型で、仮想キーコードを、格納してますよね。
wsprintf()内で(TCHAR)キャストしてますが、
これは、変数strの型がTCHAR型なので(wParamは、unsigned intなので型をあわせるために)やっているんですか?
(TCHAR)キャストしないとエラーになりますか?教えてください。
HDC hdc;
TCHAR str[255];
swich(umsg){
case WM_CHAR:
wsprintf( str, TEXT("%c"), (TCHAR)wPara );
hdc = GetDC(hwnd);
TextOut(hdc, 0, 0, str, lstrlen(str));
return0
}
No.3ベストアンサー
- 回答日時:
そもそも8ビットに収まらない文字を扱うのであれば、キャストしようがしまいが駄目なので、8ビット以内の文字に限定して回答します。
可変個引数に渡した実引数(今回の場合は(TCHAR)wParaがそうです)は、既定の実引数拡張という型変換が行われます。すなわち、実引数がintまたはunsigned int以下の場合には、intまたはunsigned intに暗黙的に型変換されるわけです。
処理系がわからないので推測の域を出ませんが、TCHARはおそらく、char, unsigned char, unsigned short, wchar_t(基本となる型は多分unsigned short)のどれかに定義されていると思います。であれば、いずれもintまたはunsigned int以下ですので、既定の実引数拡張の対象となります。
既定の実引数拡張の対象となるのであれば、明示的なキャストがあってもなくても動作には変わりありません。元々がかなり環境に依存したコードですので、必要以上に移植性を考慮する必要もないでしょうし。
ちなみに、既定の実引数拡張が行われる限り、リトルエンディアンかどうかは全く関係ありません。
回答ありがとうございます。
私は、初心者でして難しそうですが、キャストの必要はないようですね。
どうも詳しく教えていただきありがとうございました。
No.4
- 回答日時:
回答への補足で恐縮ですが。
>・私が知る限りでは『wsprintf』関数で『%c』を指定した場合、それに対応する引数を
> 『wsprintf』自身が内部で(char)型に勝手にキャストして処理します。
これは明らかな間違いです。
wsprintf()(或いはその内部で呼び出した関数)はintとして渡された引き数を
charと解釈するかもしれませんがキャストするわけではありません。
#例えば%cに対応する引き数としてポインタや実数値を渡したら……言うまでもありませんね。
初心者がプログラミングする上で意識しなければいけないことではありませんが、
回答をする立場でしたらご承知あるべきと思いますので老婆心ながら。
No.2
- 回答日時:
一応型キャストしておいた方がwsprintfにやさしいと思います。
少し使い得ない方法ですがこちらのプログラムをテストしてみてください。
======
#include <stdio.h>
#include <windows.h>
int main()
{
WPARAM wp = L'あ';
char str[64];
wsprintf (str, "%d/%d", (TCHAR)wp, wp);
puts(str);
return 0;
}
=========
きちんと型キャストした場合は型にあわせた数値が送られています。
数値が違うのに何故きちんと動いてるように見えるのか。
今回は奇跡的にtata120様のコンピュータがこのバグを防ぐ環境にあったからといえます(奇跡というと大げさかも知れませんが)
例を挙げますが[]を1バイトの塊だと思ってください。
wParaが'a'(=0x61)だとすると、WPARAMは4バイトなので[00][00][00][61]となります。
蛇足ですが(TCHAR)wParaとすると上位3バイトを切捨てて[61]を返します。
ここで問題なのは%cですが、こちらは対象の先頭から1バイトを必要とします。
つまりwParaの先頭から1バイトです。
しかし上記を見ても分かるとおりwParaの先頭は[00]です。
やはり不思議としか言えません。
ですがtata120様のコンピュータがリトルエンディアンである事が鍵となります。
リトルエンディアンのコンピュータは2バイト以上の変数を尻を先頭から置きます。
つまりwParaは[00][00][00][61]という値でありながらメモリ上では[61][00][00][00]と置かれているという事です。
なので%cで取得した時にきちんとした値が得られたように見えた訳です。
Windowsが乗っかっているPCは大抵がリトルエンディアンなので問題ないと思いますが、一応キャストしてあげたほうがいいと思います。
tata120様には不必要な説明になったかも知れませんが、一応書いて見ました。
分かりづらいところもあると思いますが、その点は申し訳ありません。
回答ありがとうございます!
私は、初心者であいまいな知識が多く、解説がいろいろ参考にになりました。
どうもありがとうございました!
No.1
- 回答日時:
★どうなんでしょうね?
・私が知る限りでは『wsprintf』関数で『%c』を指定した場合、それに対応する引数を
『wsprintf』自身が内部で(char)型に勝手にキャストして処理します。
・ですから、自分で『wsprintf』の引数『wPara』をキャストする必要性はないと思います。
・何処かのサイトで見つけた『小技』で書かれていたんですか…。
最後に:
・(TCHAR)型に、キャストしなくても良いです。
・エラーにはなりませんよ。→動作も異常にはなりません。
・以上。おわり。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# 宣言する関数の形が決まっている状態で、 str1とstr2の文字列をこの順に引っ付けてstrに保存し 2 2022/05/30 18:21
- C言語・C++・C# c言語配列の結合についてです。 なぜうまくいかないのでしょうか。 #include <stdio.h 4 2022/05/30 22:42
- C言語・C++・C# c言語 プログラムのエラー 1 2023/02/11 20:31
- C言語・C++・C# プログラミングの授業の課題です 1 2023/01/17 22:15
- C言語・C++・C# str[j++]の意味 2 2022/08/30 16:20
- C言語・C++・C# sprintf()の使い方について 1 2022/08/17 16:16
- C言語・C++・C# C#テキストボックスの文字を配列にいれてその後表示する 4 2022/07/17 04:47
- その他(プログラミング・Web制作) Pythonでエクセルファイルの列を指定してスライス 3 2022/08/28 17:35
- C言語・C++・C# C# 浮動小数の数値文字列化 1 2022/04/18 15:15
- C言語・C++・C# C言語 共用体について コマンドライン引数で値を2つ入力したときに、argv[2]の値をUNI u1 4 2022/04/25 20:34
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
fgetsなどのときのstdinのバッ...
-
CStringをwchar_tに変換したい
-
間接参照のレベルが異なっています
-
テキストデータをそのままバイ...
-
文字列から空白を取り除きたい...
-
c言語でユーザ関数を利用して入...
-
型変換
-
charからLPTSTRへの変換方法
-
配列をnビットシフトする
-
atoi( ) の反対をやりたい
-
C言語のfor文です。 繰り返しの...
-
2曲同時再生するにはどうした...
-
C言語、リダイレクト
-
str系関数を使わずに二つの文字...
-
TCHAR文字列?の特定部分の数字...
-
recvfrom関数の戻り値がおかし...
-
文字コードチェックについて
-
char型からのバイト数取得
-
C言語のポインターで詰まっている
-
C言語の入力した文字を反転させ...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
fgetsなどのときのstdinのバッ...
-
文字列から空白を取り除きたい...
-
間接参照のレベルが異なっています
-
C言語のfor文です。 繰り返しの...
-
CStringをwchar_tに変換したい
-
テキストデータをそのままバイ...
-
charからLPTSTRへの変換方法
-
atoi( ) の反対をやりたい
-
charでの計算?
-
配列をnビットシフトする
-
c++ 文字列を入力して、一文字...
-
'const char *' 型は 'char *' ...
-
c言語でユーザ関数を利用して入...
-
干支のプログラム
-
switch文で文字を比較すること...
-
char型からのバイト数取得
-
ネットワークにつながっている...
-
getchar()を int でとる理由...
-
間接操作のレベルとは
-
str系関数を使わずに二つの文字...
おすすめ情報