C言語なら俺に聞け 149

■ このスレッドは過去ログ倉庫に格納されています
2018/10/28(日) 22:01:44.38ID:D9Gt7gmT0
!extend:checked:vvvvv:1000:512

次スレを作る時は上記1行をコピーして2行に増やして必ず1行目に入るようにしてください。

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/

※前スレ
C言語なら俺に聞け 148
https://mevius.5ch.net/test/read.cgi/tech/1537347410/
VIPQ2_EXTDAT: checked:vvvvv:1000:512:----: EXT was configured
2018/10/29(月) 21:37:04.36ID:l03/lfXna
0x99b9e4313e3e
2018/10/30(火) 23:57:20.35ID:EION13qUM
自分を賢いと思っている馬鹿は
周りが自分をどう見ているかも
相手がどのレベルにいるのかも
なぜ自分が放置されてるのかも
何一つ知らない
2018/11/01(木) 16:13:41.13ID:upF+pHX50
musl-libcみたいに,特定のOSのプロジェクトではないPOSIXユーティリティの実装ってありますかね。
2018/11/01(木) 17:07:48.90ID:g+DLXddba
NewLibとかあったね
2018/11/03(土) 10:27:59.63ID:gIO4YTzK0
strtok_sを4変数にするとエラーになるんですけどどうしたらいいですか?
strmaxがある説明と無い説明があってわからないです。
2018/11/03(土) 11:28:06.76ID:hj5IrB61M
>>6
msvcのstrtok_sは非標準だから、_MSC_VERとかが定義されてるかどうかで呼び分けるしかないね。
あんまり覚えてないけどmsvcバージョンのほうが先にあった気がするから、iso/iecが悪い気がする。(間違ってるかも)
まあmsが切り替えスイッチを用意してくれればよいのだけど。
2018/11/07(水) 08:24:14.69ID:60G+FgCT0
>>7
よくわからないのでstrtokを使いました。
2018/11/07(水) 16:09:41.16ID:39tnP8GCx
ちょっとお知恵を拝借。

符号付き14ビットの整数があるとき(14ビットのMSBが符号ビット)、その値を符号付き16ビット値に拡張するうまいやり方はないでしょうか?
拡張後も符号や数値自体は変化なしです。
例えば2進で
10 1010 1010 1010
という符号付き14ビット値があった時、
1110 1010 1010 1010
のように変換したい。

14ビット値を16ビット符号付き変数に入れて左に2ビット論理シフトし、さらに右に2ビット算術シフトすれば実現できるのですが、何となく気持ち悪くて。
サクッとエレガントな方法はないでしょうか?
2018/11/07(水) 16:25:54.26ID:Gtw+mwj/H
>>9
シフトが一番エレガント。
2018/11/07(水) 18:02:56.37ID:d49i6th8M
>>9
2の補数表現として…
普通に14bit目が1なら0xc000とorするだけじゃないの?
12デフォルトの名無しさん (アウアウウー Sac7-AdN2)
垢版 |
2018/11/07(水) 18:16:05.56ID:bimd4khFa
もはや答えが出切ったと思うので斜め上からの回答でも書いておくか。

回答

int型が14ビットの整数型になっているCコンパイラを使う。
もちろんchar型は7ビット。
CPUは1バイトが7ビットである。
2018/11/07(水) 19:11:16.88ID:d49i6th8M
それ16bitの結果得るのが面倒なだけだろ
もう少し面白い回答頼むわ
2018/11/07(水) 19:12:35.33ID:xr+D7aWAM
皆様回答ありがとうございます。
今回はビットシフト方式で行こうと思います。

>>12
使ってるCPUとコンパイラがマイナーな、ある意味純粋な16ビット環境で、sizeof(char)もsizeof(short)も1を返し、sizeof(long)は2を返すような特殊な環境なので7ビットマイコンではありません。
2018/11/07(水) 19:46:07.55ID:SCUqGzCI0
intが14ビット
そんな処理系あるの?
16デフォルトの名無しさん (アウアウウー Sac7-AdN2)
垢版 |
2018/11/07(水) 20:47:19.69ID:bimd4khFa
>>15
多分ない。
しかし1バイトが6ビットとか9ビットのマシンはあったようだよ。
https://qiita.com/yaju/items/c5da6df2221d5c3611e0
2018/11/07(水) 20:49:47.59ID:YuYLxFMn0
60〜70年代メインフレームは百花繚乱だったなぁ

