2ちゃんねる スマホ用 ■掲示板に戻る■ 全部 1- 最新50    
レス数が1000を超えているけど、まだ書けるかも知れないよ。

SQL質疑応答スレ 15問目

1 :NAME IS NULL:2014/06/16(月) 20:52:29.14 ID:???.net
このスレは
「こういうことをやりたいんだけどSQLでどう書くの?」
「こういうSQLを書いたんだけどうまく動きません><」
などの質問を受け付けるスレです。

SQLという言語はISOによって標準化されていますが
この標準を100%実装したDBMSは存在せず、
また、DBMSによっては標準でない独自の構文が
追加されていることもあります。

質問するときはDBMS名を必ず付記してください。

【質問テンプレ】
・DBMS名とバージョン
・テーブルデータ
・欲しい結果
・説明

前スレ:
SQL質疑応答スレ 14問目
http://peace.2ch.net/test/read.cgi/db/1371476534/

964 :NAME IS NULL:2015/10/12(月) 20:04:23.95 ID:5QQ971OL.net
>>963
何がやりたいの?

検索ってどういう条件?

965 :NAME IS NULL:2015/10/12(月) 20:18:07.51 ID:???.net
>>963
その比較はお前が書くプログラムのレベルを考慮しないと意味が無い

数千件程度なら、C++で書く方が早いかもしれん
何件でも、データのあり場所次第では、C++で最適化されたプログラムが書ければそっちが早いかもしれん
今時のDBMSがオールアセンブラで書かれてるとは思えんしな

そもそも、単純な「検索だけ」の速度なんて比較しても意味が無い
DB使うなら、DBからC++のプログラムにデータを取り込む時間も込みで考えないと

966 :NAME IS NULL:2015/10/12(月) 20:24:02.87 ID:???.net
>>965
>かもしれん
>思えんしな
何の説明にもなっていないアホな回答の典型だな

967 :NAME IS NULL:2015/10/12(月) 20:58:43.29 ID:???.net
>>963
DB無しで作る場合、
配列にセットするデータはどこから取ってくるつもり?

最初から配列が用意されてるならDB無しの方が早いだろうけど、数千件程度ならミリ秒レベルの差だよ。

名簿検索プログラムをDB無しで作る事は稀なので、
余計な事は気にせず勉強に取り掛かった方が良い。

968 :NAME IS NULL:2015/10/12(月) 21:14:41.69 ID:???.net
ローカルDBって要するに開発用PCにインストールしたDBの事だろ
それとオンメモリの配列じゃ話にならん。
圧倒的的に配列の方が早いわ

969 :NAME IS NULL:2015/10/12(月) 22:41:02.00 ID:???.net
ま、2倍くらいでしょw

970 :NAME IS NULL:2015/10/12(月) 22:50:40.56 ID:???.net
要求されたコードを実装できる人がやるという前提なら、
特定の検索条件に特化して作るならC++の方が速いかも知れない。
ただ、検索条件を変えたいとなると、辛いことになるだろうな。

971 :NAME IS NULL:2015/10/12(月) 23:47:29.35 ID:???.net
>>967
その程度にミリ秒もかからないで欲しい。

>>968
だね。

972 :NAME IS NULL:2015/10/20(火) 11:04:13.11 ID:???.net
MySQLテーブルの設計についての質問です。
ひとつの製品が複数のカテゴリに属する可能性のある場合、TINYINT(1)を用いて

id name cat1 cat2 cat3 ……
----------------------------------
1 製品A 1   0   1
2 製品B 0   0   1
3 製品C 1   1   1
4 製品D 1   1   0

という形(0もしくはNULL)で作成しているのですが、
このcat1、cat2等のカテゴリ自身も、例えばcat4を新設したり削除したりなど
可変にする場合はどういう構造にするのが良いのでしょうか。
現状は、変更があった場合に直接DB構造やUI側を修正しています。

以下の様にテーブルを分け、コンマ区切りで取り出して
スクリプト側で配列に分離するというのも考えたのですが、
これはやってはいけない方法だと聞きました。

id name cat
---------------
1 製品A 1,3
2 製品B 3
3 製品C 1,2,3
4 製品D 1,2

id name
---------
1 cat1
2 cat2
3 cat3

基本的なDBの設計思想をまだ理解しておらず見当外れだとは思いますがよろしくお願いします。

973 :NAME IS NULL:2015/10/20(火) 11:42:23.33 ID:???.net
それで問題なく運用できてるならそれでもいいんじゃないのと思うけどね。
カテゴリが増えるたびに列を増やすのが手間、あるいは問題だと考えてるのならこうする。

id name
--------
1 製品A
2 製品B
3 製品C
4 製品D

id name
---------
1 cat1
2 cat2
3 cat3

