C/C++小心者スレッドP ..
[2ch|▼Menu]
856:デフォルトの名無しさん
10/03/07 21:01:36
>>854
> C/C++にそんな型は存在しません。

小心者スレッドなんだからまあ良いではないか。

>>853
どんなコードでコピーしたの?
そもそもBYTE型に256以上の値は入らないし、DWORDだったら4バイトだよね。


857:854
10/03/07 21:21:41
>>856
> 小心者スレッドなんだからまあ良いではないか。
一応 小心者 向けに多少はしたつもりだったんだが、
俺の言い方はやっぱまだ厳しかったか。
スマン


858:デフォルトの名無しさん
10/03/07 21:40:13
コード見たほうが早いなたぶん

859:853
10/03/08 00:08:15
>>854-858
ありがとうございます、memcpy使えば良かったですね、
他の事に気がいっててそんな事にも気付かなかった、 orz
あとDWORDは4バイトだったんですね、ご指摘ありがとうございました。

860:デフォルトの名無しさん
10/03/08 10:55:08
配列ならポインタを強引にキャストするだけでもよくね
メモリ上の配置の把握が必要だけど、memcpyするにしてもそれは必要だし

861:デフォルトの名無しさん
10/03/08 12:43:22
>>860
エイリアシングルールというものがあってだな。
URLリンク(www.radiumsoftware.com)

862:デフォルトの名無しさん
10/03/09 03:46:00
8bit変数配列→32bit変数、ってだけならunion作れ
8bit変数配列→32bit変数配列、とかならどうしたもんだか

863:デフォルトの名無しさん
10/03/12 22:33:09
unionつかったらエンディアンの問題はどうするの?

864:デフォルトの名無しさん
10/03/12 23:04:11
2倍あるいは1/2倍していたところをビットシフトに書き換えたら、若干遅くなりました。
同じかそれ以上の速さになることはあると思っていましたが、遅くなるとはどういうことなんでしょうか??
CPUには乗算や除算のほうが高速に行える回路が付いてるんでしょうか??

865:デフォルトの名無しさん
10/03/12 23:45:00
>>864
推測ではどういう風にでも考えられるので
コンパイラにアセンブリを吐き出させてみればどうでしょう

866:864
10/03/13 01:38:25
>>865
ありがとうございます。
アセンブラは読めませんが、がんばって解読してみます。

867:デフォルトの名無しさん
10/03/13 10:20:26
>>863
気になるなら#ifdefするなり効率落として変換関数書くなりすればいいんじゃね
綺麗で効率いい方法は知らん

868:デフォルトの名無しさん
10/03/13 10:40:47
絶対にWindowsでしか使わないのにクロスプラットフォームで書きたくなる病とかあるよな

869:デフォルトの名無しさん
10/03/13 12:11:15
>>868
できる限り標準に準拠するのは正しい態度だと俺は思うよ

* ずっとWindowsだけの仕事をするとは限らん
* 元々Windowsだけのつもりでもコードの一部流用とかすることがありうる


870:デフォルトの名無しさん
10/03/13 13:45:37
8bit配列→32bitなんていう処理についての話からの流れだからなぁ
汚くする理由の無い部分は綺麗に書くのが当然だが、エンディアン絡みの処理を
すっきり綺麗に効率良く、って訳には行かんだろ現状

871:デフォルトの名無しさん
10/03/13 14:15:49
>>869
* 言語標準に準拠しつつクロスプラットフォームではないコードは極めて一般的
* OS標準に準拠しつつクロスプラットフォームでないコードは言うまでもなく一般的
* そもそも「絶対に」という前提の話

まず、クロスプラットフォームと規格準拠は全くの別物。前者の需要は極めて稀。
Windowsアプリを書く時にクロスプラットフォームにしようとするのは、かなり病的
にならないと困難だと思うぞ。犠牲も大きいし。

872:デフォルトの名無しさん
10/03/13 15:25:22
Qtとかの外部ライブラリを使えば
クロスプラットフォームでも楽に書けるぞ。


873:デフォルトの名無しさん
10/03/13 21:57:02
>>871
プラットフォーム依存性が必要無いところは敢えて依存性持たせない方が
良いと俺は思うけどな
必要もなくプラットフォーム依存してるコードもよくあるが
元々絶対に流用しないつもりでも一部切り貼りって結構あると思うぞ

874:デフォルトの名無しさん
10/03/13 22:02:26
forループのインデクスすらDWORD使うサンプルとかあるからな

