C言語なら俺に聞け 140 [無断転載禁止]©2ch.net

レス数が900を超えています。1000を超えると表示できなくなるよ。
1デフォルトの名無しさん 転載ダメ©2ch.net (ワッチョイ 6f8c-8ulf)
垢版 |
2017/05/11(木) 22:20:03.99ID:cn414UR90
C言語の話題のみ取り扱います C++の話題はC++スレへ
質問には最低限の情報(ソース/コンパイラ/OS)を付ける
数行で収まらないソースは以下を適当に使ってURLを晒す
https://paiza.io/
https://ideone.com/
http://codepad.org/

C11
http://www.open-std.org/jtc1/sc22/WG14/www/docs/n1570.pdf

C99
http://www.open-std.org/jtc1/sc22/WG14/www/docs/n1256.pdf
http://kikakurui.com/x3/X3010-2003-01.html

C FAQ 日本語訳
http://www.kouno.jp/home/c_faq/

JPCERT C コーディングスタンダード
https://www.jpcert.or.jp/sc-rules/


http://echo.2ch.net/test/read.cgi/tech/1487757355/
http://www.geocities.jp/c_cpp_cs/about_c/
VIPQ2_EXTDAT: checked:vvvvv:1000:512:----: EXT was configured
2017/07/13(木) 22:13:53.71ID:lX8cJUTX0
グローバル変数から関数の引数にしたりするときに、置換が面倒だと思うことはある
C++だと山椒があるんでそういうことも少ない
2017/07/13(木) 22:40:18.99ID:5QMVP3z90
参照はピリリと辛いのさ
2017/07/13(木) 22:48:52.06ID:ZRvPs5t50
>>846
思想としてそこまで意識して書き、ソース上にもその痕跡を残せってことでしょ。
他言語で言うプロパティの良し悪しと同じ議論だよ。
好き嫌いはあれども、正しい or 間違いの結論はでない。

コンパイラはエラーを検出できてるんだから、
その場合は . を -> と読み替えろ、というルーチンを入れれば君が欲しいものは簡単に作れる。
でも誰も用意しなかった。それが事実だね。
2017/07/13(木) 23:28:37.17ID:EExJF9140
>>844
勝手に前提にするな〜
836は俺だ

>>846
そうそう、仕様として何か不都合があるのかという話がしたかったんだ

>>849
だから836で「教育的な意味」と書いている
結局言語仕様としてこうしないと問題がある訳じゃなくて
「教育的な意味」だけのことでいいんだな

>>847
きっかけはまさにそれ
書き換えめんどくせーから始まって、
コンパイラが困るのかと
色々なパターンを考えてみたんだけど
困るパターンを見つけられなかったんで
こんな話を始めたんだよ
2017/07/14(金) 00:02:31.73ID:jsZNOhnp0
>>850
> 「教育的な意味」だけのことでいいんだな
>>839に答えは既に書いてあるだろ。アホなのか?
具体的にはスタック上に構造体を取って高速化する手法が使えなくなるんだよ。

(大抵の他言語では記述方法自体が用意されていない。
VC++/CLIではvalue型が用意されていて効果があることになっている。
が、ろくな説明が見当たらないorz)
古いが以下。
http://www.eonet.ne.jp/~maeda/cpp/value.htm
MS公式は以下。全く説明する気が無いw
https://msdn.microsoft.com/ja-jp/library/ke3a209d.aspx

というか、そこらへんが面倒だというのならJavaやC#使えって話でしかなく、
今の時代にC使うのならそこまで含めてチューニングする気で書け、でしかない。
2017/07/14(金) 00:16:04.99ID:1+0wIQjnM
839だけど >>851 は周回遅れ。
構造体へのポインタでも、構造体でも、. を使う文法にできるんじゃねっていう主張。
今のところ俺もそれへの具体的な反論を用意できていない。
「教育的」っていうのは違うと思うがな。
2017/07/14(金) 00:35:26.21ID:jsZNOhnp0
>>852
いやみりゃ分かるが 851=849で、俺もそれは否定しない。
ただ、確かに851は間違いだったわ。
確保時の文法が異なっていて、それで十分だから、その後は区別する必要はないね。

見た目、直接か間接か分かるようにしろってことだろ。
2017/07/14(金) 05:37:38.18ID:JCM3Qqhn0
ポインタなら(*foo).member と書くべきのところ->で書けるようにしたってことだけじゃないの?
糖衣構文的なオプションだろう