ttps://en.wikipedia.org/wiki/Word_(computer_architecture)
27bitマシンとかどーすんだよ
2018/11/07(水) 20:55:36.02ID:Lazgvcn1M
このように1バイトが何ビットかはアーキテクチャ依存のため、EUではハードディスクなどのパッケージにはGB単独表記は認められず、Go(ギガオクテット)を併記または単独で表記しなければならない。
1オクテットは必ず8バイト。
2018/11/07(水) 21:07:14.78ID:fEoWtkRgM
つまりEUでもHDDの容量はわからないってことか
2018/11/07(水) 21:09:34.64ID:u7stYdWj0
>>18
いや、Octetは8ビットでは?
2018/11/07(水) 21:12:33.55ID:Lazgvcn1M
そうでしたwwwww
22デフォルトの名無しさん (アウアウカー Sac3-U2lQ)
垢版 |
2018/11/07(水) 21:19:59.22ID:h4FWJh3Ka
大丈夫。
文脈から理解はしてる。
上げ足取りなだけだ。
2018/11/07(水) 21:47:40.71ID:lW24kLVO0
バグってそういうもんだろ
笑ってられる神経が異常だ
24デフォルトの名無しさん (ワッチョイ 5b80-Q1ft)
垢版 |
2018/11/07(水) 23:27:18.47ID:fWOqg0Pc0
バカってそういうもんだろ
2018/11/08(木) 00:45:35.31ID:LWRNNBjj0
>>12
CHAR_BIT は 8 以上、 INT_MAX は 32767 以上って規定があるから、規格非準拠になっちゃう。
2018/11/08(木) 22:02:06.26ID:WtJgli4G0
だから何? 違ったら笑うしかできない無能か
2018/11/08(木) 22:55:19.89ID:nQ7J47/rx
C89止まりのものです
私のような者が C11などの新しい規格を学ぶのによい書籍はありますか?
2018/11/08(木) 23:16:18.68ID:x4oYjs6S0
このスレは最近独り言が増えたのか?
オレもそうだがな
2018/11/08(木) 23:21:07.60ID:PviajTiD0
>>27
>C89止まりのものです、私のような者が C11などの新しい規格を学ぶのによい書籍はありますか?
私もC89止まりですが、それで困ることがあるのでしょうか?
2018/11/08(木) 23:28:43.81ID:6k9Hci0C0
>>29
私はC99で止まっていますが、最近はもっぱらPythonを使っているので困りません
2018/11/09(金) 05:43:42.12ID:1ixP0EQ90
pythonいいよな
yieldとかC標準にもほしい
2018/11/09(金) 10:07:36.38ID:6cegpcYL0
cpythonのyield実装を見ればC言語に移植できるんじゃねえの
2018/11/09(金) 11:42:49.67ID:Sh6b3ug/a
yieldって何につかうの?
34デフォルトの名無しさん (アウアウカー Sa9d-Gc0T)
垢版 |
2018/11/09(金) 12:33:54.85ID:DHGOZxvaa
動き的にgets的な動きする。
表示したら即メモリ解放的な。
2018/11/09(金) 12:41:29.53ID:GUqFOdkWM
>>31-32
yieldはソース上に出ないデータを管理しないといけないからC言語の理念と合わない気がする
※ 個人の感想だが…
C++には欲しいな
2018/11/09(金) 12:52:21.62ID:1VeVq06f0
yieldはいわばスタック情報の保存だから、setjmp、longjmpで出来そうな出来なさそうな?
37デフォルトの名無しさん (アウアウウー Sa05-ahuQ)
垢版 |
2018/11/09(金) 13:11:31.21ID:JsSTi+Gxa
ん?thread?
2018/11/09(金) 13:52:10.49ID:Sh6b3ug/a
単にコンテキスト保存するだけだからまあ再現はできるよ
書き方としてイテレータとか欲しいのはわかるけど実現方法はどうでもいいわけじゃん
2018/11/09(金) 14:11:15.88ID:lOb1tGzl0
yieldは便利で使い勝手がいーるど
2018/11/09(金) 20:13:38.25ID:3ZHBVzZ50
POSIXの<errno.h>にある番号とBSDの<sysexits.h>で全然番号が違うのは理由があるのかな。
いままで<sysexits.h>に従って「許可がない」動作は77を返すものだと思ってたら
Linuxでは1を返すのでなぜだと思って調べたら<errno.h>では権限エラーは1。
嫌だなぁ。
2018/11/09(金) 20:53:23.68ID:GUqFOdkWM
77とか1とかのリテラルで書くバカって今でもいるんだ…
2018/11/09(金) 23:18:17.74ID:Sh6b3ug/a
POSIXで具体的な数値決めてたっけ?
43デフォルトの名無しさん (ワッチョイ db9f-ki2E)
垢版 |
2018/11/10(土) 05:46:23.69ID:PYYpj2JU0
>>40
<errno.h> の方はC言語でシステムコールしてエラーになった時の errno 変数の値で、
<sysexits.h> はプログラムが exit() 等で終わる時に使う値なので全く用途が違う。
2018/11/10(土) 06:30:10.24ID:lBOHSSIo0
>>43
つまり<errno.h>で定義された値はユーザーからは見えないんだね。
45デフォルトの名無しさん (ワッチョイ db9f-9t8X)
垢版 |
2018/11/10(土) 06:43:06.70ID:PYYpj2JU0
>>44
見えないというか、ただの数値なのでどこにでも使えないわけではないが、errnoの値をexit()で返す事は想定して作られていない。
2018/11/10(土) 11:37:20.64ID:lMF42kZL0
>>45
わりとerrnoを返してくる人多いけどね
2018/11/10(土) 11:58:28.71ID:4Oh2WWEl0
errno返してもらっても困る
2018/11/10(土) 17:42:25.30ID:16GnFLu/0
#defineマクロ定数はプリプロセッサで単純置換されるだけだからな
49デフォルトの名無しさん (アウアウウー Sa05-ahuQ)
垢版 |
2018/11/10(土) 18:12:43.61ID:JVjCprWqa
>>46
多いか?
別にそう作っちゃいけないということはないが、できれば exit() では <sysexits.h> の方を使って欲しいな。
単なる個人的な希望だが。
2018/11/10(土) 18:13:54.94ID:lBOHSSIo0
>>45
>>46
ありがとう。
ユーティリティ自体の終了ステータスはPOSIXの範囲では0もしくは非0,
BSD拡張で<sysexits.h>で定められている値を使えば まあユーザーの助けにはなるって認識でいいかな。
51デフォルトの名無しさん (アウアウウー Sa05-ahuQ)
垢版 |
2018/11/10(土) 18:26:46.25ID:JVjCprWqa
そう。
52デフォルトの名無しさん (ワッチョイ 937f-nWRh)
垢版 |
2018/11/11(日) 12:27:27.91ID:2PA7tL2j0
struct S {
size_t len;
type-X buf[0];
};
という状況下で、