875:デフォルトの名無しさん
10/03/14 07:46:33
程度問題だな。病気レベルの無駄なことはやらない方がいい。無理せずに依存無く
書けるなら当然その方がいい。
Qtは微妙だろ。必要も無しにあれを選ぶ理由は無いと思う。

876:872
10/03/14 10:36:59
別にQtじゃなくても、とにかくクロスプラットフォームな外部ライブラリなら
俺の言いたいことは伝わると思うんで、適当に読み替えてください。

877:デフォルトの名無しさん
10/03/14 15:01:47
クロスプラットフォームなフレームワークに乗っかれば
クロスプラットフォームでも楽に書けるぞ。

・・・当たり前だろjk

878:デフォルトの名無しさん
10/03/15 00:23:17
本気で細かいことをしようとするととても楽に書けるなんてもんじゃないから、
普通は細かいことをバッサリ諦めるしか無いのがクロスプラットフォーム

879:デフォルトの名無しさん
10/03/15 00:27:38
まぁGUIに関しては特にそうだよね

880:デフォルトの名無しさん
10/03/15 08:24:51
独自機能は全部諦めることになるしなぁ

881:デフォルトの名無しさん
10/03/15 21:37:14
>>878
細かいこと気にしない方が逆にいいものできたりして…
稀かもしれんが

882:デフォルトの名無しさん
10/03/15 22:23:42
>>881
「逆にいい」は稀かと
あっても無くても関係ない、ならまだそれなりにある話だが

CUIなら割と素直にクロスプラットフォームになりやすいけどな
それでも、元の流れの内容をエンディアン違いにまで対応させようとしたら
あまり綺麗には済まないが

883:デフォルトの名無しさん
10/03/16 21:46:48
CUIでも、実用品でクロスプラットフォームなコードになると大抵はマクロで個別に
ソース分岐させてるけどな。C/C++標準だけで書ける実用品なんて小物だけ。
LinuxとBSD系ですら、パフォーマンスを実用レベルにする為には移植作業が必要に
なったりする訳で。Windowsならなおのこと。

884:デフォルトの名無しさん
10/03/16 21:56:00
標準の範囲ではWindowsでUnicodeファイル名を扱えないし
ディレクトリすら作れないし
バイナリファイルを標準入出力で読み書きできないし
大きなファイルのシークもできない

885:デフォルトの名無しさん
10/03/16 21:57:51
だからクロスプラットフォームなフレームワークに乗っかろうぜ
と言ってるじゃないか。
だれもC/C++標準だけで満足はしないさ。


886:デフォルトの名無しさん
10/03/16 22:03:09
オープンソースだと、単にWindowsのUnicodeファイル名などは
切り捨てているものも多いな

887:デフォルトの名無しさん
10/03/16 22:18:27
そしてパスに空白を含むと落ちるクソアプリができあがると

888:デフォルトの名無しさん
10/03/16 22:24:03
>>887
> そしてパスに空白を含むと落ちるクソアプリができあがると
たまにそういうクソアプリが見つかるけど、
それが原因だったんかい!

889:デフォルトの名無しさん
10/03/17 01:19:44
クロスプラットフォーム向けのフレームワーク使ったところで、問題の本質の
ほとんどは解決しないよな

890:デフォルトの名無しさん
10/03/17 18:28:38
プラットフォーム依存性があるにしろオープンソースでクロスプラットフォー
ムというと firefox, thunderbird, gimp, cygwin とか思いつくけど
これらってクソアプリやへぼアプリの分類なの?

891:デフォルトの名無しさん
10/03/17 18:58:00
cygwinは最近出た1.7まではUnicodeファイル名に対応していなかった
実のところ、Windows専用でも、Unicodeファイル名に対応していないプログラムは
ものすごく多い、特にコンソールアプリケーションではそれが普通

892:デフォルトの名無しさん
10/03/17 19:20:32
>>890
必死に移植作業してマクロで分岐させるんならいくらでもクロスプラットフォームに
なるのは当然だろw

893:デフォルトの名無しさん
10/03/17 22:53:58
>>890
firefox, thunderbird, gimp, cygwin が
クソアプリやへぼアプリだったら
そうじゃないアプリって世の中にほとんどないんじゃないか?


894:デフォルトの名無しさん
10/03/17 23:49:10
クロスプラットフォームなコードでもクソじゃないのはあると言いたいんだろ
だが、あの辺のは「現実に十二分な需要がある」から、仕方なく「多大な手間を掛けて
複雑なコードを書いて」実現してるから、牧歌的な話からは程遠い

895:デフォルトの名無しさん
10/03/18 00:16:50
>>894
> クロスプラットフォームなコードでもクソじゃないのはあると言いたいんだろ

