- 1 名前:デフォルトの名無しさん mailto:sage [2021/11/15(月) 18:49:18.44 ID:I69rZ/Of.net]
- 前スレ
C++相談室 part157 https://mevius.5ch.net/test/read.cgi/tech/1628474251/
- 692 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 14:11:22.71 ID:0LC8SyT+.net]
- >>596
万能の一般論は無い(キリ なぜなら、f(x)が0かどうかの判定をしたいとして、±|處を0とみなすべきなのかは f(x)の精度に依存するから ただし、>>560式に f(x1) と f(x2) の等値判定なら >>560式にやりうる これは f(x1) - f(x2) のゼロ判定として>>560式にやればよろっし
- 693 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 14:15:01.32 ID:0LC8SyT+.net]
- アンカーミスった;;;orz
s/>>560/>>588/g
- 694 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 16:12:55.51 ID:13b+4FON.net]
- >>681
O(1) の数値を使って計算してたら例えば 1e-15 以下の数値をゼロと見なすとかするより他ないでしょ バカ?
- 695 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 16:30:03.25 ID:OQdcFc3P.net]
- sedかよ
- 696 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 16:59:40.11 ID:gWLf+Bka.net]
- 知らなくて驚くかもしれないけどdoubleは1e-324も表せちまうんだ
- 697 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 17:34:26.32 ID:UJcbhjLZ.net]
- >>681-687
まだやってたのか小学生・・・ID変えてご苦労様 何度も言ってるが>>560でこの話は終了している
- 698 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 17:48:02.61 ID:vZsc1PCZ.net]
- >>687
そこまで拗らせてる事に驚いたわw
- 699 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 19:34:50.12 ID:DSkywrpw.net]
- >>560
>100万をsin()しても、sin()は2π周期 >doubleの精度15桁中の5桁以上を無駄にしている これよくわからん。
- 700 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 20:03:51.19 ID:0LC8SyT+.net]
- 言ってる当人もわかってないんだろJK
- 701 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 20:37:14.45 ID:0LC8SyT+.net]
- double sin(double x)の精度が±10E-10程度らしいことは>>588の結果が示しているが
こっれはxが100万かどうかによらないことも結果が示してゐる 実装を見ないとわからんが、多分マクローリン展開の打ち切りによる誤差とみるべき
- 702 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 21:05:23.18 ID:yfbq4hUz.net]
- >>692
実装見てから言った方がいいよ。マクローリン展開というが、0を基準にマクローリン展開してるわけないだろ。
- 703 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 21:18:55.93 ID:0LC8SyT+.net]
- >>685
その方法は等値判定として一貫性が無いからNG double x = 2.0; double y = 2.0 + (10E-15) / 2.0; assert(fabs(x - y) <= 10E-15); // pass. 10E-15基準で x == y とみなされる assert(fabs(100 * x - 100.0 * y) <= 10E-15); // fail。 10E-15基準の下で 100 * x と 100.0 * y はイコールにならにあ
- 704 名前:デフォルトの名無しさん mailto:sage [2022/01/22(土) 21:22:04.30 ID:0LC8SyT+.net]
- >>693
sin(x)の場合は|x|<<1においてsin(x) ≒ xなのでsin(x+a)を展開をする際のaを0にするのが妥当に思えまっする、
- 705 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 04:16:28.14 ID:QgynSmAQ.net]
- >>689-695
まだやってたのか小学生・・・ID変えてご苦労様 何度も言ってるが>>560でこの話は終了している
- 706 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 09:39:04.54 ID:CWW/bMN0.net]
- >>678
挙動としては正にそんな感じですね >>679 test.hにあるinline void 内でprintf("%p\n", Field1)、test.cppのvoid Func1内で同様の事をして確認しました 出力のみならず、そもそもヘッダのinline void内でField1に値をセットしたはずなのにソース内ではデフォルト値のままで動作が狂ったので上記のテストをして発覚した次第です structを名前付きにするかしないかの一点だけで上記の結果が変わります
- 707 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 09:40:35.92 ID:CWW/bMN0.net]
- >>697
printf("%p\n", Field1)はレス間違いでprintf("%p\n", &Field1)で実験しています
- 708 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:41:30.96 ID:QgynSmAQ.net]
- #include<iostream>
struct A{static struct SubStruct{int value;} Field1;}; A::SubStruct A::Field1; int main() { std::cout << std::hex << &A::Field1 << std::endl; return 0; } 無名で実体の定義なんてできんのか?
- 709 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:43:19.72 ID:vZkrAotW.net]
- キャストやconst&でできるな
- 710 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:47:03.39 ID:QgynSmAQ.net]
- >>700
どうやんの?上の例でやってみてよ
- 711 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:48:14.26 ID:QgynSmAQ.net]
- ちなみに上の例は無名でない構造体で、実体の定義は
A::SubStruct A::Field1; な
- 712 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:51:00.92 ID:CWW/bMN0.net]
- >>699
C++20だか17だかからはinlineをつける事で出来ます
- 713 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:51:47.13 ID:QgynSmAQ.net]
- #include<iostream>
struct A{static struct {int value;} Field1;}; decltype(A::Field1) A::Field1; int main() { std::cout << std::hex << &A::Field1 << std::endl; return 0; } 意外とやってみたら出来たw
- 714 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:55:02.08 ID:vZkrAotW.net]
- >>700
A::SubStruct{} で実体の「定義」ができる &A::SubStruct{} は実体がprvalueという理由でエラーだが 実体を定義できるか否かとは別問題だ
- 715 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:57:42.35 ID:QgynSmAQ.net]
- >>705
根本的に意思疎通できてないみたいだな staticメンバA::Field1の実体定義だって
- 716 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 10:59:48.93 ID:vZkrAotW.net]
- >>706
そのようだな なぜstaticメンバが出てくるのか不明だ
- 717 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 11:04:13.16 ID:QgynSmAQ.net]
- >>703
確かに出来た -std=c++17 付けたら実体定義なくても通った
- 718 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 11:05:12.08 ID:QgynSmAQ.net]
- コードはこんなのね(with -std=c++17)
#include<iostream> struct A{static inline struct {int value;} Field1;}; int main() { std::cout << std::hex << &A::Field1 << std::endl; return 0; }
- 719 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 11:25:38.49 ID:QgynSmAQ.net]
- 実体は同じのを指すようで再現しなかったな。MakefileはちゃんとTAB入れてな。
cat >Makefile <<EOF CXXFLAGS += -std=c++17 sample: main.o sub1.o sub2.o \$(LINK.cc) \$? -o \$@ EOF cat >main.cpp <<EOF void sub1(); void sub2(); int main() { sub1(); sub2(); return 0; } EOF cat >sub1.cpp <<EOF #include<iostream> struct A{static inline struct {int value;} Field1;}; void sub1() { std::cout << std::hex << &A::Field1 << std::endl; } EOF cat >sub2.cpp <<EOF #include<iostream> struct A{static inline struct {int value;} Field1;}; void sub2() { std::cout << std::hex << &A::Field1 << std::endl; } EOF make
- 720 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 15:40:28.67 ID:K/S7vg9Z.net]
- >>697-698
wandbox の gcc 11.1.0 でもやってみたけど、再現せず同じアドレスが出た。 https://wandbox.org/permlink/SSg6OZD97wmgR8kq コンパイラやバージョンやコンパイルオプションを合わせれば再現するのかね?
- 721 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 15:53:41.49 ID:QgynSmAQ.net]
- >>711
複数のオブジェクトファイルにしないと検証できないと思うよ
- 722 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 16:09:46.74 ID:K/S7vg9Z.net]
- >>712
>>697の説明にあるtest.cppはtest.hをインクルードしてるんだろうからこの形でいいだろうと思った。 まぁやってみたけど、変わらないね。 https://wandbox.org/permlink/hfbakWmCF1i5stqr
- 723 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 16:31:20.27 ID:QgynSmAQ.net]
- >>713
流石にヘッダファイルから何かが生成されることはないw wandboxで複数オブジェクトファイルって処理系内部の作り次第になるし、>>710でもやってみようかと思ったけど、3つは無理そうだね
- 724 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 17:20:50.76 ID:hHkcGLX7.net]
- ヘッダに実装書くと管理が楽だよね
- 725 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 17:32:20.44 ID:CWW/bMN0.net]
- >>711
検証頂いてるところ環境を明記しておらず申し訳ありません Visual Studio 2022、C++20で発生している現象です #include "test.h" int main() //main.cpp { A::Initialize(); //printf("%p\n", &A::Field1);をするだけのstatic inline関数 A::Func1(); //printf("%p\n", &A::Field1);をするだけのstatic関数(__declspec(noinline)をし実装はtest.cpp) } struct名をつければInitializeの出力とFunc1の出力は一致、無名structにしたら不一致 本当に他は一切いじらずに名前の有無だけで変わります
- 726 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 17:54:11.09 ID:QgynSmAQ.net]
- 現象を再現させる最小限のコードを全セット載せないと先には進まんて
始めからそうしてればこんなにいろいろ書かずに済んでいる
- 727 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 18:17:03.90 ID:K/S7vg9Z.net]
- >>714 wandbox でも -v 追加で as が2つ test.cpp と prog.cc と別で走ってるのまでは見た。
- 728 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 18:18:38.46 ID:K/S7vg9Z.net]
- >>716
MSVC のバグっぽいね。おとなしく名前つけて回避しつつ、できればバグ報告しとくのがいいんじゃない。
- 729 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:02:54.49 ID:QgynSmAQ.net]
- >>715
>>675で「無名構造体のスタティックメンバ変数はヘッダファイルとcppファイルとでそれぞれ別の実体が生成されアドレスが異なる」 と書いてあるが、ヘッダファイルから直接実体は生成されないよってこと .cppなどのソースファイルからincludeされないとコンパイルしないから (もちろんただのファイル名なのでコンパイラに
- 730 名前:直接ヘッダファイルをコンパイルせよと指定する事はできる)
つまりA::Field1に該当するシンボルが複数の.objに含まれた場合、同じになっているか=アドレスが同じになるか? の検証でないと意味がない [] - [ここ壊れてます]
- 731 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:09:37.28 ID:QgynSmAQ.net]
- >>718
それは昔からgccを使ってる人は知ってるけど、そういう話じゃない 明らかに不自然な位置にソースファイルを指定して無理矢理2個同時にコンパイルする上に、引用されて3個はできない つまり想定された使い方ではないということ おまけに処理系やそのバージョンを複数変えられることが比較的便利なwandboxで、処理系を変えると確認が必要になるやり方はどうかと言っただけ まあ、分かってるとは思うんだが
- 732 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:24:03.88 ID:QgynSmAQ.net]
- とりあえず、710のコードでVS2019を調べた結果、再現は確認できた。
ただし、コンパイルオプション次第で現象が出たり出なかったりする。 VS2022でもないし、VSはコンパイルリンクオプションがデフォルトで大量に指定されてて確認が面倒なのでそれ以上は放棄した。 以下のコードではpermissive-オプションの有無で現象が再現したりしなかったりするが、デフォルト時だとその切替えで現象は変わらないので、一次原因ではないと思う。
- 733 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:24:36.31 ID:hHkcGLX7.net]
- 保守できないような書き方して自分の仕事を守る。PGの当然の権利ですよね。
- 734 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:25:06.27 ID:QgynSmAQ.net]
- > main.cpp (
@echo void sub1^(^); @echo void sub2^(^); @echo int main^(^) { @echo sub1^(^); @echo sub2^(^); @echo return 0; @echo } ) > sub1.cpp ( @echo #include^<iostream^> @echo struct A { static inline struct { int value; } Field1; }; @echo void sub1^(^) { @echo std::cout ^<^< std::hex ^<^< ^&A::Field1 ^<^< std::endl; @echo } ) > sub2.cpp ( @echo #include^<iostream^> @echo struct A { static inline struct { int value; } Field1; }; @echo void sub2^(^) { @echo std::cout ^<^< std::hex ^<^< ^&A::Field1 ^<^< std::endl; @echo } ) > sample.mak ( @echo CXXFLAGS = /MDd /EHsc /std:c^+^+17 /permissive- @echo .cpp.obj: @echo $^(CXX^) $^(CXXFLAGS^) /c $^< @echo sample.exe: main.obj sub1.obj sub2.obj @echo link /OUT:$@ $^*^* ) nmake /f sample.mak rem バッチファイルもnmakeもよく知りません。
- 735 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:34:19.55 ID:K/S7vg9Z.net]
- >>721 ソース3つ以上もできるよ。 https://wandbox.org/permlink/UgIc9mFrs59059jq
- 736 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:40:05.18 ID:QgynSmAQ.net]
- >>723
そういうのはプロジェクトの方針だと思うので、ここで話す内容ではないと思うよ
- 737 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:45:20.80 ID:QgynSmAQ.net]
- >>725
改行と空白で違うのかよw b烽、知るかってャ激xルだけど、bりがと bニりあえず>>710を載っけとく https://wandbox.org/permlink/e8khwggKe00rtekJ
- 738 名前:デフォルトの名無しさん mailto:sage [2022/01/23(日) 20:49:22.51 ID:QgynSmAQ.net]
- >>723
>>727は何故だか文字が化けてたので一応書き直しとく。 改行と空白で違うのかよw もう知るかってレベルだけど、ありがと とりあえず>>710を載っけとく https://wandbox.org/permlink/e8khwggKe00rtekJ
- 739 名前:デフォルトの名無しさん [2022/01/24(月) 19:27:55.24 ID:WxnVLAIm.net]
- C++11から、C++20までの変更点を解説した入門書を年末に買ったのだが(C++は書けるよ)、まだ読む気になれないw
「今更C++か、pythonでいいだろ」と悪魔が囁くw
- 740 名前:デフォルトの名無しさん mailto:sage [2022/01/24(月) 19:42:15.63 ID:nLfFXIoN.net]
- c++cliについてネットに解説している情報あまり無いですが、まとまってるサイトとかないですかね。
- 741 名前:デフォルトの名無しさん mailto:sage [2022/01/24(月) 20:29:40.39 ID:kghIRcG8.net]
- https://docs.microsoft.com/ja-jp/cpp/dotnet/dotnet-programming-with-cpp-cli-visual-cpp?view=msvc-170
- 742 名前:デフォルトの名無しさん mailto:sage [2022/01/25(火) 08:07:34.25 ID:m+e4/QVD.net]
- めずらしい
変態に興味あるとは VisualJ++とかワケ
- 743 名前:ワカだったぜw []
- [ここ壊れてます]
- 744 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 05:15:43.56 ID:DGJ/MazB.net]
- 1秒おきのタイマーでtmDraw()を呼んで右に伸びる四角を描くプログラムです。VSCでMFC未使用。
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_PAINT: OnPaint(hWnd); break; case WM_CREATE: SetTimer(hWnd,1,1000,(TIMERPROC)NULL); //タイマー定義 break; case WM_TIMER: //タイマー { PAINTSTRUCT ps; HDC hdc = BeginPaint(hWnd, &ps); tmDraw(hdc); //これを呼んで描画 EndPaint(hWnd, &ps); } break; return 0; } static VOID tmDraw(HDC hDC) { SetDCPenColor(hDC, RGB(0x99, 0x66, 0x00)); //ここが呼ばれてるのは確認 SetDCBrushColor(hDC, RGB(0xFF, 0xCC, 0x00)); Rectangle(hDC, SIZE16(0, 0, cx++, 6)); //伸びる描画 } 最初の1回の描画はされます。タイマーでtmDraw()が呼ばれてるのは確認しています。 呼ばれて描画されてるはずなのですが、実際の画面は更新されず四角は伸びません。 windowサイズを手動で変えていくと四角は右に伸びていき更新されます。 タイマーでtmDraw()が呼ばれた時に描画だけでなく画面の更新もされるようにするにはどうすればよいですか?
- 745 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 06:35:00.77 ID:R08bxH5q.net]
- WM_TIMERでBeginPaintはおかしいぞ
WM_PAINT専用なんだから 無効領域ないのにBeginPaintしたらあかん [誘導] 続きはこっちでな Win32API質問箱 Build127 https://mevius.5ch.net/test/read.cgi/tech/1639053176/
- 746 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 07:17:52.16 ID:T9eKedNN.net]
- InvalidateRectとかGetDC〜ReleaseDCだっけ?
- 747 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 07:50:18.18 ID:td9ayUMw.net]
- アップデートはマイクロソフトがやりたい時にやる
という基本理念を理解していないようだね
- 748 名前:デフォルトの名無しさん [2022/01/26(水) 09:14:18.23 ID:m89Xdimf.net]
- WM_TIMERでInvalidateRectしておくとWindowsがWM_PAINT呼んでくれるからそこで描画するんだっけ
- 749 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 09:17:55.57 ID:qvNTvCwo.net]
- そもそもこれCだろ…
WinMainから書く超基礎的コードをここで聞く頭がもうね
- 750 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 09:26:13.12 ID:WR8doP3S.net]
- べつにアイドルループで描画してもいいんだよ
メッセージの処理さえ忘れずにピークしてこなせば
- 751 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 09:32:54.79 ID:g/1zEXcm.net]
- >>738
スレチなのは確かだが、いちいち見下して何がしたいんだお前
- 752 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 09:36:18.65 ID:dkXO6/An.net]
- どこにでもいるんだよ
自分より下の者をいたぶることで 安心しようとするチンピラ気質なやつは
- 753 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 10:21:44.17 ID:qvNTvCwo.net]
- だってココ定期的に湧くじゃん
Windows使っててWin32APIの使い方聞いてくるC++ほとんど知らない自称天才のバカ 同じやつだよきっと 毎回Win32APIに誘導されてるってのにな
- 754 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 10:46:25.17 ID:g/1zEXcm.net]
- あー、言われれば確かにそんなの居たっけ・・
でもまぁ同一人物とは限らないんだし誘導して終わりでいんじゃね たまに見当違いの初心者は入ってくるし(DirectXスレにDirectXランタイムのインスコの仕方聞きにきた猛者が居た
- 755 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 10:59:27.08 ID:vhiSf69I.net]
- 733 すいません、そっちのスレは知りませんでした
そちらで聞き直します
- 756 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 11:06:01.05 ID:qvNTvCwo.net]
- DirectXスレにDirectXランタイムのインスコの仕方聞くのはまだ仕方ない話
ドライバ固有の問題に当たっているなら専門家に聞いた方がいいだろう 自称天才のバカである確率の方が高いと思うし、高確率で単発IDで荒らすバカも同じだろうし、わざわざレスしてくるやつも同じだろうから、バカにはバカと言ってあげた方が親切
- 757 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 12:02:29.99 ID:dkXO6/An.net]
- 誘導ももう済んでるのに
どうしても喧嘩言葉を使いたくて沸いてくる 三下のそのまた下の家畜はいいのか
- 758 名前:デフォルトの名無しさん [2022/01/26(水) 13:23:53.73 ID:m89Xdimf.net]
- DirectXランタイムが許されるならWin32 APIだって許してあげなよ
製品名はVisual C++だし、既定の拡張子 .cpp なんだから Win32はC++ではなくCだって言ってもしょうがない
- 759 名前:デフォルトの名無しさん mailto:sage [2022/01/26(水) 23:06:08.50 ID:UuxYD5f6.net]
- いかにも漏れは天才だが
さすがにWinMain()から書くようなバリバリWindowsアプリの質問はしないかなあ、、、 漏れの言ってることがまるで理解できない低レヴェル凡人の反発を招くことはあってもな
- 760 名前:デフォルトの名無しさん mailto:sage [2022/01/27(木) 10:59:27.25 ID:Z+Vqme3O.net]
- 天才でも質問することあるんですね
回答者は超天才?
- 761 名前:デフォルトの名無しさん mailto:sage [2022/01/27(木) 11:49:44.22 ID:avZQ9Wm7.net]
- いかにも
私が超天才だが ってどっかのハンコ貰いにいく人事のCMみたい
- 762 名前:デフォルトの名無しさん mailto:sage [2022/01/29(土) 15:04:46.13 ID:mo0R2qbj.net]
- 大学の課題でコンパイルエラーになるので教えてもらいないでしょうか
main.cppで、B<A> b; b.display(); のようにAを使っています。 g++ -Wall -std=c++17 -g -o test a.cpp main.cpp undefined reference to `operator<<(ostream&, A const&)' ※コンストラクタなどの関数定義は省略してます。 ■ a.h class A { public: string m_str; friend ostream & operator << (ostream &os, const A &a); }; ■ a.cpp ostream & operator << (ostream &os, const A &a) { os << a.m_str << endl; return os; } ■ b.h template <typename T> class B { public: void display(ostream &os = cout) const; T m_dummy; }; template <typename T> void B<T>::display(ostream &os) const { os << m_dummy << endl; // ここが undefined referenceエラー }
- 763 名前:751 mailto:sage [2022/01/29(土) 15:50:41.96 ID:mo0R2qbj.net]
- 失礼、自己解決しました。
namespaceをa.hだけ括って、a.cppに入れ忘れましたw
- 764 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 02:23:38.98 ID:iz74n4+D.net]
- 下の★1を★2のように書きたいんだけど、どうやって書けばいいのか
教えてぇ #include <iostream> template <typename T> auto Sum(T h) { return h; } template <typename Head,typename... Rests> auto Sum(Head head,Rests... rests) { return head + Sum(rests...); } template<class F,class... Args> auto foo(F&& f,Args... args) { return f(args...); } int main( int argc, char *argv[] ) { std::cout << foo(Sum<int,int,int>,1,2,3) << "\n";//★1 //std::cout << foo(Sum,1,2,3) << "\n"; //★2 }
- 765 名前:はちみつ餃子 mailto:sage [2022/01/31(月) 04:05:32.34 ID:y6tOo2ii.net]
- >>753
そのようには書けない。 C++ では高階多相を許していない。
- 766 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 04:18:19.49 ID:o5RGUewZ.net]
- なんでも適当に済ますクセ
高級言語に慣れすぎの弊害
- 767 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 14:49:02.61 ID:y2HjUy1l.net]
- >>753
・まず、Sumを多重定義にする必要性は特にないはず ・次に、fooが関数でSumが関数テンプレートの場合、 関数の実引数として具現しないテンプレートは渡せない だからfooの代わりにstd::bindを使っても解決しない ・テンプレートテンプレート仮引数を使っても クラステンプレートしか渡せず関数テンプレートは不可 こうなるとマクロくらいしか手がない #define foo(func, ...) func(__VA_ARGS__)
- 768 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 16:24:09.60 ID:4mzN2AL1.net]
- 戻り値のautoが決まらないってことでしょ?autoをdouble固定にしてReturnをなくせば通る
#include <iostream> auto sum() {return 0;} template<typename Head> auto sum(Head head) {return head;} template<typename Head, typename... Tails> auto sum(Head head, Tails ...tails) {return head + sum(tails...);} template<typename Return, typename... Args> Return wrap(Return (*f)(Args...), Args ...args) {return f(args...);} int main( int argc, char *argv[] ) { std::cout << sum(1,2.1) << std::endl; std::cout << wrap(static_cast<double(*)(int,double)>(sum), 1,2.1) << std::endl; std::cout << wrap(sum<int,double>, 1,2.1) << std::endl; std::cout << wrap(sum, 1,2.1) << std::endl; return 0; } // /usr/bin/g++ -fdiagnostics-color=always -g /home/user/cpp/autoreturn/sample.cpp -o /home/user/cpp/autoreturn/sample // /home/user/cpp/autoreturn/sample.cpp: In function ‘int main(int, char**)’: // /home/user/cpp/autoreturn/sample.cpp:10:29: error: no matching function for call to ‘wrap(<unresolved overloaded function type>, int, double)’ // 10 | std::cout << wrap(sum, 1,2.1) << std::endl; // | ^ // /home/user/cpp/autoreturn/sample.cpp:5:52: note: candidate: ‘template<class Return, class ... Args> Return wrap(Return (*)(Args ...), Args ...)’ // 5 | template<typename Return, typename... Args> Return wrap(Return (*f)(Args...), Args ...args) {return f(args...);} // | ^~~~ // /home/user/cpp/autoreturn/sample.cpp:5:52: note: template argument deduction/substitution failed: // /home/user/cpp/autoreturn/sample.cpp:10:29: note: couldn’t deduce template parameter ‘Return’ // 10 | std::cout << wrap(sum, 1,2.1) << std::endl; // | ^
- 769 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 20:55:29.83 ID:ExACmeMg.net]
- >>753
auto Sum = [](auto head, auto... rests) { return (head + ... + rests); };
- 770 名前:デフォルトの名無しさん mailto:sage [2022/01/31(月) 22:50:37.06 ID:67CF9RIT.net]
- ラッパークラスを通せば似たようなことはできそう。
struct Wrapper_ { constexpr static auto doit = [](auto... args) { return Sum(args...); }; } wrapper; int main( int, char ** ) { std::cout << foo(wrapper.doit,1,2,3) << "\n"; }
- 771 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 04:38:50.89 ID:X9o0BiPI.net]
- クラスは不要だった。
ラムダなら通るみたいだから、 >>758 みたいに元の関数をラムダで書くか、 auto wrapper = [](auto... args) { return Sum(args...); }; みたいなラッパー関数オブジェクト通すかってあたりで足りそう。 // 最初実験してたとき、ラムダ式にしただけだとエラー出てた気がしたんだけど、今やると問題なく通る…
- 772 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 05:38:09.33 ID:wGiSz27Y.net]
- おお、auto... なんてできたのか
- 773 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 07:53:40.48 ID:vPA4cgbg.net]
- >>757にラムダ入れた。
ラムダはオーバーロードできずC++17の畳み込み式が必須で引数なしが表現できないが、選択の手間がない。 #include <iostream> auto sum() {return 0;} template<typename Head> auto sum(Head head) {return head;} template<typename Head, typename... Tails> auto sum(Head head, Tails ...tails) {return head + sum(tails...);} template<typename Return, typename... Args> Return wrap(Return (*f)(Args...), Args ...args) {return f(args...);} auto lambda_sum = [](auto head, auto ...tails) {return (head + ... + tails);}; // 追加 auto lambda_wrap = [](auto f, auto ...args) {return f(args...);}; // 追加 int main( int argc, char *argv[] ) { std::cout << sum() << std::endl; // 追加 std::cout << sum(1) << std::endl; // 追加 std::cout << sum(1,2.1) << std::endl; std::cout << wrap(static_cast<double(*)(int,double)>(sum), 1,2.1) << std::endl; std::cout << wrap(sum<int,double>, 1,2.1) << std::endl; // std::cout << wrap(sum, 1,2.1) << std::endl; // エラー // lambda版追加 // std::cout << lambda_sum() << std::endl; // エラー std::cout << lambda_sum(1) << std::endl; // 追加 std::cout << lambda_sum(1,2.1) << std::endl; std::cout << lambda_wrap(static_cast<double(*)(int,double)>(sum), 1,2.1) << std::endl; std::cout << lambda_wrap(static_cast<double(*)(int,double)>(lambda_sum), 1,2.1) << std::endl; std::cout << lambda_wrap(sum<int,double>, 1,2.1) << std::endl; // std::cout << lambda_wrap(lambda_sum<int,double>, 1,2.1) << std::endl; // not template // std::cout << lambda_wrap(sum, 1,2.1) << std::endl; // エラー std::cout << lambda_wrap(lambda_sum, 1,2.1) << std::endl; return 0; }
- 774 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 22:23:26.64 ID:rdLB3H0G.net]
- c++では
sz=120; char dt[sz]; このように配列のサイズを変数の可変サイズで指定することはできないんですか? これを実現する方法は何かありませんか?
- 775 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 22:43:02.67 ID:rdLB3H0G.net]
- 自己解決しました
しかし dt[10][d] のように2次元以上はjavaのような動的変動はできないんですね
- 776 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 23:27:31.22 ID:fhOfpvRh.net]
- vector使わんの?
- 777 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 23:28:28.99 ID:hJiWfYJV.net]
- 配列使わんし
- 778 名前:デフォルトの名無しさん mailto:sage [2022/02/01(火) 23:30:45.06 ID:Sh1zYLGa.net]
- >>763
arrayという似たようなやつはあるが 基本的に作法が違う
- 779 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 10:03:42.12 ID:pPu7Tazo.net]
- コンストラクタ・テンプレートでテンプレート実引数を推定させず明示的に与えるのはどう書く?
struct some_class { template <class A> some_class(int) {} }; int main() { some_class obj<void>(1); //error }
- 780 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 12:11:02.47 ID:ryNE78sg.net]
- >>768
コンストラクタには明示的に型引数を渡せない
- 781 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 12:36:54.65 ID:pPu7Tazo.net]
- そっか。。。残念
thx >>769
- 782 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 12:56:51.10 ID:X/91R13x.net]
- ファイルサイズを取得しようとしていろいろサイトを参考にして次のようにしたのですが
std::filesystem::file_size(path) filesystemのところに赤線が出て使用できません これらは記述しています #include <iostream> #include <fstream> #include <filesystem> 使っているのはCommunity 2019です filesystemが使えないのはなぜでしょう?
- 783 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 13:02:34.63 ID:ryNE78sg.net]
- >>771
filesystemが使えるのはC++17以降 プロジェクトの設定から言語バージョンをC++14(既定)->C++17に
- 784 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 13:34:32.24 ID:pPu7Tazo.net]
- >>771
/std:c++17は指定してる?
- 785 名前:デフォルトの名無しさん mailto:sage [2022/02/02(水) 13:43:30.57 ID:X/91R13x.net]
- ありがとうございます C++17指定できました
- 786 名前:デフォルトの名無しさん mailto:sage [2022/02/03(木) 12:49:10.84 ID:d1XPVqCl.net]
- filesystemは、できればC++20モードで使いたい
file_clockまわりがC++17ではgdgdだから
- 787 名前:デフォルトの名無しさん mailto:sage [2022/02/04(金) 13:06:35.94 ID:ovGR74Kw.net]
- 小文字に変換するプログラムです
string toLowerCase(const string& str) { string lower = str; std::transform(lower.begin(), lower.end(), lower.begin(), std::tolower); return lower; } 実行するとstd::transform 一致するオーバーロードする関数が見つかりません、とか 6引数が必要です 4が設定されてます、とか出て 実行できません これは何が問題なのでしょうか?
- 788 名前:デフォルトの名無しさん mailto:sage [2022/02/04(金) 13:07:58.25 ID:N/NFryku.net]
- tolowerが多重定義関数だからじゃね?
- 789 名前:デフォルトの名無しさん mailto:sage [2022/02/04(金) 13:22:13.60 ID:ovGR74Kw.net]
- 自分では他に定義してないんですがどこで定義されてるんでしょう
- 790 名前:はちみつ餃子 mailto:sage [2022/02/04(金) 13:28:07.50 ID:RpLWwySn.net]
- >>776
ちょうど >>658 で同じような事例が出ている。 std::tolower は cctype ヘッダと locale ヘッダにそれぞれあって locale ヘッダのほうが関数テンプレートだし二引数なのでこの場の都合に合わない。 なんらかの方法でどれを使うのか選択する必要があり、 たとえば static_cast などが使える。 ただ、 >>661 が提示しているようにデフォルト引数が追加される可能性があったりもするので static_cast よりはラムダ式を経由するほうが安心できるスタイルかもね。 #include <iostream> #include <string> #include <algorithm> #include <cctype> std::string toLowerCase(const std::string& str) { std::string lower; std::transform(std::begin(str), std::end(str), std::back_inserter(lower), static_cast<int(*)(int)>(std::tolower)); return lower; } int main(void) { std::cout << toLowerCase("abcDEfgHi") << std::endl; }
- 791 名前:デフォルトの名無しさん mailto:sage [2022/02/04(金) 13:35:40.02 ID:ovGR74Kw.net]
- ありがとうございます ビルド通ったみたいです
- 792 名前:デフォルトの名無しさん mailto:sage [2022/02/04(金) 13:55:24.36 ID:3M0ClPfa.net]
- 最近のはptr_funやんなくても通んだな
|

|