id1 id2 ←名前は適宜変えて。product_id category_id とか。
------
1  1
1  3
2  3
3  1
3  2
3  3
4  1
4  2

974 :NAME IS NULL:2015/10/20(火) 21:39:39.43 ID:???.net
初歩的だし、何度も質問あるだろうけど
inとexistsの違いを教えてください

975 :NAME IS NULL:2015/10/20(火) 22:23:37.39 ID:???.net
自分が考えていることが初歩的だと思い込むのはよくない。
それではいつまで経っても初心者のまま。
本当に初歩的であればいくらでもネットに情報はあるのでまずは検索すること。

976 :NAME IS NULL:2015/10/20(火) 23:05:23.09 ID:???.net
>>973
ありがとうございます。
練習のためにも、そのやり方で作成してみます。

977 :NAME IS NULL:2015/10/20(火) 23:18:30.90 ID:???.net
>>974
inは項目がリストに存在するかどうか
existsは行がサブクエリに存在するかどうか

978 :862:2015/10/20(火) 23:35:27.58 ID:???.net
ありがとうございます。
調べてはいるんですが、
inは副問い合わせをした条件の属性?を探す
なんとなくわかるんですが、
existsのサブクエリ存在するしないというのは
存在しないという時点で探すのをやめるということなんでしょうか

979 :NAME IS NULL:2015/10/21(水) 00:08:24.21 ID:???.net
>>978
逆。EXISTSは存在した時点で探すのをやめることができる。
一個でもあれば、ある。NOT EXISTSは一個もないことを調べるために途中で打ち切ることができない。

まず検索しろと書いたものの、INよりEXISTSの方が速いからどんどん使うべきという情報が
まだ多く残っていると思うので、その辺は鵜呑みにしないほうがよいかと。

んで、挙動的にはEXISTSのほうが多重ループをしている感じが強いと思っておけば何かの足しになるかも。

980 :NAME IS NULL:2015/10/21(水) 00:19:13.14 ID:???.net
in と existis どっちが速いか
inner join の方が速いよって話もあるし自分で書いて計ってみたほうがいいな

981 :NAME IS NULL:2015/10/21(水) 03:52:06.89 ID:???.net
>>978
inと副問い合わせは直接関係ない
inの対象にするリストを(副)問い合わせで作れるってだけ

inとexistsでどちらが早いかという話は、そのクエリ全体から実行計画を見ないと無意味
状況によっては全く同じ実行計画になる可能性もある
そもそもSQLは書いたとおり実行されるものではないから、どの命令が早いとか遅いとかはない

982 :NAME IS NULL:2015/10/21(水) 03:55:19.68 ID:NNtjMknF.net
>挙動的にはEXISTSのほうが多重ループをしている感じが強いと思っておけば
こういうのも鵜呑みにしちゃダメだぞ

983 :NAME IS NULL:2015/10/21(水) 19:10:19.27 ID:???.net
>>982
すいません
情報処理試験とかで4たくで出られると
分けわかんなくなるんですよね
基本情報レベルなら大丈夫ですが
こういうのって直接触ってみるのが
一番手っ取り早そう

984 :NAME IS NULL:2015/10/21(水) 19:14:47.36 ID:???.net
確かに早いのはexistsってのは聞きますね
ケースバイケースなんでしょうけど
副問い合わせと相関副問い合わせってのがあるんですね
そのあたりも見てみようと思います

985 :NAME IS NULL:2015/10/21(水) 22:26:00.56 ID:???.net
dbからORDER BYを用いてソートした状態で取り出す際、行に対して「任意の順序」を定義することはできるのでしょうか?

例えば行構造が<id, state_A, state_B, state_C>となっていて、行をとるbinary predicateが
両辺共にstate_C==αのときにはidによる順序
両辺共にstate_C!=αのときにはstate_Bによる順序(state_Bには順序が定義されているとする)
両者が異なる場合には……

という具合です

986 :NAME IS NULL:2015/10/21(水) 22:51:22.14 ID:???.net
order by
 case
  when left.state_C = α and right.state_C = α then id
  when 〜 then state_B
  when

複数カラムでソートする場合はソートできる状態の文字列にする+そういうインデックスを作るといいかも。

987 :NAME IS NULL:2015/10/21(水) 23:12:10.98 ID:???.net
>>986

アドバイスも添えて下さりありがとうございます
明日試してみます

988 :NAME IS NULL:2015/11/07(土) 16:10:57.12 ID:+XbcKiq/.net
>>985
SQLを分けるのが普通だと思う。

無理に一緒にしたら、あとのメンテナンスが面倒。

989 :NAME IS NULL:2015/11/08(日) 15:38:58.68 ID:???.net
分けてunionとかかな?

990 :NAME IS NULL:2015/11/08(日) 23:59:31.78 ID:a7cMoyHv.net
>>989
やるとしたらunion allだけど、レコード順が保証されない気がする。

