C++相談室 part134
■ このスレッドは過去ログ倉庫に格納されています
次スレを立てる時は本文の1行目に以下を追加して下さい。 !extend:on:vvvvv:1000:512 C++に関する質問やら話題やらはこちらへどうぞ。 ただし質問の前にはFAQに一通り目を通してください。 IDE (VC++など)などの使い方の質問はその開発環境のスレにお願いします。 前スレ C++相談室 part133 http://mevius.5ch.net/test/read.cgi/tech/1511509970/ このスレもよろしくね。 【初心者歓迎】C/C++室 Ver.102【環境依存OK】 http://mevius.5ch.net/test/read.cgi/tech/1509780815/ ■長いソースを貼るときはここへ。■ http://codepad.org/ https://ideone.com/ [C++ FAQ] https://isocpp.org/wiki/faq/ http://www.bohyoh.com/CandCPP/FAQ/ (日本語) VIPQ2_EXTDAT: default:vvvvv:1000:512:----: EXT was configured でもポインタにしてしまうと困るシチュエーションなんてありうるの? マクロの中でsizeofしてるとか? メンバのコピーコンストラクタを起動すべきところをmemcpy()しかしない手製コピーコンストラクタで済ませようとしたら破滅が訪れる MyClass(const MyClass&) = default; なら勝手にやってくれるのでその心配が無いので安心 しかしまあ >>68 なんていう便利なモノがあるとは フラフラこういうスレ読んでるのもためになるなあ >>62 処理系に依存することなく「保証」なんて出来ない 以上 >>63 で解決している もしくは以下への回答も>>69 で出ている バイト列コピーが = default; なわけねーだろアホ よく読め バイト列コピーでokの保証は>>69 遅くならないコンストラクタの書き方が>>63 そもそも「どうコンストラクタを書けば」ってのを質問してるんで バイト列コピーでコンストラクタを書けってのは単に>>65 の珍解答に過ぎない 元の質問>>62 は ・処理系に依存せずデフォルトより遅くならないことが保証されているコンストラクタの書き方 もしくは ・バイト列コピーでokと明示する構文 だろ。 前者は>>63 後者は>>68-69 元質問: デフォルトのコピーコンストラクタ以上の性能 おまえ: デフォルトより遅くならないこと よく読めをそのまま返す 以上っていうのは等しいかまたはそれを越えるという意味だぞ そもそも memcpy は前者の性能保証も後者の仕様の保証もどちらも満たしてない 仕様が保証されてるなら多分性能的に大丈夫だろうという程度 間違いを認めると死ぬ病気なんだろうからもうこれ以上は言わない。 バイトコピーでmemcpyより高性能な手段を1つでも例示したらどうなんだ > 間違いを認めると死ぬ病気なんだろうから ああ、おまえがか memcpy()より速いコピー手段Xが仮にあったとして 論理的にmemcpy()で済むケースについてコンパイラが提供する デフォルトのコピーコンストラクタがコピー手段Xにならない理由がわからん… 個人的には「=default;」と書いたら最高性能なんなら毎回手でmemcpy()とか書きたくないカンジ >>94 class A { public: A() {} A(A const&) { std::cout << "aho"; } }; class B { public: A a; B() = default; }; int main() { B b, c = b; //this will call you. } >>95 は「論理的にmemcpy()で済むケース」では無いからちげう 仕方ないので漏れが訂正するわ; ttps://ideone.com/TZnGv4 ↑のコードの (*1)は「=default;」でデフォルトのコピコンの使用を明示 (*2)は手でmemcpy()でコピーするように書いたコピコン 次の条件で試したら(*1)も(*2)も同じコードになったわ x86-64 gcc 7.2 -O2 -fno-strict-aliasing -std=c++14 -pedantic -Wall -Wextra こことかで試せるが保存と公開方法がわからんかったのでideoneを使わせてもろうた ttps://gcc.godbolt.org/ 漏れの国語力ではようわからんが、さすがに多分>>84 は間違いなんジャマイカ、 Cから来た連中ってどうしてmemcpyやmemset使いたがるんだろうな >>76 reinterpret_cast でなければ通らないときはだいたい駄目なときやわ。 >>100 「default がバイト列コピーとは『限らない』」という意味で >>84 は真。 開始アドレス、終了アドレス、サイズが64bit等で割り切れれば バイトコピーより早いコピーはあるだろうね 頭のいいコンパイラなら勝手にベクトル処理とかしてくれるんじゃないの? 知らんけど "!"!"!MOHYO!"!"!"2" 1.[[[HUn≒MUL=POSI≠MAHO+Set*HUGE=SAGE=LOGE=NOISIA=0≒1]]] 2-[[[[[[[E=RAT%2^10%SPELAn!%]&!TOWA&!PEG#!NOLNOL8!#!HYAGO!2#]1*2=1]U]S]0]O]!#PAL! 3--->PAGODOL7&!@17,2222734.15&[[[%%RENRAK6,9,99"^10"]#$11.2%}]KAIJ]{ 41.2SSS = RALQI2.β{{{RA4,0,238^97,1,$.S.L.E.I.L."Q5352.15Q"JOL"5*3>>>41 .3q}}}>1.2<0 .3φTALHOSI"0">>>105 .10<1.235<1.2>51≠52===55.632>V="E=0.835"of"1.32","632",0.683,1.end { C++では、 int i; for (i = 0; i < 9; ++i) { ... } が、 for (int i = 0; i < 9; ++i) { ... } って書けるのは知っているだろう。( )の中で、変数を宣言できる。 だが、ifやwhileの( )の中で、変数を宣言できることを知らない人は多い。 C++17では if ( auto v = n; conditions ) { ... } が可能になるし、これからは広がってくれるかのう for( ) の制御変数はそのループでしか使わないことが多いから意味あったけど、if( ) でそんなケースはまれだしなぁ あれば使うけど待ち遠しいって言うほどじゃない気がする 理想主義的な文法ですが、実効性はあるのか疑問ですね 一瞬意図が分からなかったが ()の中が;で区切れるという話? dynamic_castとの組み合わせで使うとかどうよ 結構あると思うけどね if(DWORD err = GetLastError(); err != NO_ERROR) この場合NO_ERRORが0だって分かってるから if(DWORD err = GetLastError()) で済むから無意味だけど >>116 前者の方が意図が明確だし意味はあると思う >>116 >if(DWORD err = GetLastError(); err != NO_ERROR) 普通こうやろ if((DWORD err = GetLastError()) != NO_ERROR) 変数宣言は少しは意味あるかもしれんが(Perlと同じことができるってこと) 複文書けるのは特にメリット感じないわ それ通らんよ こうだろ DWORD err; if((err = GetLastError()) != NO_ERROR) if内でしか使わないerrが外部に漏れてるのがよろしくないってこと >>119 それが通るという変更だと思ってたわ こう書けるPerlのほうがまだ優位性あるね if((my $err = GetLastError()) != NO_ERROR) if(init ; expr)だと初期化と式が関連していなくてもいいので>>120 とは違う構文になる だからこんなのでもよい if(int err = GetLastError(); hoge.aho()) lock_guardもしておける if(std::lock_guard<std::mutex> lock(m); flag) 構造化束縛も使える if(auto [a, b, c] = f(); b > c){ std::cout << "b > c" << std::endl; } Cでは名前空間っていうのをすごい扱っていた気がするんだけどC++は名前空間扱うことってないの? 一つのアプリケーションも完成させたことがないど素人の質問ですまんが >>122 まずは"C"の入門書を読んで、何を見間違えたのかはっきりさせてからにしようか。 構造体タグと型名の名前空間が分かれているといったような意味での名前空間は C に有るが C++ では構造体タグはそのまま型名としても使えるし、そういう意味での名前空間の話かな? こんな名前空間もあるね int x; int main(void) { x = 1; int x; x = 2; { int x; x = 3; } return 0; } 謎すぎワロタがそこから上のスコープのxを参照してくれ std::mapのように文字列や構造体をキーにした高速アクセスができて、 要素の数が一定数を超えたらLRU形式で勝手に削除してくれる、 キャッシュのような機能を実装したいのだけど、 C++でそのような仕組みを作れるクラスはないですか? 自分で実装するならどうにでもなるだろ そのための道具は全て標準で揃っている バックグラウンドならスレッド使うしかないんじゃないかな C++のプログラマーって性格ねじ曲がってるなあ 初めてGo応援したくなったわ >>137 どんな点が、性格悪い、と思わせるのですか? >>136 要素数が閾値を超えるのは要素が追加される時だからその時に古い奴を削除すりゃいいだけじゃね? >>135 簡単で良いのでサンプルコード書いてもらえませんか? >>135 じゃないけどシンプルにいくなら { map<key,value> data; // 本来のデータ map<key,list<key>::iterator> lruindex; // list<key> lrulist; // LRUリスト ... // mapと同じインターフェイス } みたいなクラスで要素の追加・削除・参照とかの時にLRUリスト見て処理すればいい 辞書・線形リスト・2分木を、組み合わせる。Ruby で書くと、 class LRU_hash def initialize (max_size = 3) # ary は、hash に追加・アクセスした順 @hash = {}; @ary = [] @max_size = max_size end def push (key) if @hash.has_key? key # 一旦、要素を削除してから、最後尾に追加しなおす @ary.delete key else if @max_size == @hash.size # 先頭要素を削除してから、最後尾に追加する @hash.delete(@ary.shift) end @hash[key] = true end @ary.push key end def print_buf puts @ary.join ', ' end end ary = ["あ", "a", "あ", "い", "b", "あ", "c"] hash = LRU_hash.new 4 ary.map { |key| hash.push key } hash.print_buf #=> い, b, あ, c >>144 > # ary は、hash に追加・アクセスした順 参照のたびに最後尾に追加しなおすの? プログラムを作っていて困っています。 プログラム動作環境、windows 7 x86_x64 プロセスをExplorerを親として、 起動したプロセスにファイルの存在するディレクトリを作業ディレクトリとして 割り当てたい。 ただし、プロセスへのアタッチによる変更は禁止とする。 ようするにファイルをダブルクリックして起動するのと同じ状況を再現したいのです。 例 C:\hoge\fuga.exe [現状] Explorer C:\hoge\fuga.exe 親 explorer.exe カレントディレクトリ C:\Windows\System32\ [理想] Explorer C:\hoge\fuga.exe 親 explorer.exe カレントディレクトリ C:\hoge\ >>145 >>134 で、LRU と書いてあるから、Hash に追加しようとした度に、 すでに存在する場合でも、配列の最後尾に追加しなおした どういう意味か、正確にはわからないけど >>146 explorer.exeへのショートカットを作ってプロパティで作業ディレクトリを指定するか、 COMでIShellLink::SetWorkingDirectoryを使って同じことをするあたりか? みなさんありがとうございます。 std::mapにLRUや最大要素数の仕組みを持たせた派生クラスでも 無いかと思ったのですが、標準ではやっぱり無いですか。 >>143 のように、std::mapをメンバの一つに持たせた独自クラスを 一から作っていくことになるんですかね。 amazonランキングの謎を解く とか言う本でmove-to-frontを見た 本の紹介「Amazonランキングの謎を解く」 http://www.kenkyuu.net/whatsnew/2011/08/book2011-08-01.html >「move-to-front規則」(最後に売れた順に並べる、つまり、注文のたびに1位にジャンプする) Move To Front - Wikipedia https://ja.wikipedia.org/wiki/Move_To_Front >>149 「c++ lru map」でググったか? いくつかサンプルになりそうなコードが見つかるんだけど C++を勉強しようと思ってる者ですが書籍を探しております。Cはある程度書けるのでそれを前提とした書籍が欲しいです C++ クイック入門&リファレンス プログラミング言語C++ 第4版 >>155 C++11 以前だが accelerated c++, ここでフォローするよ 以下のようにconst char*型の文字列でchar*型の変数を初期化したいときに strcpyやstrlenを書かずにstd::stringを利用して短くかけないかと思うのですが msvcだとエラーにならず、clang, gccだとdeleteでセグメンテーション違反になります。 どうすればより良い感じになるでしょうか?const_castはできれば使いたくないです。 #include <string.h> #include <string> #include <iostream> int main() { const char* asdf = "asdf"; // char* psz2 = new char[strlen(asdf)+1]; // strcpy(psz2, asdf); std::string *psz = new std::string(asdf); char* psz2 = &(*psz)[0]; std::cout << psz2 << std::endl; delete psz2; return 0; } delete psz2なんてしちゃだめconst関係ない 何故stringそのものじゃなくて内部データをdeleteしようと思ったのか newで確保した配列じゃないからdeleteはできない stringの内部データは静的な配列と動的な配列を組み合わせて表現されている mscvの場合先頭16文字はchar[16]でそれ以降は動的な配列に入るようになっている psz[0]のアドレスはchar[16]の先頭アドレスなので当然deleteできない msvcはdeleteに失敗しても落ちないのかな >>155-159 本格的な本なら、ロベール、ハーバート・シルトの独習 軽めの本なら、柴田 望洋、林 晴比古、猫 ハンガリー人まだ絶滅してないのか。 stringはnull terminatedでないからpszはおかしい。 psz2もnull terminatedの保証がないからc_strを使うべき。 うまくいったらstrdupも調べとこうな。 >>162 char* psz2 = &(*psz)[0]; って char* psz2 = psz->c_str(); と同じなのかな? いずれにせよ delete psz; は出来る(するべき?)だけど、 delete psz2; は出来ないんじゃないかな。 必要ないところでnew/delete使う人は根本からして何も分かってない >>162 お前はstringがただの配列だと思っているのか? このトンチキ野郎! >>162 弁護士の唐沢です しっかり「char* const」と「const char*」の違いを認識しなさい const char*は参照先の定数を変更しない事を保証する宣言であり、char*は参照先の定数を変更できる為、const char*で保持するアドレスをchar*にコピーする事は言語仕様により禁止されています。それは分かるよね? 最初に宣言したポインタを間違えて別アドレスで上書きしないようにconstで固定したいのなら、char* constを使うようにしましょう。とりあえずとりいそぎ >>162 strdupという手があるが何がしたいのか今一つ分からない const char* asdf = "asdf"; char *p = strdup(asdf); std::cout << p << std::endl; delete p; >>167 データは連続しているので同じになる 16文字まではスタックを使い、それ以上の長さになるとヒープにコピーされる 実装ではメンバの配列には何かしらのエスケープ文字が入る ちなみにmsvcでは実装の都合上free(&str[0])で強引に解放できる 補足 スタックとヒープを使い分けるかどうかは実装依存 gcc、clang、msvcでは行われている したがって短い文字列でnewを避けるためにstringを使わないというのは意味が無い >>171 strdupで確保した領域をfreeでなくdeleteするのは正しいの? ■ このスレッドは過去ログ倉庫に格納されています
read.cgi ver 07.5.0 2024/04/24 Walang Kapalit ★ | Donguri System Team 5ちゃんねる