size_t const len = 500;
struct S* const p = (struct S*)malloc(sizeof(struct S) + sizeof(type-X)*len);

p->len = len;
p->buf = (type-X*)((size_t)p + sizeof(struct S));

という処理を偶に見かけますが、これだと末尾パディングの影響でbuf[1]のアドレスがtype-Xのアライメントに沿っていない可能性があるので、不正な気がします
具体的には

struct S {
size_t len;
type-X* buf;
};
として、

size_t const len = 500;
size_t const padding_for_align_x = alignof(type-X)*(sizeof(struct S)%alignof(type-X) == 0 ? 0 : 1);
struct S* const p = (struct S*)malloc(sizeof(struct S) + padding_for_align_x + sizeof(type-X)*len);

p->len = len;
p->buf = (type-X*)((size_t)p + sizeof(struct S) + padding_for_align_x);

...などとしないとアライメント違反になりそうな気がするのですが、この認識は正しいでしょうか
2018/11/11(日) 12:57:16.34ID:2PA7tL2j0
すいませんよく考えたら自己解決しました
>>52の質問は取り下げます

お騒がせしました
2018/11/11(日) 14:07:31.98ID:PRctJ18Z0
>>4
へー。musl-libc知らなかったけど組込Linuxとかの界隈では有名っぽいね。
ソース見たけどすごく短かいのが多くて逆に不安になったw
2018/11/11(日) 15:17:31.04ID:0RasjQan0
sysexits.h って初めて知った

>>49
Linuxとかだと ls unko で 2 が返るとか割と普通
2018/11/11(日) 16:17:47.42ID:PRctJ18Z0
>>55
まあBSDでプログラミングしたことないと あんまり知りえないと思うわ。
だいたいPOSIXで定められてる訳じゃないから 知っておくべきなのはBSDプログラマくらい。

ただLinuxプログラムのエラーコード周りはなぜか非統一的なんだよね。
GNUコーディング規約で事細かに決められてそうなものだけどねw
apt(1)なんて権限エラーに100返すんだぜ?
2018/11/11(日) 16:41:45.09ID:PCIE9alw0
>>52
『MSDNこそC++である』という格言があるように、構造体の末尾の配列は不定長に出来ます