クロスプラットフォームのアプリのほとんどが
クソアプリだってことが言いたいのかい?

896:デフォルトの名無しさん
10/03/18 00:19:05
クソアプリの定義にもよるんじゃないの
例えばlameは最優秀のMP3エンコーダーだが、Unicodeファイル名には対応していない

897:デフォルトの名無しさん
10/03/18 00:31:07
英語限定ならば問題は大分少なくなりそうだな…

898:デフォルトの名無しさん
10/03/18 00:32:40
そうだな
GUIの場合、IMEという難関もあるし

899:デフォルトの名無しさん
10/03/18 11:56:10
>>895
どう見ても真逆の意味にしか読めないが

900:デフォルトの名無しさん
10/03/18 12:05:23
コードは肥大するけどお勉強の為に非依存で書いてみました、でも誰も使いません
けどね、ってのが無駄
自然に非依存なコードになるならそれでいいんだよ(エンディアンなんかは面倒な
ことをしなきゃ非依存にはならんけど)
実需があるなら無理もしなきゃならないし、変態コードが肥大しても許される

901:デフォルトの名無しさん
10/03/18 12:08:51
実装の手間自体もでかいが、テストの手間のほうがより悲惨だな

クロスプラットフォームを本気で考えるのは、プロジェクトが大きくなってからで
いいと思う

902:デフォルトの名無しさん
10/03/18 14:36:18
クロスプラットフォームにするほど
他人が使ってくれるかどうかっていうところがなw

903:デフォルトの名無しさん
10/03/18 18:14:36
>>900
> 自然に非依存なコードになるならそれでいいんだよ(エンディアンなんかは面倒な
> ことをしなきゃ非依存にはならんけど)

素朴な質問だが通常のコーディングでなぜエンディアンを
生で扱わなければいけないの?

904:デフォルトの名無しさん
10/03/18 18:20:57
>>903
誰かがエンディアンを持ち出したからだろ

905:デフォルトの名無しさん
10/03/18 18:21:42
>900ではないが
少なくとも画像や音声など、バイナリデータを弄る場合には必ずエンディアンの問題は
出てくるでしょ

ネットワークプログラミングにおけるntohl()のように、ホストエンディアンを
意識せずに「ホストエンディアンと対象エンディアン(bigないしlittle)を
変換する関数」を複数用意することで、問題を解決できることが多いと思うけど

906:デフォルトの名無しさん
10/03/18 18:35:28
>>905
画像,音声,ネットワークだと生で扱わなくてもライブラリがあるんでは
自分で用意する必要は必ずしも無いはず

907:デフォルトの名無しさん
10/03/18 18:47:09
そもそも>>900を読んで「通常のコーディングでもエンディアンを生で扱わなければ
いけない」とは読み取れないんだが

908:デフォルトの名無しさん
10/03/18 20:41:29
>>906
ま、ライブラリにおんぶにだっこでいい場合はそうだね

ただ、例えばntohl()のようなものはホストエンディアンによってコードを
分ける必要はなくしてくれるが、「ここはネットワークエンディアンに変換する
必要があるのでntohl()を呼ぶ」ような仕事は残るわけだから、
エンディアンを意識しなくてよい、というわけではないよね


909:デフォルトの名無しさん
10/03/18 22:06:47
>>908
それはどういうライブラリ使うかじゃないか?

たとえば画像の時は「必ずエンディアンの問題は出てくる」というが,
magick++ みたいなもの使えば「エンディアンを意識しなくてよい」
という状況だと思うけど違う?

910:デフォルトの名無しさん
10/03/18 22:30:11
>>909
正直議論の意味というか、何にこだわってるのか、何を知りたいのか
全く理解できんのだけど……
magick++を使ったことは無いのでわからんが、まあ、そう言ってしまえば
何だってそうだといえるだろうさ

画像処理で言うと、ファイルフォーマット内のバイトオーダーは
ライブラリによって隠蔽されるケースは多いと思う
が、ライブラリにロードしてもらった32bitラスタ画像のピクセルフォーマットが
ARGBかBGRAか、といったことは、ピクセルを弄る場合には結局必要になるわけだ

911:デフォルトの名無しさん
10/03/18 22:54:34
picture[y][x].a = 〜
みたいに使えるんでないの?
ロードの処理が重くなりそうだが。

912:デフォルトの名無しさん
10/03/18 23:01:06
>>911
一瞬意味が分からなかった、その.aはARGBのAか
まあ、そういう実装は可能だろうね
Cだと
PutPixel(point, a, r, g, b)
のような関数ないしマクロを使うんだろう