つうか、どちらもドット演算子に統一した場合、
ポインタなのにデリファレンスしないで値にアクセスできる仕様はCの文法としておかしくね?
2017/07/14(金) 05:52:17.16ID:JCM3Qqhn0
逆にドット演算子の意味を考えてみると、これ変数からのオフセットだろ
2017/07/14(金) 06:19:15.44ID:JCM3Qqhn0
デリファレンスしてもしなくても意味が同じという仕様にした場合、
構造体のポインタのポインタだともっとおかしなことになる
やっぱりダメなんだよw
2017/07/14(金) 06:56:35.87ID:ES2lu6HJM
その反論じゃダメージゼロだ
2017/07/14(金) 07:00:49.03ID:8xomc53MM
>>843
struct s { int *a; };
void f(struct s *sp){
int b = 1;
sp.a = &b; /* 今の文法なら sp->a = &b; */
x = sp.a;
って書かれたら x には b へのポインタが入るの?
それとも 1 が入るの?
まさか右辺の型に依存して変わるとか?
2017/07/14(金) 07:45:04.78ID:OkthEzhE0
最初Cのソース見たとき -> って記述がなんのジョークかと思ったわ。
2017/07/14(金) 07:47:03.66ID:JCM3Qqhn0
>>857
構造体Fooのポインタをメンバーに持つ構造体Fooのポインタで考えてみ
ドットでアクセスするのはどっちのメンバー?
2017/07/14(金) 07:52:21.63ID:JCM3Qqhn0
いや問題はそこじゃないな
862デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/14(金) 08:05:49.17ID:ZvHE7cBu0
>>854が最後にいいこと言った
>>856の指摘が読めてない>>857はIQで30くらい差があるんだろうな
2017/07/14(金) 08:06:19.82ID:OlhrA2fz0
(*pa).m と a->m
(*pa+i) と a[i]

お好きな方をどうぞ
2017/07/14(金) 09:01:40.73ID:i0uGqEt60
>>854
関数へのポインタは(*func)()とデリファレンスしなければいけないのに
func()と書けるようにしたのでおかしくはない
865デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/14(金) 10:09:02.17ID:ZvHE7cBu0
>>863
ミスってるぞ

>>864
sizeof func != sizeof *func
2017/07/14(金) 10:36:06.28ID:7SJq6nEP0
字下げスタイルについて質問です
現在職業訓練校で習っているのですがそこの先生が
「プロはみんなこっち(K&R)だから。最近の教科書はこういうの(オールマン)増えてるけど、初心者向けの本書いてる人はそもそもプログラマじゃないから……」と。
自分がオールマン好きなのと、本を書いてくれる人たちをばかにするような言い方でちょっとむっとしたのですが、実際にK&Rばかりなんでしょうか
2017/07/14(金) 10:58:17.61ID:XOCK9tWfH
>>866
自分一人で書くならプロだろうが何だろうが自分の好みを貫けばいい。
チームならそのチームのスタイルに合わせるのがプロ。
多数派は多分K&R。俺の好みもそう。
2017/07/14(金) 11:03:48.20ID:XOCK9tWfH
>>862
IQ180のお前さんならコード例一瞬で出せそうだからよろしく。
2017/07/14(金) 12:28:17.80ID:i0uGqEt60
>>865
コンパイラが忖度してデリファレンスしてくれるって事じゃん
2017/07/14(金) 13:06:11.17ID:XJoggiB0M
>>866
今は他言語含めてK&Rが主流。昔の初心者本にオールマンスタイルで書かれてるのがあって
自分も最初は括弧の対応が分かりやすいからそれを使ってたけど
今は使わなくなった。括弧の対応なんて見れば分かるので重要じゃなくなる
2017/07/14(金) 13:16:54.77ID:q7yAZvho0
sizeof 関数 って何ぞ?
872デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/14(金) 14:28:28.54ID:ZvHE7cBu0
>>869
void (**f)();
f(); //error
2017/07/14(金) 15:00:47.41ID:JCM3Qqhn0
>>864
C FAQ 4.12
http://www.kouno.jp/home/c_faq/c4.html#12

配列名と関数名が特殊なのは、ポインタに成り下がるからなんだそうだ
構造体はどうだろうか?
874デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/14(金) 15:04:40.25ID:ZvHE7cBu0
>>866
その「先生」もプログラマじゃなさそうに聞こえる
どこのチームに入っても「こいつのクセうぜえ」と思われたらあかん
K&Rだのオールマンだのと言うが純粋なK&Rや純粋なオールマンはむしろ少数派で
たいていなにがしか方言があり、それを無視して原理主義に走ると
標準語を使っているはずの自分のほうが訛っていることにされてしまう
保護色ができないやつがプログラマの世間を知っているのか疑わしい
もしくは、元プログラマでも引退してからずいぶん長いとかな


プログラマ以外の世間でも「前の会社では」が口癖の新入りが干されるのと同じで
狭い世界の狭い正義にとらわれたスッパマンに居場所はない
2017/07/14(金) 15:11:15.53ID:UhIUjxkr0
そこのコーディング規約に従うまで

ただ、古典だけあってK&Rスタイルに近くなると話が早くなる
2017/07/14(金) 15:54:44.39ID:TDDe5YT10
c#はオールマンだし、どっちでもいいな
2017/07/14(金) 18:24:36.67ID:TDGI45F00
え?C#はオールマンなの?
2017/07/14(金) 19:07:42.77ID:pMddghpW0
コーディングスタイルなんて、GNUスタイルとかいう汚物じゃなければ何でもいいわ
2017/07/14(金) 19:09:37.89ID:TDGI45F00
あなたの色に染まります!
2017/07/14(金) 19:46:42.57ID:g8QLqbc9M
>>877
そうらしい

C#
マイクロソフトはC# のコーディング規則を発表しており、これは、BSD/オールマンのスタイルに基づいている。
https://ja.m.wikipedia.org/wiki/%E5%AD%97%E4%B8%8B%E3%81%92%E3%82%B9%E3%82%BF%E3%82%A4%E3%83%AB
881デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/14(金) 21:40:14.77ID:ZvHE7cBu0
汚物は消毒だ〜!!
882デフォルトの名無しさん (エーイモ SE9e-RQIi)
垢版 |
2017/07/15(土) 15:35:51.02ID:mwrVMnVyE
clangにはソースコードを解析してコードを補完する機能がありますけど
gccにはこういう機能はないのでしょうか?
2017/07/15(土) 16:17:52.28ID:4RmHy8z30
>>858
> x には b へのポインタが入るの?
> それとも 1 が入るの?
その仕様にした場合は、 x の型によって決まる。
多分、結局のところは、float->doubleのような暗黙のキャスト、
structPtr* -> *structPtr を許すかどうかだろう。
許しても大した問題はないように思えるが。

ポインタを使える最近の言語はGoとRustか?
詳しい奴がいれば聞いてみればいいのではないかな。
C言語で問題だった点は当然改修されているだろうし。
2017/07/15(土) 16:57:34.95ID:hu77KrcYM
>>883
> その仕様にした場合は、 x の型によって決まる
struct s { size_t *a; size_t *b; };
void f(struct s *sp){
size_t c[] = {1, 2};
sp.a = &c[0];
sp.b = &c[1];
x = sp.b - sp.a;
ってされたらどうするおつもり?
デリファレンスしてもしなくても結果は size_t だよ
2017/07/15(土) 17:11:06.39ID:4RmHy8z30
>>884
だからxの宣言によって決まるだろ。
Cにはvarはないんだよアホ。
お前根本的に型を分かってないだろ。
886デフォルトの名無しさん (ワッチョイ f146-I8+U)
垢版 |
2017/07/15(土) 17:16:20.81ID:pcaRmStc0
>>881
聞いたことのあるセリフだなあ?
何だっけ?
北斗の拳?
2017/07/15(土) 17:16:23.73ID:G5lsIkPM0
これだからなスクリプタは
スクリプタがプログラマ気取るなよと
トホホ
2017/07/15(土) 17:27:16.03ID:jhhap/jh0
>>885
アホなの?
size_t x;
って宣言されててもどっちの解釈もできるだろ
って話だぞ
2017/07/15(土) 17:42:18.56ID:jg2H7hGL0
大元の話で . 演算をポインタに対して適用したら ->とみなすという仕様なら矛盾はないと思うが、
>>843で「左辺が」とか書いたんで話がおかしくなっている気がする。
2017/07/15(土) 17:57:08.70ID:4RmHy8z30
>>889
違うね。
>>888は「右辺を評価する際、 . を . とみなすか -> とみなすか区別できない。なぜならば結果が同じだからだキリッ」
という論理らしいが、そもそもそんな仕様の言語なんて無い。スクリプト言語ですらも。
そもそも着想の仕方がおかしいだろ。エアプだからだよ。

エアプはマジで死ね。
2017/07/15(土) 18:03:19.98ID:Boc3n4O+0
ドットに統一した場合、コードレビューでNULLチェックを見逃す可能性がある
こっちの問題の方が大きいかもしれんな
2017/07/15(土) 18:56:38.12ID:Ok1a2C+90
諸先輩方ご意見ありがとうございました
とりあえずその場所場所でのコーディングスタイルに合わせることが大事なのはわかりました
2017/07/15(土) 19:20:07.01ID:jhhap/jh0
>>890
> そもそもそんな仕様の言語なんて無い。
そりゃアホの子の>>843がない知恵絞って考えた言語仕様だし
今更何を言ってるんだよって話だが w
2017/07/15(土) 20:28:46.13ID:4RmHy8z30
>>891
-> を廃止して . に統一するのならその手の型チェックは緩くなる。
これは結局のところ、他言語でもなされている議論と同じで、
「静的チェックのための記述をどこまで許容するか」でしかない。
俺はCなら厳しい方が似合っていると思うが。

それはさておき、具体的にそのケースならnull許容型、って奴だろう。
他言語でも死ぬほど議論されているからググれ。
2017/07/15(土) 22:24:26.68ID:Z+b63Gri0
>>886
画像検索汁
2017/07/16(日) 00:35:41.14ID:JuGvxIE40
>>894
C言語とは水準が違いすぎる話なのでナンセンスというのが結論だろう
NULL許容で書けたところで、実行時にはNULLチェックするわけだから
2017/07/16(日) 01:49:05.19ID:AkX0kyqa0
>>896
> NULL許容で書けたところで、実行時にはNULLチェックするわけだから
いや、そうじゃない。
というかそっちの議論も多いようだから、誤解するのも分かるんだが。
以下を読むのがいいだろう。
> null許容参照型
> http://www.buildinsider.net/column/iwanaga-nobuyuki/012

Cに対して導入するとしたら以下か。
1. 「null非許容のポインタ」を文法的に用意する。
2. 「null非許容のポインタ」にはNULLは代入できない。(SyntaxError)
3. 「null非許容のポインタ」に「従来のポインタ」の値を代入するには明示的なキャストが必要。
これでヌルポを静的に検出できるようになる。
「null非許容のポインタ」に関しては実行時のNULLチェックは必要ない。

問題は3で、C++ならdynamic_castのみとして例外を投げればいいのだが、
Cの場合これは無理なので、
・リンター等でキャスト直前にNULLチェックしているかを検出する
・明示的キャストをマクロ等でNULLチェックのインライン関数等に置き換える
等の対策が必要にはなるが、
それでもNULLに対してクリーン/ダーティな区画を文法的に分離できるようになるので、
今よりはだいぶマシにはなる。

とはいえこれはbetterCとしてC++を使うのなら現行のC++でも似たようなことは十分できる。
だからわざわざ新文法が必要か?というのと、他と同様に、
静的チェック「だけ」のための新文法を導入する価値があるのか?
という話にはなる。
そして . と -> の話に戻すなら、
「『null非許容型の』struct* から *structへの暗黙的キャストを認める」
という仕様なら、そちらの危惧している部分については回避できることになる。
2017/07/16(日) 07:21:30.62ID:xeCnao79M
>>889
だから . 演算子を適用した結果がポインタならどうするんだ?
って指摘されてるだろ
ID:4RmHy8z30 はレスできなくなって
> エアプはマジで死ね。
とか恥ずかしい捨て台詞で逃げてるけど w
2017/07/16(日) 07:28:16.81ID:xeCnao79M
>>897
> 問題は3で、C++ならdynamic_castのみとして例外を投げればいいのだが、
> Cの場合これは無理なので、
> ・リンター等でキャスト直前にNULLチェックしているかを検出する
> ・明示的キャストをマクロ等でNULLチェックのインライン関数等に置き換える
> 等の対策が必要にはなるが、
そんなアホな対策は要らんわ
キャストまでしてNULL非許容の変数にNULL入れる奴はわかってやってるんだからそのまま入れてくれればいい
それに起因するエラーはプログラマの責任
C言語ってそう言う言語だろ
2017/07/16(日) 07:41:24.58ID:H6W6/XNn0
>>898
>だから . 演算子を適用した結果がポインタならどうするんだ?

. 演算の対象がポインタかそうでないかで分かれるだけで、演算の結果は
それがポインタならポインタとして扱えばいいだけだろ。何か問題あるのか?
2017/07/16(日) 08:14:36.33ID:xeCnao79M
>>900
なら>>858のケースで値が欲しいときはどうするんだい?
まあ新しい演算子を追加するのか?
2017/07/16(日) 08:28:51.97ID:MBQ46mKu0
*sp.aで取れるじゃん
2017/07/16(日) 08:32:10.19ID:H6W6/XNn0
>>858で x に入るのはbへのポインタとしか解釈しようがないと思うが、値とはどれのことを言っている?
bの値の1が欲しいなら普通に x = *sp.a; でいいだろ。
2017/07/16(日) 09:37:42.33ID:xeCnao79M
>>902-903
要するに構造体へのポインタに対する . 演算子は今の -> 演算子と見なせってことね
>>883みたいな奴がいるから念のために確認しただけ
仕様として矛盾はないと思うけど
struct s sl;
struct s *sp;
x = *sl.a;
x = *sp.a;
と統一的に書けるから便利と思うか
x = *sl.a;
x = *sp->a;
とたいして変わらんと思うかは人それぞれだと思う
2017/07/16(日) 09:51:29.40ID:H6W6/XNn0
要するにも何も、>>889でそう書いているんだが。
で、>>898が「念のために確認しただけ」なわけ?
2017/07/16(日) 09:59:26.34ID:JuGvxIE40
要するに、(*p).m を p.m と書けるということ
つまりデリファレンスの階層を一個省略しようってことで、
格段便利ってわけでもないし、かえってややこしいかもなw

これ、ポインタが何段になっても p.m って書いて整合性取れるかい?
2017/07/16(日) 10:06:14.91ID:AkX0kyqa0
>>902-903
だからエアプなんだって。話の通じなさ具合がおかしいだろ。

>>899もそうだ。
> キャストまでしてNULL非許容の変数にNULL入れる奴はわかってやってるんだからそのまま入れてくれればいい
Cの場合はmallocの失敗がNULLになるんだから、これとかありえないだろ。
Cはnullありき、キャストありきで世界が構築されているから、
ヌルポ対策を静的にやりたいのならキャストも含めないと使い物にならない。
しかしエアプだからこれが分からない。マジでウザいから死ね。

> C言語ってそう言う言語だろ
これも違う。
C言語は静的な対策を拒否してない。動的な対策は全面拒否だが。
つっても通じないとは思うが。

>>904
> struct s sl;
> x = *sl.a;
エアプマジ死ねよ

というか、エアプがここに来る意味が俺には分からないのだが。
こいつらどの種のキチガイなの?
2017/07/16(日) 10:11:57.19ID:xeCnao79M
>>905
だからアホがいるから蒸し返されないように念のための確認してるんだよ
匿名掲示板だから>>890みたいな奴すらいるんだぞ
2017/07/16(日) 10:12:48.56ID:xeCnao79M
って書いてるそばから現れたわ w
2017/07/16(日) 10:14:08.60ID:xeCnao79M
>>906
> これ、ポインタが何段になっても p.m って書いて整合性取れるかい?
それは大丈夫だと思う
2017/07/16(日) 10:21:16.17ID:JuGvxIE40
>>910
俺はまだそこがちょっとひっかかるんだよな
デリファレンスが一個ずれるだけなら意味ないと思うしね
時間ができたら検証してみるよ
2017/07/16(日) 10:33:31.23ID:AkX0kyqa0
>>906
> これ、ポインタが何段になっても p.m って書いて整合性取れるかい?
実体になるまでデリファレンスしろ、というだけだから、出来なくはないと思うが。

> 格段便利ってわけでもないし、かえってややこしいかもなw
まあCがほぼ完成しているからな。導入する価値があるか微妙というのは同意。
> Cが見事にこなしていることは、全く"出来るだけシンプルにせよ、
> しかし、それ以上シンプルにするな"をしていることだ。
> そして、そのことがCを素晴らしいものにしている。言語はパワフルでありながら、ほぼ最小である。
> by Linus Torvalds
> https://srad.jp/~taro-nishino/journal/509450/


俺が思うに、Cに必要なのは階層(≒関数内関数)だよ。一部拡張されているようではあるが。
最近別言語だがCスタイルの記述(グローバル+関数、非オブジェクト指向)を読んだことがあって、
22K行のコードだが初見で簡単に目的のコードを探し当てられて、軽く衝撃だった。
Cが読みにくいのは100-500行のファイルで細切れになっているからであって、
あれ、設計者が分かりやすい順にcatしてくれていれば衝撃的に読みやすいことに気づいた。
2017/07/16(日) 10:47:18.34ID:AkX0kyqa0
あと、前方宣言必須というのも糞だ。
というか、今だにあれを放置している理由がよく分からない。

あれが無ければトップダウンで記述できるのでさらさら読める。
あれのおかげで下から構築しないといけないので、(include等つかって擬似的に回避できるが)
詳細まで確認する必要が無いときにも読まなくてもいい関数を読まされる事になる。

元々「世界の全てを把握して、絶対神として振舞え」という言語ではあるから、
「読みたくも無い関数を読まされたくねー」オブジェクト指向感性とは合わないが、
今更全てを把握できるほど世界は小さくないし、その必要が無いことも多い。
色々手抜きできる言語があることを知ってしまってからは、もっと手抜きさせてくれよーとは思う。
2017/07/16(日) 12:56:07.96ID:G64lD0g30
>>913
前方参照は確かにどうかと思うが、前方参照の制限が解消されたからといって読みやすさが改善するとは思えないね
現状でも底から読んでいけばいいだけなのではないか?
読みやすさは…識別子を日本語で書くのがよさそうだが
2017/07/16(日) 18:30:50.90ID:dVrh8pbL0
typedet struct
{
    void ( *reset_func )( void );
    unsigned long initial_stack;
    void ( *divide_by_zero )( void );
    ・・・
}    intvec_t;

#define INTVEC  ( *( intvec_t* )0 )
916デフォルトの名無しさん (ワッチョイ f146-I8+U)
垢版 |
2017/07/16(日) 21:14:38.36ID:TI5o59vg0
> 要するに、(*p).m を p.m と書けるということ

これ、できるできない以前に、初心者にきついな。
ルールを覚えるのは楽だけれど、例外事項が増えてくると、結局暗記になっちゃうからなあ。
917デフォルトの名無しさん (ワッチョイ 7d33-RIgB)
垢版 |
2017/07/16(日) 21:46:19.69ID:aJG+vjk10
ts
2017/07/16(日) 23:15:41.79ID:kT8dsikx0
>>913
プロトタイプ宣言というのがあってだね、それを宣言すればトップダウンで書ける。
919デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/17(月) 03:39:18.28ID:woO8V6Ze0
>>918
だよな
トップダウンなだけでなく
関数の一覧ができているという点でも
>>913が書いていそうな糞コードのDBL_MAX倍マシ
2017/07/17(月) 05:22:39.76ID:6JtF0HSC0
>>918
>>913はそれを知らないで書いてたのか?とするとかなりの初心者ということになるが。
2017/07/17(月) 05:32:30.17ID:6JtF0HSC0
まあしかし俺は同じファイル内にあるにも関わらずプロトタイプ宣言入れないと
わかってくれないのが嫌で使われる個所よりも上に書いちゃうけどな。
同じファイル内なんだからわかって欲しいものではある。

そういや PASCAL なんかも前方参照しかなかったような気がするな。
あの当時の言語はこういうの当たり前だったのかな。
PASCALなんかだとわざわざそういう思想で作られたって感じもするが。
Cだと手抜いただけのように見える。w
922デフォルトの名無しさん (ワッチョイ 8a1c-UU3S)
垢版 |
2017/07/17(月) 06:51:56.93ID:woO8V6Ze0
うん、Cのバヤイは確信的な手抜きだな
2017/07/17(月) 07:49:13.30ID:Dn7+fEGp0
ほー PASCALが前方参照しかないとか初めて聞いたわ

ID:kT8dsikx0とID:6JtF0HSC0の次の活躍に期待だな
2017/07/17(月) 07:57:41.59ID:HedtDN7o0
何時、前後を覚えるのかな?
2017/07/17(月) 08:01:01.05ID:n9t4u9yj0
>>921
Pascal は LL(1)言語としてつくってあり、ワンパスでパースできる、その意地があるんだね
2017/07/17(月) 08:11:52.63ID:PKmAGp8M0
Cもワンパスのため前方宣言必須ということのようだが、
一回舐めて拾うだけでいいんだし、今時こだわる必要も無いだろう
ヘッダに出した公開インターフェースは先、モジュール内プライベートはその下がわかりやすいよな
2017/07/17(月) 08:13:23.74ID:n9t4u9yj0
>>926
C はプリプロを除いてもワンパスにはならないと思う
2017/07/17(月) 08:53:08.22ID:U2FIHXXv0
>>918
>>913がプロトタイプ宣言知ってるかどうかは知らんけど同じ情報を二ヵ所に書かないといけないのはいかがなものかと思う
言語仕様を決めた当時はI/Oも遅いので高々数回のパースでコンパイルする必要あったからしょうがないとは思うが

>>921
Pascalは1-Passでビルドできるように言語仕様を決めていた
なので当初はモジュールみたいな概念もなかった
2017/07/17(月) 08:57:46.36ID:LYlgQVUQ0
>>920
さすがに知っているぞ。
俺は君と同様それはほぼ使わないというだけで。
というか、あの「事前に分かってないと使えない」事は正確には何と言うんだ?
「前方宣言必須」というのはどうも「前方宣言」自体が別の用語らしいのでまずかったようだ。

>>921
Cの場合、1パスコンパイルするためのものだ。
Cは紙テープ時代からある。
Wikiによると10文字/秒らしいので、1KBのファイルなら読み取りに1分40秒かかる。
これで2パスされると死ねるから、1パスでいけるように、
あらかじめ人間が順番を整えとけ(=機械に人間が合わせろ)というものだ。
どう考えても今はそんな時代じゃないだろ。
2パスに変更して「後方参照」(という用語でいいのか?)出来るようにすればいいだけだ。
紙テープの時代なら時代の要請だが、HDDの時代にこれを大事に守る理由は無い。
だから新しい全ての言語はこの制限は無い。必要ないからだ。
(ただしPythonを除く。この点だけでもPythonは糞だと断定できる)

ところがな、>>919みたいな老害は、
できる理由を見つけてきて頑なに現状維持しようとするものだ。
Cの場合は、確かに下から構築していけばプロトタイプ宣言は通常全く使わずに構築できる。
だからそれが作法になってしまってるだろ。
Pythonの場合はおそらくこれ、つまり、下からの構築を強制させるためにあえて採用してないのだと思う。

しかしな、他人のコードを一から読むとき、下から読む必要はなく、上から読んだほうが楽だ。
(正確には中レベルから。一番上のレベルも読む必要ないから)
お前らがそれに気づけてないのだとしたら、お前らはCしか読んでないからだ。
というか俺も最近までそうだったのだが。
2017/07/17(月) 08:58:08.57ID:LYlgQVUQ0
既に書いたが、Cの読みにくさは、ファイルが細切れになっていることもある。
これはOOPも別の意味で同罪で、「で、その処理は具体的にはどこに書いてあるんですかね?」は常だ。
だからそんなものだと思っているのだと思う。

ところが最近、後方参照できる言語でCスタイルで書かれているコードを読んで戦慄した。
圧倒的に読みやすいのだ。(OOPよりも)
上からスクロールしていくだけで、読み飛ばしていいか、そうでないか、はっきりと分かった。
ところが肝心のCにはこの類のソースコードは存在しないんだよ。後方参照禁止だから。

後方参照が出来るようになれば、設計者が自由に関数を配置できるようになる。
当然、一番分かりやすいように並べることになる。
今のCにはその自由度が無いんだよ。人間が機械に合わせる仕様だから。
「プロトタイプ宣言」とかいう二度手間をやらないと、最もわかりやすい順に並べられない。
だから今のCソースは基本的に「分かりにくい」。
少なくとも後方参照できればもっとわかりやすくなる方向でしかない。
だからいまだにそれを放置しているのはマジで糞だって事。
老害的には「下から構築しろ」という教育効果を主張するのだろうが、そんなのは要らない。
2017/07/17(月) 08:59:15.27ID:U2FIHXXv0
>>927
シングルパスでダメな構文あったっけ?
2017/07/17(月) 09:03:20.21ID:iqtGzeji0
ここで議論している人の 前方宣言 後方参照 の定義が一致しているのか気になる。
2017/07/17(月) 09:07:49.80ID:U2FIHXXv0
>>929
> (ただしPythonを除く。この点だけでもPythonは糞だと断定できる)
Python の def が「実行文」であることも知らんのだろうな w
2017/07/17(月) 09:11:05.59ID:LYlgQVUQ0
>>932
というか今更その辺の用語は無いんだよ。理由は他言語では必要ないから。
「後方参照」も正規表現でしか使われてないし、
しかもあれって「後方」よりも「バッファ」と言え、という類のものであるし。

とりあえず俺の定義は、
前方宣言必須:どうやらこれは俺の誤用だったすまん。「事前に宣言しておかないと使えない」の意で使ってた
後方参照:後で定義されている関数を使うこと
だね。これが適切かは分からんが、Cやってる奴ならあーはいはい程度には通じるとは思う。
2017/07/17(月) 09:14:46.40ID:LYlgQVUQ0
>>933
知らんね。
つかあれ、そうなのか。だとすると動的に構築するから致し方なし、って奴か。
JavaScriptが糞な点と同じだな。

まあどの道2パスすれば回避できるだけのことを、なぜやらん?ってのはある。
Pythonは聞けば聞くほど糞なので、俺はやってない。
2017/07/17(月) 09:19:12.83ID:PKmAGp8M0
>>927,931
たとえばgotoのラベルは下でもいいよね
たかだか関数内限定ではあるけど

>>932,934
今話してる文脈は「Cの前方宣言必須について」でいいんじゃないの?
2017/07/17(月) 09:39:52.04ID:PKmAGp8M0
引数が無い宣言のこと特別に「前方宣言」と言うのか
知らんかったわw
http://wisdom.sak ura.ne.jp/programming/c/c27.html
2017/07/17(月) 09:50:00.72ID:U2FIHXXv0
>>935
知らないなら黙ってりゃいいのに
知ったかはこれだから...
2017/07/17(月) 09:54:21.13ID:U2FIHXXv0
>>936
Pascalはラベルに数値が(と言うか数値しか)使えないこととコンパイラを単純にするためにlabel文で宣言が要るけど、コンパイラの実装としては必須じゃないでしょ
goto文の飛び先はラベル見つけた時点で入れればいいだけだし
2017/07/17(月) 10:26:39.93ID:+Y9zLnEF0
K&Rの時代じゃあるまいし、前方宣言を原型形式でない関数宣言子と捉える奴なんていねーだろ
プロトタイプ宣言とか言い出した>>918は例外として
2017/07/17(月) 10:42:28.15ID:LYlgQVUQ0
>>938
お前はPython信者なのか?ならばもう一度言ってやるよ。Pythonはそこも糞だ。

Pythonはdefで関数宣言を行い、それがそのままオブジェクトになる仕様らしい。
つまりそこで暗黙の代入があるから、後方参照できないとの理由だ。まさに糞だ。

JavaScriptの場合は、これらの宣言を分けている。つまり、
function func0(){console.log('func0');} // (A) console.logはCでいうprintf
var func1 = function(){console.log('func1');}; // (B)
ここでfunc0は後方参照できる。つまりスコープに入っていればいつでも使える。
func1は関数ポインタであり、代入以降でしか使えない。
これが妥当な仕様だ。
関数ポインタは再代入可能だから、順に処理する必要があるからだ。

Cの場合、関数ポインタへの代入は自前で行うわけだから、
コンパイラの努力だけで後方参照できないという制限を解除することが出来る。
いまだにやってないのはただの手抜きというよりも確信犯だろうが。

なおJavaScriptでもPythonと同様に関数はオブジェクトになるのだが、
要するに「スコープ内で先に処理して再代入禁止にしておくべきfunction(A)」と
「順に処理するべき関数ポインタ(B)」を明示的に分離して記述できるだけだ。
みたところPythonには(A)しかなさそうなので、技術的に出来ない理由は無い。
この点についてはCも同様に糞だが、時代の要請があったという理由はある。
Pythonは本当に何の意味も無く制限をつけている、ただの糞だ。
2017/07/17(月) 10:49:45.35ID:U2FIHXXv0
知ったかが慌ててググって的はずれの長文乙
Python 関数ポインタ
辺りでググる程度の知恵もないのが残念だが w
2017/07/17(月) 10:50:54.11ID:LYlgQVUQ0
>>937,940
俺もそれを知らんかった。
そしてそのページでそれを確認し、K&Rみたら確かに「プロトタイプ」となっている。
だからどうやら俺の誤用だった、とした。

ただまあ、その意味での「前方宣言」なんて見たことないんだけどね。
2017/07/17(月) 10:55:39.50ID:g3mBUieLd
Pythonはファイルの最後に
if __name__ == 'main':
main()

ってやる関係で、結局実行は最後になるからdefの順番とかで困ることはまずないな
せいぜい関数内関数定義で先に書くか後で書くかくらいか?
一体どんなコード書いてりゃそんなどうでもいいところで引っかかるんだ
2017/07/17(月) 10:57:04.61ID:LYlgQVUQ0
>>942
Pythonのdefは941で言う(A)なんだよ。
だから後方参照できない技術的理由は無い、という見解だ。
お前には通じないようだが。

それとは別に(B)の記述はPythonでも出来る。
というかこれが出来ない新しい言語なんて無い(ただしJavaを除く)
2017/07/17(月) 11:02:44.43ID:U2FIHXXv0
>>941
> みたところPythonには(A)しかなさそう

>>945
> それとは別に(B)の記述はPythonでも出来る。

バカの上塗り w
そもそも>>944が言うように前方参照の話ですらないのに何を必死になってるんだか
レス数が900を超えています。1000を超えると表示できなくなるよ。
5ちゃんねるの広告が気に入らない場合は、こちらをクリックしてください。

ニューススポーツなんでも実況