2回に分ける方が確実。

991 :NAME IS NULL:2015/11/09(月) 10:39:28.94 ID:???.net
order by database_func()
とかできたらいいのに。

992 :NAME IS NULL:2015/11/09(月) 10:51:22.91 ID:???.net
え、それはできるっしょ

993 :NAME IS NULL:2015/11/09(月) 16:31:06.51 ID:???.net
>>992
あ、書き方が悪かったかな。
一般的なプログラミング言語のソートにおける比較関数みたいなのが書ければなぁってこと。
function compare_func(rec1 as table1.recordtype, rec2 as table1.rectype)
みたいな関数を定義して、
order by compare_func()
って書けるといいなと妄想。

994 :NAME IS NULL:2015/11/09(月) 17:04:43.98 ID:???.net
まあそれは手続き型言語の考え方だな
SQLの思想には合わないだろう

995 :NAME IS NULL:2015/11/09(月) 19:01:33.56 ID:???.net
多くのDBMSではユーザ定義関数が作れるしorder byにも使える

996 :NAME IS NULL:2015/11/10(火) 22:24:19.13 ID:???.net
次スレ
http://peace.2ch.net/test/read.cgi/db/1447160858/

997 :NAME IS NULL:2015/11/11(水) 15:23:07.11 ID:???.net
>>994
ユーザ定義型についてはそれが行えてもさほど不自然じゃないと思う

998 :NAME IS NULL:2015/11/11(水) 18:56:41.55 ID:3mpv2MQg.net
>>997
ユーザー定義型?

999 :NAME IS NULL:2015/11/11(水) 20:41:56.94 ID:???.net
>>993から話がおかしい

1000 :NAME IS NULL:2015/11/11(水) 23:19:10.04 ID:???.net
>>999
一般的かどうかは知らんが、自作の比較関数を渡してソートできるプログラミング言語はある
多くのDBMSでユーザ定義関数は作れる
ユーザ定義型をサポートしているメジャーなDBMSは存在している

個別に見れば、なにもおかしくないけど
どこがどうおかしいと?

1001 :NAME IS NULL:2015/11/12(木) 00:28:30.86 ID:LOOLB3CF.net
ユーザー定義型とユーザー定義関数は別物だろうが。

1002 :NAME IS NULL:2015/11/12(木) 03:29:27.86 ID:???.net
マ板やム板じゃないからC知らない人がいてもおかしくないか。
そう考えれば合点のいくレスがちらほら。

1003 :NAME IS NULL:2015/11/12(木) 08:05:14.16 ID:???.net
>>1000
ものすごく一般的なんだけど、SQLはORDER BY句でソートキー取得用関数を使ってソート出来るようになっている。
これでも分からんか?

1004 :NAME IS NULL:2015/11/12(木) 10:13:39.56 ID:???.net
SQLでは、一般のプログラミング言語には良くある2レコードの比較関数を作って渡すことが
できないってことで、言われてみて初めて気づいた。

1005 :NAME IS NULL:2015/11/12(木) 12:33:02.59 ID:???.net
そもそもソートに比較関数を使うのは筋の悪い方法だから、むしろ使えない方が良い設計。
SQLで使えないのは理由が違うが。

1006 :NAME IS NULL:2015/11/12(木) 19:56:43.64 ID:???.net
>>1003は比較関数を理解してなかったってことでOK?

1007 :NAME IS NULL:2015/11/12(木) 20:37:20.84 ID:???.net
比較関数を使わずともソートはできるよということを言いたいんじゃない?
元も子もないなって思うけど。

1008 :NAME IS NULL:2015/11/12(木) 20:46:46.68 ID:???.net
「できるよ」じゃないんだよな。
>>1005にも書いたけどより良い方法(>>1003)が可能なのに
あえて筋の悪い、具体的には遅い比較関数を使う必要がないということだ。

1009 :NAME IS NULL:2015/11/12(木) 20:58:20.72 ID:???.net
理解しているんだろうけど
比較関数はSQLとは関係ない話だろう

1010 :NAME IS NULL:2015/11/12(木) 22:14:48.10 ID:???.net
速いとかとか遅いとかどういう根拠なんだろうな

1011 :NAME IS NULL:2015/11/12(木) 22:15:25.84 ID:???.net
途中から入るけど
SQLとプログラミングで作成するソートがごっちゃになってる
って話でいいの?

1012 :NAME IS NULL:2015/11/12(木) 22:21:48.55 ID:???.net
話の途中で悪いが1000ゲト

1013 :2ch.net投稿限界:Over 1000 Thread
2ch.netからのレス数が1000に到達しました。

301 KB
新着レスの表示

掲示板に戻る 全部 前100 次100 最新50
名前: E-mail (省略可) :

read.cgi ver 2014.07.20.01.SC 2014/07/20 D ★