913:デフォルトの名無しさん
10/03/18 23:13:43
>>910
画像処理と言ってもライブラリを使える場合もあるから
「必ずエンディアンの問題は出てくる」ということも無いということだよ

magick++ とかを使ってできることをわざわざ車輪を再発明する事もない場合も多いし
具体的にピクセルをどう弄りたいわけ?


914:デフォルトの名無しさん
10/03/19 01:45:40
>>913
ああ、要するに「必ず」は言いすぎだろ、という突っ込みか
確かに言い過ぎたね

915:デフォルトの名無しさん
10/03/19 12:22:01
Windowsでカレントディレクトリを取得する方法を教えてください

916:デフォルトの名無しさん
10/03/19 12:36:42
GetCurrentDirectory()

917:デフォルトの名無しさん
10/03/27 23:45:49
失礼します。
C++を勉強中の初心者です。

ポインタを関数の戻り値する場合は関数内の宣言にstaticをつけなければならないという記述をよく目にするのですが、
以下のようにstaticをつけずにHoge hを宣言しても問題なくプログラムが動き、5が出力されます。どういうことなのでしょうか。

typedef struct{
int k;
} Hoge;

Hoge* func(int a)
{
Hoge h;
h.k = a;
return &h;
}

int main()
{
Hoge* h = func(5);
cout << h->k;
}

918:デフォルトの名無しさん
10/03/27 23:59:25
>>917
Hoge h がスタック上に作られている場合、関数から帰ってきた
直後は問題ない可能性が高いが、もう1回func()を呼んだり
別の関数を呼んだりすると、おかしくなる可能性がある。

919:デフォルトの名無しさん
10/03/28 00:02:59
>>917
動くのはたまたまです
試しに、func(5) のあとに別の関数を呼んでみてください
別の結果になると思います

920:デフォルトの名無しさん
10/03/28 00:16:44
なるほど
たしかにおっしゃるとおりの事態が起きました。
ありがとうございます。

あと実はこのことに直接関わるかはわからないのですが、
別のプログラムにおいて、同じように構造体のポインタを戻り値とする関数をつくって内部の宣言をstatic有りと無しどちらも試したところ、
staticをつけた方はmainを抜けるところで停止してしまいます。
関係があるのかどうかよくわかりませんが、もし心当たりがありましたらお教えいただけると幸いです。

921:デフォルトの名無しさん
10/03/28 00:23:11
>>920
ソースをcodepadに貼れ
言ってる事がよくわからない

922:デフォルトの名無しさん
10/03/28 00:25:57
>>920
そんなことで悩むぐらいならポインタでなく実体を返せばいいと思う

Hoge func(int a)
{
Hoge h;
h.k = a;
return h;
}


923:デフォルトの名無しさん
10/03/28 01:30:09
>>922
構造体の配列を返したかったので・・・

すみませんどうやら別のところで引っかかっていたようで、今解決しました。
どうもお騒がせしましてすみません。

924:デフォルトの名無しさん
10/03/28 03:13:39
つーか根本的に関数側で確保した構造体のポインタを返すのがキモイ
呼び出し側で(空でいいから)構造体を用意して、そのポインタを関数に渡して、
関数側はその渡されたポインタで構造体の中身を加工する、っつーのが普通だし、
そういう設計ならポインタを返す必要も無いしstaticも要らないし、static無しで
ポインタ返しても別に問題無い
何でそうなるかが分からんようだと辛い

925:デフォルトの名無しさん
10/03/28 09:22:50
>>924
関数側で確保した構造体のポインタじゃなくて構造体を返すのもダメ?

926:デフォルトの名無しさん
10/03/28 10:41:34
>>924-925
(コピーのオーバーヘッドはおいといて)1個の構造体や、固定長の構造体配列ならそれでもいいんじゃないの?
任意個数の配列をポインタではなく値で返す方法ってのを俺は知らないのだけど、どんなのがある?

>>920
staticつけないのは論外として、つけてもポインタの指し示す先が共有されていることは理解してる?
int *func(int n){
static int a;
a=n;
return &a;
}
int main(void){
int a,b;
a=func(1);
b=func(2);
printf("a = %d, b = %d\n", a, b); /* a = 2, b = 2 */
return 0;
}

927:926
10/03/28 10:42:50
ごめ、すっとぼけてた。
int main(void){
int *a,*b;
a=func(1);
b=func(2);
printf("*a = %d, *b = %d\n", *a, *b); /* *a = 2, *b = 2 */
return 0;
}