構造体内の可変長配列
ttps://msdn.microsoft.com/ja-jp/library/b6fae073(v=vs.120).aspx
2018/11/11(日) 18:01:07.65ID:EYHizhRi0
VLAとは違うんだよな
そのページのサンプルに限っては不完全型配列の直前にサイズ情報があって確かに可変長だが
配列そのものがサイズ情報を含むのではないので、不定長とでもいうべきものだ
2018/11/11(日) 18:07:53.58ID:PRctJ18Z0
どうでもいいけど そのURLの書式はなんだ?
URLパラメータってそんな位置に置けたっけ。
2018/11/11(日) 18:21:19.83ID:1ROtIrLE0
先頭さえ確定できれば後ろなんてどうでも良い
さすがのC言語さん
2018/11/11(日) 21:36:09.88ID:1MIvJQ9R0
>>57
その格言は初めて聞きましたw

その方法だとアライメント違反になるかならないかが気になっていたのですが、
* 末尾のbuffer[0]でその型のアライメント以上のアライメントを構造体に強いることができる(拡張)
* 末尾のbuffer[1]の場合は当然構造体にそのアライメント以上のアライメントを強いることができる(c89)
* 末尾のbuffer[]でも同様(c99での仕様)
となり、全パターンでbuffer[i]へのアクセス時にアライメント違反にならないので、
ポインタメンバにしてアライメント気にしてmallocする必要ないのかー、これでいいのかーと解決した次第です

>>58
英語だとflexible arrayでした
2018/11/11(日) 22:09:10.99ID:3Du2sMqla
>>59
v=vs.120のとこ?
クエリストリングちゃうやろ
63デフォルトの名無しさん (ワッチョイ db9f-ki2E)
垢版 |
2018/11/11(日) 22:26:25.11ID:0F8Q4Ddx0
>>55
ま、確かにコマンドごとにバラバラだな。
errno とも無関係だったりする。
2018/11/12(月) 13:20:45.59ID:JkRQG90v0
もうちょっと皆がリターンコードについて考えてくれたらいいね。
2018/11/12(月) 13:26:58.93ID:yW6s8Lj00
コマンドの戻り値って、皆さんどの様に活用されてますか?
成功か失敗か、それが分かれば十分な気はしますけど
2018/11/12(月) 13:50:25.07ID:JkRQG90v0
>>65
例えば同じ「失敗」でも何が原因なのか分かったほうが問題に対処しやすくない?
ファイルが存在しないのか はたまたファイルが現状の権限では読みとれないのか。
もちろんエラーメッセージを見てもいいけど。

あと,終了ステータスを見ないと成功失敗が分からない場合がある。
例えばdiff(1)ユーティリティーなんかは「1」という(一見失敗してるような)終了ステータスに
「(コマンド自体は成功してるが)不一致が発見された」という意味を割り当ててる。
fsck(1)ユーティリティーはもっと複雑。

まあ知ってるに越したことはないし<sysexit.h>はPOSIX標準ではないにせよ,
Unixプログラミングをする場合は積極的に利用してもいいかも。
2018/11/12(月) 14:11:20.80ID:yW6s8Lj00
イヤ、使い方の可能性としてそう言うものがあるくらいは知っている
実際に使っている人がいたら、どういう使い方をしているかを聞きたいんだ
2018/11/12(月) 16:42:56.85ID:JkRQG90v0
勘違いしてましたわ
俺の知ってる限りじゃシェルスクリプトでは多用されてるがCではどうだろうね。あまり見掛けない。
2018/11/12(月) 17:16:29.53ID:7RdsKszja
diffでちょっと迷うくらいだよな。
2018/11/18(日) 22:01:33.04ID:Fz4U8sel0
#define elif(e) else if (e)
みたいにして
if (...) {
...
} elif (...) {
...
} else {
...
}
↑こういう感じにするのってやっちゃマズいのかな。
個人的にelifキーワードがある言語に慣れてるんでこうやってて
現状特にエラーに遭遇したことはないんだけど
OSSのソースコードとか個人が公開してるソースコード見ても
こういうことやってないんだよね。
2018/11/18(日) 22:14:05.51ID:Eond7dK60
>>70
やめとけ

メリットが1ミリもないから誰もやらない。
善し悪しはさておき、C言語での判断基準はほぼ「実行性能」であって、
else if と書けばいいだけの所をいちいちマクロにする馬鹿なんて世界中に誰もいないだけ。
というか、そのレベルで慣れられないのなら、elif言語だけ使っておけ。
2018/11/18(日) 22:24:21.65ID:KTJRdzRs0
#define { begin

みたいなことを本気でやる奴がいたとはw
■ このスレッドは過去ログ倉庫に格納されています
5ちゃんねるの広告が気に入らない場合は、こちらをクリックしてください。

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