928:925
10/03/28 13:39:27
デザインの問題だけどたとえば何かデータをファイルから読むとか
与えたデータから新しいデータを作るというときに

const vector<double> parseData(double x,vector<double> v,...){
vector<double> v1;
…vector 領域確保して,データを料理してv1に入れる…
return v1;
}
int main(){
...
vector<double> vData(paseData(x,v,...));
}

みたいなのはなぜいかんのかなと思って

void parseData(vector<double>&v1,double x,vector<double> v,...){
…vector 領域確保して,データを料理してv1に入れる…
}
int main(){

vector<double> vData;
paseData(vData,x,v,...);
}

みたいに必ず書かなきゃいかんのかな?(確かに昔Fortranとかはいつもこういう
スタイルだったなぁ)

個人的には前者の方が直感的だけど
簡単のため vector の例にしたけどもちろん自分で定義したデータ class でも同じこと




929:デフォルトの名無しさん
10/03/28 13:40:41
コピーが発生したら嫌じゃん

930:デフォルトの名無しさん
10/03/28 15:38:13
コピーのコストが問題にならない状況でなら、その手も使った。

931:デフォルトの名無しさん
10/03/28 16:47:51
関数内でnewしてshared_ptrで返せばいいよ

932:デフォルトの名無しさん
10/03/28 17:06:34
#include <vector>
#include <memory>
#include <iostream>

using namespace std;
using namespace std::tr1;

shared_ptr<vector<double> > parseData(double x){
    shared_ptr<vector<double> > v1(new vector<double>);
    v1->push_back(x);
    return v1;
}
int main(){
    shared_ptr<vector<double> > vData(parseData(1.5));
    cout << vData->at(0) << endl;
}

933:デフォルトの名無しさん
10/03/28 20:14:03
何でstatic付けると助かるのかを理解しない限り、いくらでも似たような問題で
引っ掛かると思われ

934:デフォルトの名無しさん
10/03/28 20:24:01
#include <iostream>
#include <vector>
using namespace std;

int sum(vector<int> vec){
int ammount = 0;
for(vector<int>::iterator it = vec.begin();it != vec.end(); ++it){ ammount += *it; }
return ammount; } // 2ch行数制限回避
int main()
{
vector<int> v;
v.push_back(1);v.push_back(2);v.push_back(3);
cout << sum << endl; // 表示結果: 6
}
はいいんだけど、sumを
template <class T, T zero> T sum(vector<T> vec)
{
T ammount = zero;
for(vector<T>::iterator it = vec.begin();it != vec.end(); ++it){
ammount += *it;
}
return ammount;
}
にして、main中のcoutの行をcout << sum<int, 0>(v) << endl;にすると
a.cpp:8: error: dependent-name ‘std::vector::iterator’ is parsed as a non-type, but instantiation yields a type
a.cpp:8: note: say ‘typename std::vector::iterator’ if a type is meant
のようになっちゃう。vector<T>::iterator itをT vector::iterator itに変えても
a.cpp:9: error: ‘template<class _Tp, class _Alloc> class std::vector’ used without template parameters
a.cpp:9: error: expected initializer before ‘it’
になっちゃう。
どう対処すればいいんでしょう?

935:デフォルトの名無しさん
10/03/28 20:29:52
>>934 URLリンク(ja.lmgtfy.com)

936:デフォルトの名無しさん
10/03/28 20:57:05
typename vector<T>::iteratorか。

937:デフォルトの名無しさん
10/03/29 20:14:09
test

938:デフォルトの名無しさん
10/03/29 20:59:59
個人的にはそろそろ>>928前者のような直接値を返すのも
VC10とかg++ 4.3とかめちゃくちゃ新しいコンパイラならはありだと思うようになってきた。
C++0xのおかげでコピー発生しなくなったから。

939:デフォルトの名無しさん
10/03/29 22:17:32
それはちゃんと右辺値参照をアレするクラスを書いた時限定じゃないのか
全てライブラリのコンテナに限定するなら構わんだろうけど

940:デフォルトの名無しさん
10/04/07 05:36:10
error: pointer to incomplete class type is not allowedってどういうことですか?

941:デフォルトの名無しさん
10/04/07 05:40:42
>>940 そのまんまだろう。

942:デフォルトの名無しさん
10/04/07 13:16:50
>>940
不透明ポインタあたりでぐぐれ


最新レス表示
スレッドの検索
類似スレ一覧
話題のニュース
おまかせリスト
▼オプションを表示
暇つぶし2ch

4854日前に更新/246 KB
担当:undef