07/10/27 21:09:21 OP1e5oAp
参考リンク
URLリンク(sql.main.jp)
URLリンク(www.atmarkit.co.jp)
URLリンク(oraclesqlpuzzle.hp.infoseek.co.jp)
URLリンク(www.techscore.com)
前スレ:【帰ってきた】SQL質疑応答スレ 4問目
スレリンク(db板)
質問テンプレ
・DBとバージョン
・テーブルデータ
・欲しい結果
・説明
2:NAME IS NULL
07/10/28 05:58:02
過去ログ
SQL質疑応答スレ スレリンク(db板)
SQL質疑応答スレ Part 2 スレリンク(db板)
【帰ってきた】SQL質疑応答スレ スレリンク(db板)
【帰ってきた】SQL質疑応答スレ 2問目 スレリンク(db板)
【帰ってきた】SQL質疑応答スレ 3問目 スレリンク(db板)
【帰ってきた】SQL質疑応答スレ 4問目 スレリンク(db板)
3:NAME IS NULL
07/10/28 12:24:13 HNaUJLCG
sqlite3です。
zip(
pubcode INT
,zip5 CHAR(5)
,zip7 CHAR(7)
,pref_k TEXT
,city_k TEXT
,town_k TEXT
,pref_j TEXT
,city_j TEXT
,town_j TEXT
);
で
SELECT zip7,pref_j,city_j,town_j FROM zip WHERE 0=0 AND city_j = 'hoge'
LIMIT 5
みたいな事をしているのですが、
WHERE 0=0の意味が分かりません。
「WHERE句の条件の所で0=0という妙なものが入っていますが、
コレはコーディングを簡略化するための小技です。
SQL文を動的に作成する場合、条件検索が複雑になってくるとWHERE句が
長くなってきますが、SQL文を文法的に正しくするため、
条件を動的に増やすたびに、その直前にWHEREを付けるかANDを付けるかを判断する必要が有ります。
ここでは、WHERE 0=0というダミーの条件を頭につける事で、後は機械的にANDでつなげば良いようにしています」
という説明が有るのですが、いまいち理解出来ません。
何か具体例はないでしょうか?
4:NAME IS NULL
07/10/28 12:42:13
>>3
スレ違いなんだが、最後の文句
> 後は機械的にANDでつなげば良いようにしています
がすべてじゃね。
とりあえずPHPで書くと、
$where = "WHERE 0=0 ";
if ($pref) $where += "AND pref_j=$pref ";
if ($city) $where += "AND city_j=$city ";
if ($town) $where += "AND town_j=$town ";
$sql = "SELECT * FROM zip $where LIMIT 5";
ってことだろう。
俺なら配列に入れておいて" AND " でJOINするけどな。
5:NAME IS NULL
07/10/28 12:46:20
うげっ、堂でもいいが
if ($pref) $where += "AND pref_j='$pref' ";
if ($city) $where += "AND city_j='$city' ";
if ($town) $where += "AND town_j='$town' ";
' 'でくくるの忘れてt。
6:NAME IS NULL
07/10/28 21:59:15
>>4,5
アルバイトで返事が遅れました。
すいません、SQLに初めて触るので不理解です。
えっと、SELECT文にはWHERE句を入れなければならないけれども、
この場合WHERE hogeで固定すると、引数に応じた柔軟なSQL文を発行するのが
めんどくさい。
そこで、WHERE 0=0として引数に応じてANDで追加したら、コーディングが
楽になると言う理解でよろしいでしょうか?
ちなみに WHERE 0=0ってどういう意味なんでしょうか?
今までの場合だと、
WHERE zip7とかWHERE 100といった直接指定しか習っていないので、
0=0の意味が良く分からないです。
7:NAME IS NULL
07/10/28 22:31:01
>>6
0=0は常に真となるダミーの条件。
つけてもつけなくてもSQLの意味としては全く同じ。
なんで必要かが分からないうちはつけなくていい。
プログラムでSQLを自動生成するようになれば
おのずと分かるようになるよ。
8:NAME IS NULL
07/10/28 23:34:47
なんで TRUE じゃないのか俺にもわからん
9:NAME IS NULL
07/10/29 11:02:14
where TRUE って書くとそんなカラムはねーって言われるからだな。
10:NAME IS NULL
07/10/29 12:01:11
MySQLへphpmyadminを介してインポートするために、
直接連絡の取れない会社に「テキストでのsqlダンプ」をくださいといったのですが、
秀丸で開くとバイナリっぽい感じがするデータが来ました。
TAPE <文字化け> microsoft SQL serverと1行目にあるのですが、
これはテキストでのsqlダンプなのでしょうか?
完全なテキストデータでは、microsoft SQL serverはエクスポートできないのでしょうか?
11:NAME IS NULL
07/10/29 20:22:15 BxcL5p6/
a, b, c
-------
1, 0101, 100
1, 0101, 200
2, 0102, 300
2, 0103, 400
というようなテーブルがあって、
a, count(b), sum(c)
-------------------
1, 1, 300
2, 2, 700
というようなのを取得するにはどうすればいいのでしょうか。
まず group by a をするのは思いついたのですが、b の扱いに悩んでいます。
postgres なんですが、サブクエリを使って二段階で処理すれば
いけるのかなとは思っているのですが、できれば一発で処理したいです。
12:NAME IS NULL
07/10/29 20:29:42
>>11
SELECT a,count(DISTINCT b),sum(c) FROM Table GROUP BY a;
13:NAME IS NULL
07/10/29 20:48:55
>>12
ありがとうございます。
DISTINCTって、集約関数の引数の欄にも書けるんですね。驚きました。
14:NAME IS NULL
07/10/29 20:50:59
>>10
スレ違い。「BCP でエクスポートしてね」って頼め。
詳しくは、SQL Server の専用スレで。
15:NAME IS NULL
07/10/30 00:14:05
質問ですが、SQLに於ける、
ボイスコット正規形がちんぷんかんぷんで解りません・・・・。
ので、解説お願い致します。
なるべくイメージが攫み易いように比喩など使って戴けると幸いです。
あと、調べた限りですと、
非キー項目から主キー項目を特定する事が出来てしまう(主キーが非キー項目に関数従属している)らしいのですが
どうして、このように特定できてはいけないのでしょうか?
16:NAME IS NULL
07/10/30 14:00:25 sO7Hyn8f
質問です。
レコードが4つあり、idがユニークで 1 2 4 6 という値が入っています。
このテーブルにインサートしたいのですが、SELECT MAX(id) の結果に
1を足した値をインサートする方法だと、いつかはオーバーフローします。
3でインサートしたいのですが、3を得るためによいSQL文はありませんでしょうか?
17:NAME IS NULL
07/10/30 15:05:25 LF/fw7ef
accessでInStrを使ってる処理を、Postgres+VBに移植しようとしているのですが、
InStrとLike/ILikeでは何か違いがあるのでしょうか。
とりあえずキーワードの前後に%をつければいいという事はわかりましたが、
ヒットする件数に微妙な違いが出るときがあるようです。
その違う例を発見できれば、何かわかりそうなのですが、
access側とpostgres+VB側それぞれ付き合わせるにしても件数が大きくて困っています。
18:NAME IS NULL
07/10/30 15:06:27
>>16
それが自然キーではない、つまりシステム内部で採番しシステム内部で使用するキーならば、
余計なことを考えずにより大きな型、32bitや64bitの整数を使う。
Max+1ではなくidentity属性やsequenceを使うのが基本。
それが自然キーならば、例えば1-9999の番号を繰り返し使うなどルールがある場合は、
例えば使わなくなった番号を管理するテーブルを別に持ちまずそれから番号を取得するなど、
いくつか方法がある。
採番の範囲が広いほどそれなりの工夫をしなければパフォーマンスを落とすことになりやすい。
19:NAME IS NULL
07/10/30 21:38:01
>>16
すでに1行以上データがあることが前提だが、最小の空き番は以下でとれる。
SELECT min(id)+1 FROM Table AS T1 WHERE NOT EXISTS (SELECT * FROM Table WHERE id=T1.id+1);
だけど、>>18に同意。
20:NAME IS NULL
07/10/31 17:46:13 WwEAVoHF
aspなのですが、
オブジェクトが閉じている場合は、操作は許可されません。
というエラーです。
rsが閉じているかどうやって調べればよいのでしょうか?
21:NAME IS NULL
07/10/31 17:49:34
>>20
すれ違い、この辺できいてくれ
ADO DAO など接続方法について
スレリンク(db板)l50
22:NAME IS NULL
07/10/31 17:51:23 WwEAVoHF
すれ違いかを教えることしかできないのか。残念。
23:NAME IS NULL
07/10/31 18:06:36
自己った。
24:NAME IS NULL
07/10/31 18:09:34
>>21
そのスレにはもっと痛い奴が何年も住み着いてるからきーつけな>WwEAVoHF
25:NAME IS NULL
07/11/02 16:01:42 B26ewXs/
質問です。
2つのテーブル tbl1 と tbl2 があり、SELECTする際にこの2つを結合させるものとします。
このとき取得できるフィールド名に、別名をつけたいと考えています。
tbl1.foo → tbl1_foo
tbl1.bar → tbl1_bar
tbl2.foo → tbl2_foo
tbl2.bar → tbl2_bar
というように、ユニークな別名をつけるにはどうすれば良いでしょうか。
もちろん、1つずつASを使うのが確実ではあるのですが、文字列操作関数で一括置換できないかなと。
プログラム側の都合上、同じフィールド名だと片方しか取得できないもので…。
26:NAME IS NULL
07/11/03 06:57:14
更新系SQLの書き方について質問させてください。
以下のようなデータがあるとします。
-----------------
id name
-----------------
1 win xp
2 max os x
3 win 95
nameの先頭が"win"になっているものをwindowsに置き換えたいと考えており、
期待している結果は以下の通りです。
-----------------
id name
-----------------
1 windows xp
2 max os x
3 windows 95
このような更新を行うSQLはどのようにかけばよろしいのでしょうか?
mysqlを使ってます。
よろしくお願い致します。
27:NAME IS NULL
07/11/03 08:24:08
update TableName set name = 'windows' where name like 'win%'
28:NAME IS NULL
07/11/03 08:26:06
>>26
UPDATE Table SET name=replace(name,'win ','windows ') WHERE name LIKE 'win %';
一応誤爆(windows -> windowsdows)回避のためwinの後ろにスペースを入れてある。
まぁ、これだと、nameが'win win os'となっていた場合、'windows windows os'ってなってしまう。
MySQLで可能かどうか不明だが、
UPDATE Table SET name='windows' || substring(name FROM 'win #"%#"' FOR '#') WHERE name LIKE 'win %';
POSIX正規表現が使えるならもそっと楽かな。
UPDATE Table SET name=regexp_replace(name,'^win ','windows ') where name LIKE 'win %';
29:28
07/11/03 08:33:59
もうちょっと楽っぽいのを思いついた。
UPDATE Table SET name='windows '||substring(name,5) WHERE name LIKE 'win %';
30:NAME IS NULL
07/11/03 14:19:49
MySQL4.0です。
テーブルのnameフィールドが一部は
「山田 太郎」や「山田 太郎」となっており、
一部は
「山田太郎」
となっています。
スペースを無くす方向で統一したいのですが、下記SQL文で合っているでしょうか。
念のためバックアップしますが、それでも失敗したくないので。。。お願いします。
UPDATE table SET name=replace( name, ' ', '' )
UPDATE table SET name=replace( name, ' ', '' )
31:NAME IS NULL
07/11/04 22:42:08
SQLってStructured Query Languageの略じゃないとWikipediaに書いてあるんですが
マジですか?ISOのサイトにそう描いてある文書ないでしょうか。
32:NAME IS NULL
07/11/04 22:56:46
>>31
『Database Language SQL』
としか書いてねぇよ。
33:NAME IS NULL
07/11/04 23:09:38
>>31
そうか・・
34:NAME IS NULL
07/11/04 23:10:41
× >>31
→
○ >>32
みすった・・
35:NAME IS NULL
07/11/05 15:33:31
Oracle9iでのSELECTについて教えてください。
現在のテーブル内情報:
GROUP_ID│REG_DATE │TEL_NO │STATUS
-──┼───┼───┼───
A001 │2007/10/01│03-9999-0001│ENABLED
A001 │2007/09/20│03-9999-0002│DISABLED
A001 │2007/10/03│03-9999-0002│ENABLED
A001 │2007/10/03│03-9999-0003│ENABLED
A001 │2007/08/01│03-9999-0003│DISABLED
A001 │2007/10/31│03-9999-0004│DISABLED
A001 │2007/10/31│03-9999-0005│DISABLED
このうちTEL_NOが重複しないように、
GROUP_ID│REG_DATE │TEL_NO │STATUS
-──┼───┼───┼───
A001 │2007/10/01│03-9999-0001│ENABLED
A001 │2007/10/03│03-9999-0002│ENABLED
A001 │2007/10/03│03-9999-0003│ENABLED
A001 │2007/10/31│03-9999-0004│DISABLED
A001 │2007/10/31│03-9999-0005│DISABLED
こうなるように、
・STATUS=ENABLEDで重複無しの場合はそのまま抽出。
・STATUS=DISABLEDで重複無しの場合はそのまま抽出。
・STATUS=DISABLEDとENABLEDの双方が設定されて重複
登録されているデータについては、
STATUS=ENABLEDのもののみを重複無しで取得したい。
という条件でselectしたいのですが、
どのように記述すれば良いでしょうか?
よろしくお願いします。
36:NAME IS NULL
07/11/05 19:32:18
>>35
ENABLED同士、DISABLED同士で重複している場合は
どういう条件で重複を排除するのか?
なんとなく
select A.GROUP_ID, A.REG_DATE, A.TEL_NO, A.STATUS
from TableName A
inner join
(select TEL_NO, max(REG_DATE) as MAX_REG_DATE
from TableName
group by TEL_NO
) B
on A.TEL_NO = B.TEL_NO
and A.REG_DATE = B.MAX_REG_DATE
;
でいいような気がするが。
37:35
07/11/06 02:07:29
>>36
ご教示ありがとうございます。
今、徹夜中で頭がもうろうとしているので、
明日、あらためて試させていただきたいと思います。
重ね重ねありがとうございます。
38:35
07/11/06 10:18:59
>>36
さっそく試してみたところ、望んでいた結果が得られ
見事うまくいきました(号泣)
本当にありがとうございました。
JOINの使い方をよく理解してないので、
これからJOINを勉強してみます。
39:NAME IS NULL
07/11/06 10:19:04 XhrkB73v
1つのファイルにmysqlとPostgreSQLから同時にアクセス
データベースに接続指定を書き込んだファイルを用意する形で、ファイルは同一サーバー上ですが、セキュリテリの面から直接プログラムファイルに書き込まず、別ディレクトリに設置し読み込ませます。
0SはLinuxです。
その読み込みファイル1枚に、MySQlとPostgleに同時接続させるような設定を書いた場合、同時にDBを操作できるのでしょうか。
40:NAME IS NULL
07/11/06 10:39:09
>>39
日本語でOK
つか、何をしたいのか全く読み取れんよ。
> 1つのファイルにmysqlとPostgreSQLから同時にアクセス
1つのファイルに2つのRDBMSからアクセスするの?
> その読み込みファイル1枚に、MySQlとPostgleに同時接続させるような
1つのスクリプト or PGから2つのRDBMSに接続するの?
後者だとして、明示的に別なConnectionとかで扱えば、
個別のDataSourceとして扱うと思うがな。
それとも2つのRDBMSを1つの物として扱いたいって事か?
41:NAME IS NULL
07/11/06 10:47:24
ひょっとして、connection.ini ってなファイルに
pgsql:server=localhost/dbname=hoge...
musql:server=loclahost/dbanme=hoge...
って書いておいて、それを読み込んで接続したいってことかな?
そりゃ、ホスト言語の仕様次第だろ。単純な読み込みならまず問題ないと思うが。
んで、スレ違いだな。
42:NAME IS NULL
07/11/06 10:48:02
musqlはtypo....rz
43:NAME IS NULL
07/11/07 00:24:57 jxOaFgZr
>>0SはLinuxです
をよく見ると数字のゼロなのがウケル。
からかってんのか??
44:NAME IS NULL
07/11/08 01:29:29
下のような表から
date | customer | paper | pen | cable
------------------------------------
2007/11/01 | Mr.AAA | 100 | 200 | 400
2007/11/01 | Mr.BBB | 150 | 300 | 350
2007/11/01 | Mr.CCC | 500 | 250 | 600
paper,pen,cableなどの列名を先頭に持ってきて
列com_name,priceを追加して、
下のような表を作ることはSQLまたは、PL/SQLでできるのでしょうか?
com_name | date | customer | price
----------------------------------
paper | 2007/11/01 | Mr.AAA | 100
paper | 2007/11/01 | Mr.BBB | 150
paper | 2007/11/01 | Mr.CCC| 500
pen | 2007/11/01 | Mr.AAA | 200
pen | 2007/11/01 | Mr.BBB | 300
pen | 2007/11/01 | Mr.CCC| 250
cable | 2007/11/01 | Mr.AAA | 400
cable | 2007/11/01 | Mr.BBB | 350
cable | 2007/11/01 | Mr.CCC| 600
カーソル使って中は何とかなるけど、
肝心の両端がどうにもならんのです。
SQL PL/SQLやり始めて1月程度。
この辺が限界です。
どなたかお力を・・・
45:NAME IS NULL
07/11/08 04:32:45
>>44
カラムが決め打ちでいいなら可能
46:NAME IS NULL
07/11/08 05:30:03
カラム名をシステムカタログから取得して、
PL/SQLでSQL組み立てれば可能かな。(カラム決め打ちじゃない場合)
Oracleスレで聞いた方がいいんじゃね。
47:NAME IS NULL
07/11/08 21:07:22 nXrq+1YJ
下記のテーブルAとテーブルBからテーブルAの重複行を
元に取得したい結果を抽出したいのですがご教授お願いします。
テーブルA
ID1 |ID2 |ID3 |MONEY
-----------------------
010101|020202|030101|1000
010101|020202|030201|2000
010101|020202|030301|3000
010101|020202|030502|4000
010101|030202|040601|5000
010101|030202|040701|6000
テーブルB
ID1 |ID2 |ID3 |NAME
-----------------------
010101|020202|030101|A
010101|020202|030201|B
010101|020202|030301|C
010101|020202|030502|D
010101|030202|040601|E
010101|030202|040701|F
テーブルAの重複行を得る。
ID1 |ID2 |ID3_1|ID3_2|COUNT
-----------------------------
010101|020202|03 |01 |3
010101|030202|04 |01 |2
ID3_1 は SUBSTR(ID3,1,2)
ID3_2 は SUBSTR(ID3,5,2)
取得したい結果
ID1 |ID2 |ID3 |NAME|MONEY
------------------------------
010101|020202|030303|A |1000
010101|020202|030403|B |2000
010101|020202|030301|C |3000
010101|030202|040601|E |5000
010101|030202|040701|F |6000
48:47
07/11/08 21:08:04 nXrq+1YJ
>>47の続き
SELECT A.ID1,A.ID2,A.ID3,B.NAME,A.MONEY
FROM テーブルA A,テーブルB B
WHERE
(A.ID1
,A.ID2
,SUBSTR(A.ID3,1,2)
,SUBSTR(A.ID3,5,2)
) IN
(SELECT
A2.ID1
,A2.ID2
,SUBSTR(A2.ID3,1,2)
,SUBSTR(A2.ID3,5,2)
FROM テーブルA A2
WHERE
A2.ID1
AND A2.ID2
AND SUBSTR(A2.ID3,1,2)
AND SUBSTR(A2.ID3,5,2)
GROUP BY
A2.ID1
,A2.ID2
,SUBSTR(A2.ID3,1,2)
,SUBSTR(A2.ID3,5,2)
HAVING COUNT(*) > 1
)
上記のようなSQLを作成したのですが
テーブルBと結合した際に重複行以外も取得してしまいます。
長文で申し訳ありませんでしたがどなたかご教授ください。
49:NAME IS NULL
07/11/08 21:18:11
重複行を取りたいってのはわかった。
でも、それとテーブルBをどう結合するのかが
理解できん。
まず日本語できちんと説明してみれ
50:47
07/11/08 22:03:41 nXrq+1YJ
>>49
テーブルBの使用用途としては名称取得の為に使います。
取得したい結果はテーブルAの重複行の結果を元に名称が違うものだけを
抽出するというものです。
グループ化した後にグループ化された結果のデータの詳細を
表示するのですが、その際にテーブルAの重複行として取得した結果以外
のものが取得されてしまうのです。
日本語が下手で分かりにくいと思いますがすいません。
51:NAME IS NULL
07/11/08 22:06:24
わかりにく・・・
箇条書きでいいから条件羅列してみれ
52:NAME IS NULL
07/11/08 22:12:33
取得したい結果
ID1 |ID2 |ID3 |NAME|MONEY
------------------------------
010101|020202|030303|A |1000
このID3=030303ってデータはどこからくるの?
テーブルAにもBにも存在しないんだけど。
53:NAME IS NULL
07/11/08 22:35:30
>>47
「取得したい結果」は、
ID1 |ID2 |ID3 |NAME|MONEY
------------------------------
010101|020202|030101|A |1000
010101|020202|030201|B |2000
010101|020202|030301|C |3000
010101|030202|040601|E |5000
010101|030202|040701|F |6000
の間違いじゃないのか?(1行目と2行目のID3)
そうだとしたら、ほぼ>>48のまま
select A.ID1, A.ID2, A.ID3, B.NAME, A.MONEY
from テーブルA A, テーブルB B
where (A.ID1, A.ID2, substr(A.ID3, 1, 2), substr(A.ID3, 5, 2))
in
(select A2.ID1, A2.ID2, substr(A2.ID3, 1, 2), substr(A2.ID3, 5, 2)
from テーブルA A2
group by A2.ID1, A2.ID2, substr(A2.ID3, 1, 2), substr(A2.ID3, 5, 2)
having count(*) > 1
)
and A.ID1 = B.ID1
and A.ID2 = B.ID2
and A.ID3 = B.ID3
で良さそうなもんだけど。
54:47
07/11/08 22:44:46 nXrq+1YJ
本当に日本語が下手ですいません。
・テーブルAのID3の1,2桁目と5,6桁でグループ化をする。
・グループ化したID3を元に重複している名称を抽出する。
・名称を抽出した際にグループ化した結果以外が抽出されてしまう。
取得したい結果 は間違ってました。すいません。
以下が本当の取得したい結果です。
ID1 |ID2 |ID3 |NAME|MONEY
------------------------------
010101|020202|030101|A |1000
010101|020202|030201|B |2000
010101|020202|030301|C |3000
010101|030202|040601|E |5000
010101|030202|040701|F |6000
55:NAME IS NULL
07/11/09 00:22:12
>・テーブルAのID3の1,2桁目と5,6桁でグループ化をする。
ID3_1|ID3_2|COUNT
03 |01 |3
03 |02 |1
04 |01 |2
>・グループ化したID3を元に重複している名称を抽出する。
上の結果からCOUNTが2以上(重複がある行)を抽出。
ID3_1|ID3_2|COUNT
03 |01 |3
04 |01 |2
テーブルAのID3の1,2桁目と5,6桁が上の結果のID3_1|ID3_2と一致する行を抽出。
ID1 |ID2 |ID3 |MONEY
-----------------------
010101|020202|030101|1000
010101|020202|030201|2000
010101|020202|030301|3000
010101|030202|040601|5000
010101|030202|040701|6000
テーブルBと合わせる。
ID1 |ID2 |ID3 |NAME|MONEY
------------------------------
010101|020202|030101|A |1000
010101|020202|030201|B |2000
010101|020202|030301|C |3000
010101|030202|040601|E |5000
010101|030202|040701|F |6000
って事?>>47
56:NAME IS NULL
07/11/12 00:31:35 tKheOgZe
MySql5.0を使用してます。
CREATE TABLE test_tbl (
id int(11) NOT NULL auto_increment,
name varchar(255) default NULL,
mydate date NOT NULL,
PRIMARY KEY (id),
);
こんなテーブルがあり
毎日定時にSELECT文を実行して mydateから30日後,60日後,90日・・・・と
mydate から本日が30日間隔のidを永遠に抽出したいんですが、どういう風に記述すればよいでしょうか?
57:NAME IS NULL
07/11/12 01:13:30
試してないが、
select * from test_tbl where mydate<sysdate() and (sysdate()-mydate)%30=0
58:NAME IS NULL
07/11/12 18:49:35 3CGhHvj/
id | date | data
--+----------+-----
1 | 2007-11-11 | aaa
2 | 2007-11-11 | bbb
1 | 2007-11-10 | ccc
3 | 2007-11-12 | ddd
3 | 2007-11-11 | eee
4 | 2007-11-10 | fff
1 | 2007-11-12 | ggg
このようなテーブルから、下記のように
1 | 2007-11-12 | ggg
3 | 2007-11-12 | ddd
2 | 2007-11-11 | bbb
4 | 2007-11-10 | fff
各idに対して最新の1件だけ抽出するSQLの書き方を教えてください。
59:NAME IS NULL
07/11/12 19:55:42
>>58
>>35-36
60:NAME IS NULL
07/11/12 20:08:04 3CGhHvj/
>>59
サブクエリーでMaxとった後に、同じテーブルを当てるのですね。
やってみたら上手くいきました。
有難う御座いました。
61:NAME IS NULL
07/11/12 22:51:57
SQLについて質問させください。
以下の二つのテーブルがあるとします。
(1)user_tbl
+---------+-----------+
| user_id | user_name |
+---------+-----------+
| 1 | tarou |
| 2 | jirou |
| 3 | saburou |
+---------+-----------+
(2)question_tbl
mysql> select * from question_tbl;
+-------------+---------+--------+
| question_id | user_id | answer |
+-------------+---------+--------+
| 1 | 1 | yes |
| 2 | 1 | yes |
| 3 | 1 | yes |
| 4 | 1 | no |
| 5 | 1 | no |
+-------------+---------+--------+
5 rows in set (0.00 sec)
この二つのテーブルから以下の結果を導き出したいです。
+----------+-----------+--------+-----+
| _user_id | user_name | yes | no |
+----------+-----------+--------+-----+
| 1 | tarou | 3 | 2 |
| 2 | jirou | 0 | 0 |
| 3 | saburou | 0 | 0 |
+----------+-----------+--------+-----+
このような結果を作るSQLはどのようになりますでしょうか?
よろしくお願い致します。
62:NAME IS NULL
07/11/12 23:14:33
>>61
ヒント:sum(case when answer = 'yes' then 1 else 0 end) as yes
63:>>61
07/11/13 07:54:51
>>61
ありがとうございました!
64:RrLJfFysqaTB
07/11/13 12:50:19
OxUDeM <a href="URLリンク(kcwofgibzljb.com) [url=URLリンク(oweqzrlrrhxk.com) [link=URLリンク(tturythxblwv.com) URLリンク(jmxakeogmots.com)
65:NAME IS NULL
07/11/14 01:15:06
Oracleを勉強していて、わからないところがあるので質問させてください。
以下のようなテーブルがあったとします。
GROUP_ID│USER_NO│SALARY
-──┼──┼──
A001 │ 17040│200000
A001 │ 18302│190000
A002 │ 28321│200000
A002 │ 23434│200000
A003 │ 56787│210000
A003 │ 98908│200000
A003 │ 67589│210000
このテーブルから
GROUP_ID毎のSALARYの最大値を取得したいのですが、
あわせてSALARYが最大値であるUSER_NOも取得したいのです。
結果のイメージとしては
GROUP_ID│USER_NO│SALARY
-──┼──┼──
A001 │ 17040│200000
A002 │ 28321│200000
A003 │ 67589│210000
となります。
select GROUP_ID, MAX(SALARY)
from TABLE
group by GROUP_ID
ここから先どのように記述してよいのかわかりません。
教えていただけないでしょうか?
よろしくお願いします。
ちなみにSALARYが重複した場合はUSER_NOが大きい方を表示するようにしたいです。
66:NAME IS NULL
07/11/14 01:20:21
select 10 as a, 20 as b, (a + b) as c
のようなことをしたいのですが、できますでしょうか?
mysqlをつかっております。
67:NAME IS NULL
07/11/14 01:23:29
>>65
GROUP_ID と SALARY がわかってるんだから、
元のテーブルと JOIN すれば OK。
68:NAME IS NULL
07/11/14 01:24:00
>>66
試してみればいいんじゃね?
69:NAME IS NULL
07/11/14 01:32:41
>>66
MySQLじゃなくてもできないよ。
SELECT *,(a+b)AS c FROM (SELECT 10 AS a,20 AS b ...) AS T1
のようにすれば桶。
70:NAME IS NULL
07/11/14 01:43:11
>>65
こうやるんだよ。
select
b.gid,
max(b.uid),
b.salary
from
(select gid, max(salary) as salary from TABLE group by gid) as a
left join
TABLE as b
on a.salary=b.salary
group by gid;
71:>>66
07/11/14 01:47:20
>>69
ありがとうございますm(_ _m)
72:ElCkbafdouVDbF
07/11/14 03:04:05
Cdjtp6 <a href="URLリンク(tvhpxzaxcajb.com) [url=URLリンク(jdtlpcftljec.com) [link=URLリンク(mktvrqchpfre.com) URLリンク(xzyfjavesqan.com)
73:fKgpGQOBRC
07/11/14 10:41:27
kXtUWP <a href="URLリンク(zffpjytxvwvv.com) [url=URLリンク(omxffvcxtpus.com) [link=URLリンク(oqvlhfrxmavo.com) URLリンク(xhhqhknnxunq.com)
74:65
07/11/14 11:28:45
>>67,70
ありがとうございます!
>>70さんのSQLはうまく動きませんでしたが、
参考にして作ることができました!
75:GnmKqIiRbSoLHQvXsv
07/11/14 12:30:56
2b1CTd <a href="URLリンク(mocxgyjjwzck.com) [url=URLリンク(xrxwfwfnrejf.com) [link=URLリンク(xzeorzfpjjxb.com) URLリンク(ewlokroibysi.com)
76:NAME IS NULL
07/11/15 01:18:33
Oracle10gの質問です。
TBL1
ID(PK)
----
001
002
003
TBL2
※IDはPKでない
ID NAME
---------
001 NAME1
002 NAME2
002 NAME3
テーブル1と2を結合して
ID NAME
----------
001 NAME1
002 NAME2
003 NULL
といった具合にTBL1の件数は維持して
NAMEには一致したIDの先頭(でなくてもいい)のものを
引っ張ってきたいです。
外部結合だと
SELECT *
FROM
TBL1, TBL2
WHERE
TBL1.ID = TBL2.ID(*)
ID NAME
----------
001 NAME1
002 NAME2
002 NAME3
003 NULL
といった具合にID:002がダブってしまいます。
(002は1件でNAME2かNAME3のうち1つだけ表示したい)
何かよい解決策はないでしょうか。
77:NAME IS NULL
07/11/15 01:21:33
>>76
Group By した結果と JOIN すればOK。
って、ちょっと前に似たような例があったような・・・
78:NAME IS NULL
07/11/15 01:48:23
>>77
回答ありがとうございます。
こんな感じでしょうか。
今は手元に環境がないので動作確認できませんが
MAXに違和感を感じます。
SELECT *
FROM
TBL1,
(
SELECT MAX(NAME)
FROM
TBL2
GROUP BY
NAME
)TBL2
WHERE
TBL1.ID = TBL2.ID(+)
>って、ちょっと前に似たような例があったような・・・
すみません。このスレでしょうか。
教えていただけるとありがたいです。
(パっと見どれだかわからない)
79:NAME IS NULL
07/11/15 04:14:56
たぶん前スレの最後のやつかな?
80:NAME IS NULL
07/11/15 07:44:36
前スレがもう見られないです。
ログ持ってる方、貼っていただけるとありがたいです。
81:65
07/11/15 16:45:32
すいません、もう一度質問させてください。
前のテーブルに付け足したテーブルがあるとします。
GROUP_ID│USER_NO│SALARY │USER_NAME
-──┼──┼──┼───
A001 │ 17040│ 200000│ 田中
A001 │ 18302│ 190000│ 田所
A002 │ 28321│ 200000│ 田端
A002 │ 23434│ 200000│ 田原
A003 │ 56787│ 210000│ 田井
A003 │ 98908│ 200000│ 田木
A003 │ 67589│ 210000│ 田守
取得条件は前の質問と同じで結果は以下になります。
GROUP_ID│USER_NO│SALARY │USER_NAME
-──┼──┼──┼───
A001 │ 17040│ 200000│ 田中
A002 │ 28321│ 200000│ 田端
A003 │ 67589│ 210000│ 田守
自分で作ったSQLは
select T4.*
from T4,
(select T3.GROUP_ID,
MAX(T3.USER_NO) as USER_NO,
select T4.*
from T4,
(select
T2.GROUP_ID,
max(T2.USER_NO)
from (select GROUP_ID,
max(SALARY) as SALARY
from TABLE
group by GROUP_ID) as T1,
TABLE as T2
on T1.SALARY = T2SALARY
group by T2.GROUP_ID) T3
where T4.GROUP_ID = T3.GROUP_ID
and T4.USER_NO = T3.USER_NO
select T4. *
from TABLE T4,
(select T2.GROUP_ID,
max(T2.USER_NO) as USER_NO,
T2.SALALY
from (select GROUP_ID,
max(SALALY) as SALALY
from TABLE
group by GROUP_ID) T1,
TABLE T2
where T1.SALALY = T2.SALALY
and T1.GROUP_ID = T2.GROUP_ID
group by T2.GROUP_ID, T2.SALALY) T3
where T3.GROUP_ID = T4.GROUP_ID
and T3.USER_NO = T4.USER_NO
です。もうちょっとスマートにかけないものかなと思って質問しました。
よろしくお願いします。
82:xjQscgvGjNP
07/11/15 17:57:09
Hi! Nice site!
83:QYuScmbNhprG
07/11/15 17:57:58
Hi! Nice site!
84:NAME IS NULL
07/11/15 18:37:40
>>76
select A.ID, B.MAX_NAME
from TBL1 A
left outer join
(select ID, max(NAME) as MAX_NAME
from TBL2
group by ID
) B
on A.ID = B.ID
>>81
>>35-36
85:NAME IS NULL
07/11/15 20:06:51
>>81
SELECT * FROM
(SELECT max(user_no) AS user_no FROM Table AS T1
WHERE SALARY=(SELECT max(salary) FROM Table WHERE group_id=T1.group_id)
GROUP BY group_id) AS T2
LEFT JOIN Table USING(user_no);
スマートかどうかは...?
86:sage
07/11/15 20:16:36 f/zLBRc9
質問します^^;
かなり初歩的なことかと思いますが。。。
IFIXなるものを現在会社で使ってまして制御系(FA)なのですが
まったく経験がなく、データベースなるものもあまり判っていませんorz
もし、詳しく判りやすいサイトや、板誘導などがありましたら、お願いします
板汚し板違いスイマセン
87:NAME IS NULL
07/11/15 21:21:59
で、何を知りたいんだ?それをはっきり書けよ
88:NAME IS NULL
07/11/15 22:41:17 NMabm+GO
LEFT OUTER JOIN で右側の列に検索条件指定したら、INNER JOIN と
いっしょですか?
89:86
07/11/15 23:38:43
>>86です
サゲミスッテマスタorz
タグの種類でPGがあって、その中に「ADDOUT」や「SETMAN」などがあるのですが
それらの説明、使い方、このときはこの文法?みたいのがわかればと思いまして。。。
まったく持って初歩的な事でスイマセン
90:NAME IS NULL
07/11/16 01:06:53
>>89
URLリンク(www.proface.co.jp)
これのことかな?それ向けのスレはないだろうな。
中でSQL-SERVERを使ってるようだけど直接は関係ないな。
ベンダーのユーザー会とかあるんじゃね?
営業に聴いて見たら。
91:NAME IS NULL
07/11/17 18:57:59
すいません。ソートについてお聞きしたいのですが、
id typeid name
---------------------------------
1 1 aaaa
2 1 bbbb
3 2 cccc
4 2 dddd
5 2 eeee
6 3 ffff
というテーブルがあった場合、typeidが多い("大きい"ではない)順番にソートする方法はあるでしょうか?
上のテーブルでいえば、
id typeid name
---------------------------------
3 2 cccc
4 2 dddd
5 2 eeee
1 1 aaaa
2 1 bbbb
6 3 ffff
となって欲しいのです。
今まではtypeidでgroup byしてcount(*)の数値を元に手作業?でどろどろとソートしていたのですが、
実は1回のselectで簡単に出来るんじゃないかと思って、色々頑張って見ましたがorzでした。
よろしくお願いします。
92:NAME IS NULL
07/11/17 19:04:25
select
B.cnt
,A.id
,A.typeid
,A.name
from table A,
(
select
count(*) as cnt
,typeid
from table
group by typeid
) b
where A.typeid = A.typeid
order by
B.cnt
,A.id
93:NAME IS NULL
07/11/17 19:11:56
うおー!すごすぎる!早すぎる!久しぶりに感動した!
本当にありがとう。次会ったらメシおごるノシ
94:msYFQKruZmljezmxU
07/11/18 04:12:25
Hi! Nice site! <a href=URLリンク(pinspekshun.blogspot.com) >hi </a> [URL=URLリンク(pinspekshun.blogspot.com) ] pillo inspekshun [/URL] URLリンク(pinspekshun.blogspot.com)
95:sEDptiCGfsyR
07/11/18 04:12:41
Hi! Nice site! <a href=URLリンク(pinspekshun.blogspot.com) >hi </a> [URL=URLリンク(pinspekshun.blogspot.com) ] pillo inspekshun [/URL] URLリンク(pinspekshun.blogspot.com)
96:UkbWCnYjjHy
07/11/18 04:13:37
Hi! Nice site! <a href=URLリンク(pinspekshun.blogspot.com) >hi </a> [URL=URLリンク(pinspekshun.blogspot.com) ] pillo inspekshun [/URL] URLリンク(pinspekshun.blogspot.com)
97:DBevzLOEcfuRezMQzKm
07/11/18 04:14:08
Hi! Nice site! <a href=URLリンク(pinspekshun.blogspot.com) >hi </a> [URL=URLリンク(pinspekshun.blogspot.com) ] pillo inspekshun [/URL] URLリンク(pinspekshun.blogspot.com)
98:NAME IS NULL
07/11/19 21:41:56
MySQL 4.1.20
table uriage
kaisha int(4),
kyaku int(9),
torihikiYMD date,
oder_number int(5)
kingaku int(9)
taishaku int(1)
というのがあって客毎に金額を集計するなら
select kyaku,sum(kingaku) from uriage
group by kyaku;
になると思うのですが、そこにtaishakuが1なら減算
9なら加算するというのをどうやったら付け加えられますか
教えてください。
99:NAME IS NULL
07/11/19 22:06:14
sum(decode(taisyaku,1,kingaku * -1,9,kingaku))
100:NAME IS NULL
07/11/19 22:08:45
sum(kingaku*(taishaku-5)/4)
101:98
07/11/19 22:17:57
>>100
何で4で割るのかしばし考えましたが、なるほどですね。
>>99
すいません、本見ましたけど、decodeって複号化する奴では?
102:NAME IS NULL
07/11/19 23:03:01
decode関数はOracleだけだな。
一応case文に書き換え可能。
sum(case taisyaku when 1 then kingaku * -1 when 9 then kingaku end)
103:NAME IS NULL
07/11/20 06:36:35
>>102
あ~、固有のやつでしたか。ありがとです。
104:twavXWUFslz
07/11/20 21:57:37
wpMblV <a href="URLリンク(orhrbykowlfh.com) [url=URLリンク(qmyxnterfghh.com) [link=URLリンク(scltuetviczt.com) URLリンク(mvcondmybzwm.com)
105:StfyyUJvYsI
07/11/20 21:57:45
J4iVVk <a href="URLリンク(rdcnpcryezok.com) [url=URLリンク(lwliadpfpbax.com) [link=URLリンク(rfkixlnovphd.com) URLリンク(bgxiydwgrytq.com)
106:HStXqNGT
07/11/20 21:58:26
BmRgkm <a href="URLリンク(wkltnhbjkxte.com) [url=URLリンク(nfqygpcebcxp.com) [link=URLリンク(acbdchtzfety.com) URLリンク(kcpavhkvmcif.com)
107:OWiqHPJDpfe
07/11/20 22:01:42
HVwtcd <a href="URLリンク(dxmcqmralrtc.com) [url=URLリンク(kqmhumhyapnr.com) [link=URLリンク(tscybluiypbg.com) URLリンク(jfsahhjbytsj.com)
108:rrFELpiUaz
07/11/23 00:24:35
URLリンク(haimba.cn) windows mp3 downloads
109:QuyNWHZjnp
07/11/23 01:56:58
URLリンク(ieirrj.cn) legal mp3 music downloads
110:mvfhwciOqYgTQlKScw
07/11/23 21:18:56
URLリンク(kgnsye.cn) Imax california
URLリンク(kgnsye.cn) California dept of corporation htm
URLリンク(kgnsye.cn) Single family homes carlsbad california
URLリンク(kgnsye.cn) Archangel tattoo design
URLリンク(kgnsye.cn) Blue book pricings for atv
111:ObnIPIqgSyv
07/11/24 10:51:11
URLリンク(bdzwbn.cn) great mp3
112:OzbYNNxQZr
07/11/24 19:10:57
URLリンク(bdzwbn.cn) real mp3
113:NAME IS NULL
07/11/25 04:46:04
MySQL5.0なんですが、
WHERE field LIKE 'hoge%'
と
WHERE field REGEXP '^hoge'
って全く同じ条件になる、と考えてよいでしょうか?
114:XwnWVoMqtvaefKbr
07/11/27 18:49:38
mP3cFn <a href="URLリンク(qpmxqjoghxos.com) [url=URLリンク(wagolwnmugfg.com) [link=URLリンク(ptgsubukuahe.com) URLリンク(nhuvhvdcasob.com)
115:NAME IS NULL
07/11/27 21:59:57 JprxOidq
ストアドプロシジャー内でINSERT分に日時を利用したいのですが、構文教えてください
116:NAME IS NULL
07/11/27 22:20:59
>>115
ストアドプロシジャはDBMSによって構文が全く違うので
DBMS名を示さなければその質問は無意味。
SQLに限って言っても、日付・時刻に関する構文は
DBMSによって違う。
あと、やりたいことをもっと具体的に言ったほうがいいかと。
117:bVukSlOdGjiEKqu
07/11/28 12:10:38
6nZWlh <a href="URLリンク(sgigiievsonb.com) [url=URLリンク(dcqrzcdqcywn.com) [link=URLリンク(ykzntgnprdwm.com) URLリンク(xytahapkrpaw.com)
118:NAME IS NULL
07/11/28 14:21:20 dhNS0GoF
CREATE TABLE DEPENDENT(
DEPEND_ID INTEGER,
DEPEND_NAME VARCHAR(50),
DEPEND_AGE INTEGER,
DEPEND_RELATION VARCHAR(20),
EMP_ID INTEGER,
DEPT_ID INTEGER,
PRIMARY KEY (DEPEND_ID, EMP_ID, DEPT_ID),
FOREIGN KEY (EMP_ID) REFERENCES EMPLOYEE(EMP_ID),
FOREIGN KEY (DEPT_ID) REFERENCES DEPARTMENT(DEPT_ID)
)
こいつを実行すると、Unique Primary not foundと言ってくるんですが、
何がまずいのでしょうか?
119:NAME IS NULL
07/11/28 19:18:06
select qid, quest from quest_tbl;
上のSQL文ですべての質問を取り出す際、ユーザがこの質問に答えているか、調べたいのですが下のSQL文を併せて調べるよう連結させるにはどうすればいいでしょうか?
select COUNT(user_tbl) FROM answer_tbl where qid=$qid and title IS NOT NULL;
120:NAME IS NULL
07/11/28 20:42:14
>>119
スレリンク(db板:78番)
121:NAME IS NULL
07/11/29 01:31:59
>>116
丁寧にお手数多謝です。
SQLServer2005です。GETDATE関数でおkですね。
もっと自分で調べてから質問するようにします。ご指摘ありがとうございます。
122:NAME IS NULL
07/11/29 01:53:38
A_ID │A_NAME│
-----------------------
A001 │ A1 │
A002 │ A2 │
A003 │ A3 │
A004 │ A4 │
B_ID │A_ID │ B_NAME
-----------------------------
B001 │ A001│山田
B002 │ A001│山田
B003 │ A001│山田
B004 │ A002│高橋
B005 │ A002│島田
B006 │ A002│中村
B007 │ A003│中村
B008 │ A004│山田
C_ID │B_NANE │COUNT
-------------------------------
C001 │ 山田 │ 3
C002 │ 田中 │ 1
C003 │ 高橋 │ 1
このような3つのテーブルを結合して、C_ID = C001 を抽出した際に
A_ID │A_NAME│B_NAME| C_ID
---------------------------------
A001 │ A1 │山田 │C001
A004 │ A4 │山田 │C001
と、A_IDが重複しないようなSQLの結合が上手く行かなくて悩んでおります。
こんな遅い時間で恐縮ですが、どなたかお教え願えないでしょうか。
日が昇ったら、これを講師に提出しなくてはならなくて・・・。
よろしくお願い致します。
123:NAME IS NULL
07/11/29 01:54:29
追記で申し訳ないです。
使用しているプラットホームはpostgresqlでした。
124:NAME IS NULL
07/11/29 02:41:49
>>122
上から TableA,TableB TableCとして
SELECT * FROM
(SELECT c_id,b_name FROM TableC WHERE c_id='C001') AS T1
JOIN (SELECT a_id,b_name FROM TableB GROUP BY a_id,b_name) AS T2 USING(b_name)
JOIN TableA USING(a_id);
125:NAME IS NULL
07/11/29 02:45:00
いつも書き込んだ後に気づく...orz
SELECT * FROM TableC
JOIN (SELECT a_id,b_name FROM TableB GROUP BY a_id,b_name) AS T2 USING(b_name)
JOIN TableA USING(a_id)
WHERE c_id='C001';
でいいか。(このままだとTableC.countまででるけど)
126:NAME IS NULL
07/11/29 03:03:57
PostgreSQL 8.2 使ってますけど、副問い合わせで 1 件も存在しない時に 0 を返すように
したいんですがうまい書き方はないでしょうか?
UPDATE HOGE SET HAGE=(SELECT HAGE FROM FOO WHERE ID=?), ...
127:NAME IS NULL
07/11/29 03:12:55
>>126
SELECT Hoge SET hage=COALESCE((SELECT hage FROM Foo WHERE id=?),0);
128:NAME IS NULL
07/11/29 03:13:38
またやった...orz
UPDATE Hoge SET hage=COALESCE((SELECT hage FROM Foo WHERE id=?),0);
129:NAME IS NULL
07/11/29 03:17:30
>>127
ありがとうございます!
130:119
07/11/29 12:21:06
>>120
あっ!
たまたま同じ質問してる人がいたなんて!!
すごい奇遇です!!
131:122
07/11/29 15:43:22
>>125
遅レスで申し訳ないです。
おかげで、何とか合格しましたですよ。本当に有難うございました。
まだまだSQLが使いこなせてないので、ちょっとSQLの本買って冬休みは
勉強します。
132:FgUIzWJFDelHSJxvY
07/11/29 22:51:54
URLリンク(zerozeroone.at.tut.by) 胙�魵鵫 ��
URLリンク(zerozeroone.at.tut.by) 胙�魵鵫 ��
URLリンク(zerozeroone.at.tut.by) 胙�魵魲� �
URLリンク(zerozeroone.at.tut.by) 胙珞�
URLリンク(zerozeroone.at.tut.by) 胙珞鵫 ��
URLリンク(zerozeroone.at.tut.by) 胙�魵顥 ⅱ肛�
URLリンク(zerozeroone.at.tut.by) ��濵� 胙�魵鮱 ⅱ肛�
URLリンク(zerozeroone.at.tut.by) 胙�魵鐱 ⅱ肛� 聰�褞�
URLリンク(zerozeroone.at.tut.by) �ⅱ濵 �� 胙�魵鵫
133:NAME IS NULL
07/11/30 00:08:38 IiAQc5hj
・DBとバージョン
MySQL4.0.24 です
・テーブルデータ
p_id,p_name(ペット用テーブル:pet)
-----------------
1,シロ
2,ぽち
3,タマ
s_id,s_name(社員用テーブル:syain)
-----------------
1,山田
2,小林
3,三木
t_id[auto_increment],p_id,s_id(担当者テーブル:tanto)
-----------------
1,1,1
2,2,2
3,1,3
・欲しい結果
一覧表示
=================
シロ | 三木
ぽち | 小林
タマ | (空欄)
・説明
シロの担当はは山田から後に三木に変更になっています
タマの担当者はまだ決まっていません
今はphpを使っていて
SELECT * FROM pet (ペットをすべて取得してループ開始)
SELECT * FROM tanto WHERE p_id ORDER BY t_id DESC LIMIT 1
SELECT * FROM syain WHERE s_id LIMIT 1
(ループ終わり)
としているのですが一回で出来るのでしょうか?
以前ペット用テーブルは
p_id,p_name,s_id
となっていて LEFT OUTER JOIN を使っていましたが
担当者の変更履歴が分かるようにと言われて考えてみたのですが、
そもそもやり方(構造?)がおかしいでしょうか?
よろしくお願いいたします
134:NAME IS NULL
07/11/30 01:24:57
担当者テーブルを p_id で Group By し、t_id の Max を取る。
その Max(t_id) と t_id を結合し、p_id で ペット用テーブルと
Left Outer Join
135:NAME IS NULL
07/11/30 01:40:36
担当者テーブルは頻繁にアクセスされるだろうし、履歴と一緒にするのはどうかと思う。
担当者テーブルは担当者テーブルとして、現状のペットと社員の関係だけ保存し、
別にログのテーブル用意して、担当代わるときに書き込めばいいんじゃないか?
あとダミーとして社員(空欄)をs_id 0 で登録しておくとLEFT JOINで目的の
一覧表示がすぐ出せていいかと思うが、どうかね?
136:133
07/11/30 07:51:32
>>134,135
5時間くらい格闘してみたのですが、なかなか々々で今日は休みます
担当者ありがなしになった時などダミーが必要とか
ものすごく参考になりました
データベースは個人的にアクセスを使っていただけな僕が
前任者のを引き継いだような感じで、悪戦苦闘なのですが
うまくいかないことがある反面、ものすごく面白いなと感じていますので
もうちょっとがんばってみます
レスありがとうございました!
137:NAME IS NULL
07/11/30 13:35:30
けっこうムズいね
mysql> select p.p_name, s.s_name
-> from pet p
-> left outer join tanto t
-> on p.p_id = t.p_id
-> and t.t_id =
-> (
-> select max(t_id)
-> from tanto t2
-> where t2.p_id = t.p_id
-> )
-> left outer join syain s
-> on t.s_id = s.s_id
-> order by p.p_id;
+--------+--------+
| p_name | s_name |
+--------+--------+
| シロ | 三木 |
| ぽち | 小林 |
| タマ | NULL |
+--------+--------+
3 rows in set (0.00 sec)
138:NAME IS NULL
07/11/30 18:26:43
mysql4.0ってサブクエリ使えたっけ?
139:NAME IS NULL
07/11/30 18:30:32
4.1からだな
140:133
07/11/30 22:08:39
>>137
>けっこうムズいね
うーん、やっぱり僕のテーブルの作り方がマズいのかなあ…
わざわざ書いてもらって本当にありがとうございました
>>138-139
昨日いろいろやっていてどうにも納得できなかった部分が釈然としました
本を2冊買って、ネットの情報も元にしていたのですが、
サブクエリが使えないバージョンだったのですね、、、
ちょっと構成を見直すことと、サブクエリを使った例文が
結構ありますので、前任者に連絡をとってみてMySQLを
4.1以降にすることをやってみたいと思います
皆様ありがとうございました
141:NAME IS NULL
07/12/02 22:23:46 SHn+jsyg
すいません、初心者です。本やWebを探したのですが理解できなかったので教えて
下さい。
以下のSQL文のaとbの結果がイマイチ理解できません。
aをGROUP BYしたあとbをGROUP BYして、異なった値があれば付け足して
表示しているのでしょうか?
SELECT a , b
FROM c
GROUP BY a , b;
142:NAME IS NULL
07/12/03 02:19:33
日本語がわからない
143:初心者
07/12/03 03:30:55 ukVIXvlY
はじめまして。初心者です。
突然ですが質問があります。
SQL SERVER 2005 で、自動的(1時間ごとに)にバックアップをとり、48時
間分のファイルを保存しておきたい時はどのようにしたらいいのですか。
基本的にフルバックアップです。
サイズはは100メガくらいです。
スケジューラは使います。
ログもそのまま保存します。
みなさまのお力をお貸しください。(__)
144:NAME IS NULL
07/12/03 03:32:56
>>143
SQL Server スレへ Go
145:初心者
07/12/03 03:38:14 ukVIXvlY
すいませんMicrosoft SQL Server 総合スレ でいいんですかね?
146:NAME IS NULL
07/12/04 15:54:19 V8j0VlBH
MySQLのON DUPLICATE KEYと同等のことをPOSTGRESQLで行いたいのですが
変わりになるようなものは用意されていないのでしょうか?
147:NAME IS NULL
07/12/04 19:34:23 g6rhgp+g
すいません。質問です。
DECIMAL型について勉強しているんですが、
salary DECIMAL(5,2)
この例で、5 (precision) は、値に対して格納される
10 進数の桁数を表わし、2 (scale) は、小数点に続いて
格納される桁数を表わします。したがって、この場合、
salary カラムに格納できる値の範囲は、-99.99 ~ 99.99 になります。(MySQL では、正数の符号を格納する必要がないため、
このカラムには、実際には、999.99 までの数値を格納することができす)。
とあったんですが、
5桁まで格納できるなら
-999.99~999.99じゃないんですか?
148:NAME IS NULL
07/12/04 23:27:25
>>146
RULEかTRIGGERを使うしかないと思う。
参考 URLリンク(codingforums.com)
続きはPostgreSQLスレで。
>>147
SQL的には-999.99~999.99が正しかったと思う。
>(MySQL では、正数の符号を格納する必要がないため、
言い換えれば、「MySQLは負の符号を格納する分ため-99.99~999.99までしか扱えない」
ということかな。MySQLスレで聞いた方がよかね。
149:146
07/12/05 09:21:40
>>148
ありがとうございます
教えていただいた内容で調べてみます
150:NAME IS NULL
07/12/05 19:32:19
テーブルにAとBがあって、A>Bの行数とA<Bの行数を取りたいんだけど、
SELECTは2回発行するしかないよね?テーブルの全行を2回スキャンするしかない
と思ってンだけど。
151:NAME IS NULL
07/12/05 19:49:55
>>150
>>62
152:NAME IS NULL
07/12/06 13:07:14 0iWlbZYz
すみません、教えて下さい。
あるゲームがあるとして、ユーザー数千人の各一人一人の
行動をログに取りたい場合なんですが、
全員のユーザーのログを、ユーザーIDとログIDをキーとして
一つのテーブルに入れると、膨大なレコード数になっちゃいますよね。
そうなるとインサートの時や索引張るときに
かなり負荷がかかりそうだし
さらにその詳細情報も…。
なんてことになったら詳細テーブルには更に指数的にレコードが増えてしまいます。
そこで、ユーザーごとにログテーブルと
ログ詳細テーブルを作ってやればいいんじゃね?
と思ったのですが
こういうやり方ってどうなんでしょう?
テーブルがめちゃくちゃ増えるだけで
結局情報量は変わらないですが、
負荷は減りそうな気はするんですが…。
他にもっとスマートなやり方があれば
教えて頂きたいッス~m(_ _)m
153:NAME IS NULL
07/12/06 14:20:20
負荷は増えるしいいことないと思うけど。
154:NAME IS NULL
07/12/06 15:21:13
小さいテーブルに分割すれば一つのテーブルの負荷は明らかに減るけど、
テーブルを管理するあたりの部分が大量のテーブルに耐えられるつくりに
なっているかどうかはわからんな。巨大な1テーブルとユーザごとの大量の
テーブルの中間が現実的な落としどころじゃない? 実際のところは具体的
にやってみないとわからんと思う。
155:NAME IS NULL
07/12/06 15:53:02 0iWlbZYz
>>153-154
ありがとうございます。
確かに問題はテーブルの管理部分ですよね。
テーブルが増えるとシステム管理系のテーブルが重くなって
全体的な負荷が上がることは考えられますね…。
DBの構造にインスタンス的な情報を入れると
DBの保守性もあまりよろしくない感じなので、やっぱり難しいですかね…。
書き込みが多く、見ることは少ないので、
イベントの種類別でテーブル作って、
見るときはそのテーブルを
マージするSELECT文作るあたりが中間の落としどころですかね…。
156:NAME IS NULL
07/12/06 17:02:54 pzP20kps
893 VS グレイシー柔術 ボコボコに893が倒される映像 普通グレイシー柔術の道場に殴りこみに行くか?
URLリンク(video.nifty.com)
157:NAME IS NULL
07/12/06 21:47:31
パーティションとかはどうよ?
158:NAME IS NULL
07/12/06 23:33:06
ログってことは追記だけだろうし、根本否定して悪いが
ユーザごとにログファイルを置いてもいいような。
ユーザごとなら同時書き込みなんて起こらないし。
159:NAME IS NULL
07/12/07 01:16:48
>152
どの程度の頻度で更新されるのか、データ量はどれくらいあるのか、によると思う。
MMORPGのように、例えば1秒とか数秒ごとに記録をするのもあれば、
PBWのように月1で記録するものもあるだろう。
160:NAME IS NULL
07/12/07 14:00:12 V9WCgeuV
レスいただいた方々、ありがとうございます。
>>157
パーティションは名前だけで良く知りませんでした、
ちょいと調べてみたところ、検討する価値がありそうですね。
>>158
ログから今度統計を取ったりするので、DB化した方が良いかなと…。
例えば全ユーザーが一番苦手とする敵とか。
>>159
MMO程じゃないですが、ログ書き込みは平均10秒に1度程度を予定してます。
また、ロギングするイベントの種類も
せいぜい15個程度なので…。
161:NAME IS NULL
07/12/08 20:30:33 jFBCt3fk
SQLでShiftJISの文字列を扱うとシングルクォート(\x27)によるSQLインジェクションの問題が起きると思うんだけど
普通どうやって回避するの?
ShiftJIS以外を使うしかないの?
一応今使ってるDBはMySQL
162:NAME IS NULL
07/12/08 20:51:38
ストアドにすれば?
163:NAME IS NULL
07/12/08 20:54:38 M+oCyQsj
上に出てくるのとよく似ているのですが、SQL文がうまくかけません。
DBは、Oracle9です。
取り扱いメニュー(T_MENU)
店舗Code | メニューコード | 適用開始日
101 | 001 | 20071001
メニューマスタ(MENU)
メニューコード | 副番 | メニュー名 | 適用開始日 | 適用終了日
001 | 1 | メニューA | 20070901 | 20070930
001 | 2 | メニューB | 20070931 | 20071020
001 | 3 | メニューC | 20071001 | 20071015
とある場合に、「取り扱いメニュー」を基に結合してメニュー名を取得したい
のですが、業務用件として取得するメニュー名は、取り扱いメニューテーブル
の適用開始日時点で有効なメニューの副番のうち、一番若い副番のものという
指示がありました。
つまり、結果として得たいクエリは、
店舗コード | メニューコード | メニュー名
101 | 001 | メニューB
というものです。
副問い合わせで
SELECT MIN(MENU.副番) FROM MENU
WHERE MENU.適用開始日 <= T_MENU.適用開始日
AND MENU.適用終了日 >= T_MENU.適用開始日
GROUP BY MENU.メニューコード
みたいなことをしたいのですが、うまくいきません。
どうぞ皆さんのお知恵をお貸しください。
164:NAME IS NULL
07/12/10 15:50:02
>>163
レス付かないようなので。
とりあえずmysqlだとたぶんこんな感じ。
select 店舗Code, メニューコード,
(select メニュー名 FROM MENU
WHERE MENU.適用開始日 <= T_MENU.適用開始日
AND MENU.適用終了日 >= T_MENU.適用開始日 order by 副番 limit 1)
from T_MENU
Oracleだと、limitではなくRow_Number()とか使うことになるんかな。
165:NAME IS NULL
07/12/10 23:49:34
イマイチ意味が... 汎用的(に書いたつもり)だとこんな感じか?
SELECT T_menu.店舗コード,メニューコード,
(SELECT メニュー名 FROM Menu WHERE (メニューコード,副番)=(SELECT min(メニューコード)AS メニューコード,min(副番) AS 副番 FROM Menu WHERE メニューコード=T_menu.メニューコード AND T_menu.適用開始日 BETWEEN 適用開始日 AND 適用終了日))
FROM T_menu;
166:NAME IS NULL
07/12/12 16:21:41
SQL Server2005を利用しております。
Select文の中にバインド変数を使用したのですが
SELECT 得意先名 FROM 得意先マスタ WHERE 得意先コード =: 得意先
を実行すると
':' 付近に不適切な構文があります
とエラーが出ます。
=: のやり方はoracleだけなのでしょうか?
167:NAME IS NULL
07/12/12 17:24:45
>>166
MSSQLでは、変数のプレフィクスは「@」じゃないっけ?
ちなみにOracleでも、「=:」が演算子なわけではなく、
「:」が変数のプレフィクスなだけだよね。
その質問の仕方だと、代入演算をしたがってるように誤解される(てか俺もした)。
168:166
07/12/12 18:22:37
>>167
トンクス!
「@」でした!
ちなみに、CSEでやろうとすると
スカラ変数 "@得意先" を宣言してください。
と出るのですが、どうしたらよいですか?
今までずっとOracleの現場でosqleditを使っていましたが
今回、初めてSQLServerなので、最初で苦労してます。。。
169:NAME IS NULL
07/12/12 20:39:36
>>168
CSE ってのが何のことやらわからんけど、
パラメータについて調べるとよいかもしれん。
で、このスレは SQL についてのスレで、
SQL Server についてのスレではない。
専用スレに Go!
170:168
07/12/12 20:51:21
>>169
CSEってこれです
URLリンク(www.hi-ho.ne.jp)
URLリンク(www.hi-ho.ne.jp)
一応SQL(ツール)の質問だけとちと違いましたかな。。。
171:NAME IS NULL
07/12/12 21:09:11
>>170
はい。違います。
172:NAME IS NULL
07/12/13 00:27:39
>>168
SQL Serverなら、クエリアナライザという優秀な標準GUIツールがあるというのに・・・
MSDEならその限りではないが。
173:NAME IS NULL
07/12/13 01:07:51
この前勉強を始めたばかりなんですが、
テーブルの上からn行目を指定、したりできますか?
174:NAME IS NULL
07/12/13 11:33:43
>>173
データの取り出し順はソートしない限り保証されないので
「テーブルの上からn行目」ってのはできない。
ソートした結果からn番目ってのはいくらでもやりようがある。
175:NAME IS NULL
07/12/14 01:31:20 nj9wJu5D
あるデータベース内のテーブル名の一覧を取得するには、
SHOW TABLES FROM db_name;
となり、更にテーブル名が「dtb」から始まるものを同様に取得するには、
SHOW TABLES FROM db_name LIKE 'dtb%";
になると思いますが、
逆にテーブル名が「dtb」から始まるもの以外の一覧を取得するには
どのような SQL 表現となりますでしょうか?
間違っているとは分かっていながら、あえて書くと
SHOW TABLES FROM db_name NOT LIKE 'dtb%";
のような感じのことをしたいのです。
どなたかご教示ください。
176:NAME IS NULL
07/12/14 12:58:44
>>175
SHOW TABLESってMySQLの方言じゃないのか?
177:NAME IS NULL
07/12/14 14:50:23
MySQLスレのがいいね
178:175
07/12/14 20:26:41
>>176-177
誘導ありがとうございます。MySQL スレで再度質問してみます。
179:NAME IS NULL
07/12/16 14:03:00
ORACLEのSQLのソースを見ていたら、
to_date('20071216','YYYYMMDD') - to_number(T.STRINGDATE)
というのがあったのですが、
日付型から数値を引くとどのような演算がされるのですか?
180:NAME IS NULL
07/12/16 14:13:47
>>179
日数が引かれる
181:NAME IS NULL
07/12/16 14:27:46
>>180
ありがとう、ネットで暗黙の型変換に関するドキュメントがなかったので助かりました。
182:NAME IS NULL
07/12/17 20:47:44
SQL Server 2000/MSDEで、インスタンス一覧、データベース一覧、テーブル一覧を得るSQLってある?
朝から調べてたけど見つけられなかった。orz
183:NAME IS NULL
07/12/18 01:02:00
GUIでしか調べられないから諦めろ。
184:NAME IS NULL
07/12/18 09:38:36
sysobjectsでも眺めてろ
185:NAME IS NULL
07/12/19 01:05:47
次のようなテーブル
ID VALUE
----------
0 NULL
1 NULL
2 1
3 NULL
4 NULL
5 0
6 NULL
7 NULL
8 2
9 NULL
10 NULL
があったとして、
ID VALUE
----------
0 NULL
1 NULL
2 1
3 1
4 1
5 0
6 0
7 0
8 2
9 2
10 2
のようにNULLの箇所を直近の値で埋めるような方法はありますか?
186:NAME IS NULL
07/12/19 01:11:03
全データ、掴んで一件一件回すしかないな
件数によっては果てしなく時間がかかる
187:NAME IS NULL
07/12/19 02:00:20
>>185
UPDATE Table AS T1
SET value=(SELECT value FROM Table WHERE id=(SELECT max(id) FROM Table WHERE id<T1.id AND value IS NOT NULL))
WHERE value IS NULL;
DBによってはちょっと変えないとダメかな。
188:NAME IS NULL
07/12/20 14:52:00
>>187
できました。どうもありがとう。
189:NAME IS NULL
07/12/20 15:29:03 WQA8NgrI
key data
----------------
1 a
1 a
1 b
1 b
1 a
2 b
2 a
2 a
というテーブルから
key a b
--------------------
1 3 2
2 2 1
というExcelのピボットの様なデータを取得したいのですが、どういうSQLになりますか?
a,bというのは固定なので、仮にcというデータがあっても無視して構いません。
環境はSQLServer2005です。
よろしくお願いします。
190:NAME IS NULL
07/12/20 16:12:54
SELECT key,SUM(CASE data WHEN 'a' THEN 1 END) AS a,
SUM(CASE data WHEN 'b' THEN 1 END) AS b
FROM table GROUP BY key ORDER BY key;
とかでいいのかな?
191:NAME IS NULL
07/12/20 19:14:43
{ID, SUBID, SEQ} の 3項目があるテーブルに
{1, 1, 0}
{1, 2, 0}
{1, 3, 0}
{1, 3, 0}
{1, 3, 0}
{1, 4, 0}
{1, 5, 0}
:
で、ID, SUBID でみた時に重複していればSEQに連番を振りたい(SEQの初期
値は0)んですが、これをカーソルを使わずに処理可能でしょうか?
{1, 1, 0}
{1, 2, 0}
{1, 3, 0}
{1, 3, 1}
{1, 3, 2}
{1, 4, 0}
{1, 5, 0}
:
192:NAME IS NULL
07/12/20 20:13:24
UPDATE対象のレコードを特定できないから無理じゃね?
RANK関数を使えば結果セットを得ることはできるから
それを一旦別テーブルに突っ込んで元テーブルと総入れ替えするとか。。。
193:NAME IS NULL
07/12/21 01:10:18
>>192
そこまでするなら普通にcursor使うけど。
最初はこう考えたんですよ
update tab A
set A.seq = (select count(*) from tab B where A.id = B.id and A.subid = B.subid and B.seq = 0)
1行目から順番に処理してるとして、3行目の処理の時点で
{1, 1, 1} 1
{1, 2, 1} 2
{1, 3, 3} 3 ←今ここ
{1, 3, 0} 4
{1, 3, 0} 5
{1, 4, 0} 6
{1, 5, 0} 7
すると、4行目を処理する際にはseq=0の行は1行減ってるから
{1, 1, 1} 1
{1, 2, 1} 2
{1, 3, 3} 3
{1, 3, 2} 4 ←今ここ
{1, 3, 0} 5
{1, 4, 0} 6
{1, 5, 0} 7
まあ、やってみたらダメだったわけだがw
194:NAME IS NULL
07/12/21 01:55:49
一時シーケンスで仮番振って、再処理。
まぁ複数行のバッチ処理には違いないが。
CREATE TEMP SEQUENCE t_seq;
UPDATE Table AS T1 set c3=nextval('t_seq') WHERE 1<(SELECT count(*) FROM Table AS T0 WHERE (T0.c1,T0.c2)=(T1.c1,T1.c2));
UPDATE Table AS T1 SET c3=c3-(SELECT min(c3) FROM Table WHERE (T.c1,T.c2)=(T1.c1,T1.c2)) WHERE 1<(SELECT counT(*) FROM Table AS T0 WHERE (T0.c1,T0.c2)=(T1.c1,T1.c2));
195:NAME IS NULL
07/12/21 07:48:40 vB2UAvni
サーブレットからJDBCを経由して、select count~のSQLを実行した時に、DBMSは排他領域を使用しますか?
196:NAME IS NULL
07/12/21 18:36:46
実行計画って、対象となるテーブルのレコード件数で変わるよね?
数件しかなければインデックス使わない、数万件ならインデックスを使う、み
たいな。
197:NAME IS NULL
07/12/21 18:46:11
>>196
オプティマイザの実装次第だろ。
オプティマイザヒント使うとか
幾らでも変えようのあるRDBMSも存在するしな。
198:NAME IS NULL
07/12/23 01:32:21 HZ1Naom1
SQLに関して質問があります。
DBはオラクル10gです
以下のレコードが格納されていまして、
1 10 A
2 20 B
3 10 C
4 10 A
5 20 B
6 30 A
取得したいのは
1 10 A
2 20 B
6 30 C
2列目の重複を省きたいのです。重複さえ省ければどの行を取得しても
大丈夫です。(例えばAに関しては4 10 Aの行でもOK)
自己結合を使って取得することはできたのですが、
出来ればサブクエリは使いたくありません…
(実際は50万行くらいある表なのでできるだけパフォーマンスを良くしたいのです)
オラクルの関数などを使って取得できないでしょうか?
よろしくお願いします。
※自分が考えたのは以下のSQLです
select * from A a1 where 1列目=(select max(1列目) from A a2 where a1.2列目=a2.2列目)
199:NAME IS NULL
07/12/23 02:14:35
distinctぢゃだめなのか?
200:NAME IS NULL
07/12/23 02:23:12
>>199
DISTINCTは行全体が一致しないと無理っぽいです…
201:NAME IS NULL
07/12/23 02:37:26
> 6 30 C
って存在しないのだが?
202:NAME IS NULL
07/12/23 02:48:43
>>201
6 30 Aの間違いでした。すみません。
203:NAME IS NULL
07/12/23 03:05:09
>>198 のクエリは相関サブクエリがあってインデックスが効くならまだしも
1+50万回(行数分)のseqスキャンが走ってそうだな。
で、Oracle独自の関数でいいのならOracleスレで聞いた方がいいかも。
ちなみにPostgreSQLなら DISTINCT ON を使えば1回のスキャンで済むので、
「Oracle "DISTINCT ON"」でググれば何かわかるかもしれない。
204:NAME IS NULL
07/12/23 04:11:22
>>203
DISTINCT ONっていうのがあるんですか!それはかなり便利ですね。
postgreSQLはまだ一度も使ったことないですが、覚えておいていざというときに使いたいと思います!
「Oracle "DISTINCT ON"」で調べたところ、やはり自己結合を使う方法しかないっぽいです…
とりあえず自己結合をする形で進めて、パフォーマンスに影響がでるようだったら他の方法を
考えてみます。ありがとうございました!
205:NAME IS NULL
07/12/23 04:58:53
>>204
PostgreSQLのDISTINCT ONは目的カラムでORDER BYして
一つ目をとったら出力して違った値が出るまでスキップ、
そして出力の繰り返し。ORDER BY 2列目,1列目 DESCをつけると
各2列目の値で1列目が最大の行をとってくれると云うことになる。
と言うことで、そんなに難しい訳でもないからPL/SQL等でで自作関数
でも作った方がいいんじゃね。
206:NAME IS NULL
07/12/23 08:45:39
>>175
WHERE
207:仕様書無しさん
07/12/23 11:06:55
>>198
なんか難しく考えてるようだけど、ROW_NUMBER関数と
ROWID擬似列を組み合わせればできんじゃね?
208:NAME IS NULL
07/12/23 11:37:01
select max(a1), b1, max(c1)
from tbl
group by b1
じゃだめなん?
209:仕様書無しさん
07/12/23 11:40:43
>>198
すまね。>>207で言ってたROWID擬似列はいらなかった。
select *
from ( select row_number()
over (partition by col3
order by col3) grp_num
,col1
,col2
,col3
from test
)
where grp_num=1
order by col1
;
結果↓
GRP_NUM COL1 COL2 COL3
---------- ---------- ---------- ----------
1 1 10 A
1 2 20 B
1 3 10 C
ずれまくりなのは勘弁。
210:NAME IS NULL
07/12/23 17:17:42
ユーザID 名前
123 あ
223 い
555 う
上記の状態でたとえばユーザIDを昇順で並べた時に3行目の名前を変更する方法ありますか?
UPDATE NAME set 名前='AAA' (ここの書き方がわからない)
ORDER BY ユーザID LIMIT 2,1←これで一応3行目が指定出来ると
211:NAME IS NULL
07/12/23 17:56:53
update NAME set 名前='AAA'
where ユーザID=(select ユーザID from NAME order by ユーザID limit 2,1)
じゃダメなん?
212:NAME IS NULL
07/12/23 23:17:35
>>211
UPDATE name SET 名前='AAA' WHERE ユーザID=(SELECT ユーザID ORDER BY ユーザID LIMIT 3, 1);
これでやってみたんですが,更新されません・・・
まだ勉強不足だorz
213:NAME IS NULL
07/12/23 23:42:06
なんで2,1が3,1に変わっちゃうんだ?
select ユーザID from NAME order by ユーザID limit 3,1
で何も結果が出てこなければもちろん何も更新されない。
214:NAME IS NULL
07/12/23 23:48:34
>>213
特定の1行を更新できれば良いので番号はなんでもOKです(汗
調べたらUPDATE … WHERE ユーザID IN (SELECT … LIMIT)って方式で可能みたいなんですが
INを使用するとLIMITが併用出来ないらしいです.
他の方法でなんとか任意の行を選択するのを考えます・・・
215:NAME IS NULL
07/12/25 11:34:20
>>210
UPDATE Table AS T1
SET name = 'AAA'
FROM (SELECT id,(SELECT count(*) FROM Table WHERE id<T2.id) AS cnt FROM Table AS T2) AS T3
WHERE T1.id=T3.id AND cnt=2;
ユーザIDは当然ユニークで、不等号で順列通りの比較が可能という条件で、
cnt=2というのは3列目な。
でも、MySQL(かな?)で動くかどうかは知らん。
216:NAME IS NULL
07/12/25 17:25:26 8tRohosM
第一列各行に一意の整理番号を割り振った表計算ドキュメントをデータソースとし、バラバラの整理番号を指定して第二以降の列も抽出する事なんてOOoBase上でHSQLで出来ますか?
217:NAME IS NULL
07/12/26 06:12:18
・MySQL4
・テーブルデータ comment テーブル
post_id, comment
1, テストコメント
2, コメント
・欲しい結果
該当結果がなくても、post_id, nullの形で3を含めた結果が欲しい
・実行しているSQL分
SELECT
post_id, COUNT(*) AS count
FROM
comment
WHERE
post_id IN (1,2,3)
GROUP BY
post_id
現状、post_id 1,2の結果しか出ない
post_id 3も0または、nullの形で出したい。
218:NAME IS NULL
07/12/26 06:35:38
>>217
ないものを出せと言われてもな・・・
コメントテーブルに 3, NULL のレコードを入れとくか、
必要な post_id を列挙した別テーブルを用意しといて OUTER JOIN するか
じゃない?
219:NAME IS NULL
07/12/26 11:27:42
TBL_AとTBL_Bがあって、どちらもSEQがPKです。
Aの内容をBにコピーしたいのですが、AのSEQ順を崩さず、かつBにコピーする
際のB.SEQはSEQオブジェクトを使いたいのです
INSERT INTO TBL_B
SELECT
SEQ.NEXTVAL,
~
FROM
TBL_A
ORDER BY
TBL_A.SEQ
これでTBL_Bの順序は必ず保証されるのでしょうか?
カーソルで回して1行ずつinsertしないとだめでしょうか?
220:NAME IS NULL
07/12/27 17:47:28 EI8HSTce
結合に関する話です。
SELECT * FROM t1
LEFT JOIN t2 ON t1.id=t2.t1_id
WHERE t1.id=1
といった結合の場合、t1.id=t2.t1_id の条件に合致するレコードが、t2テーブルに複数ある場合、
結果セットとして、複数レコード(t1のデータは同一)が返ってきますが、
1件しか返ってきてほしくない場合は
GROUP BY t1.id
とするのが、普通の方法でしょうか?
他に、もっと適切な方法はあるのでしょうか?
221:NAME IS NULL
07/12/27 19:45:38
t2テーブルに複数ある場合、1件だけ返したいと言うんだけど
t2テーブルのどの1レコードを選ぶの?
t1.id, t2.id, t2.id2, t2.data
1, 1, 1, あああ
1, 1, 2, いいい
2, 2, 1, ううう
3, null, null, null
ここからどんな結果を出したいの?
222:NAME IS NULL
07/12/27 22:33:07
>>220
1件だけにしたい場合はどういう条件で1件に絞るのかを記述するのが普通です。
よく使うのはmaxとかminとかです。
この場合は必然的にgroup byも使うことになります。
223:NAME IS NULL
07/12/27 23:56:04
厳密に言えば、min()/max()は1「件」を選ぶんじゃないね。
224:220
07/12/28 10:22:49 p8DR0nlD
ありがとうございます。
今回の場合、
関連するt2のデータが1件以上存在することさえ確かめられればいいので、
t2のデータについては、どれが取れてきても構いません。
(t2のデータ自体は使わない)
t1とt2の関係は1対多です。
とすると、やっぱりGROUP BYのみでOKですかね?
225:NAME IS NULL
07/12/28 10:48:27
DISTINCT は使えるかな?
226:NAME IS NULL
07/12/28 12:21:56
foo(
number INTEGER -- 登録番号
PRIMARY KEY
,dataA DECIMAL(13,6) -- aの値
NOT NULL
,datab DECIMAL(13,6) -- bの値
NOT NULL
,dataC DECIMAL(13,6) -- cの値
NOT NULL
,name TEXT -- 名前
NOT NULL
,today TEXT -- 日付
NOT NULL
);
というテーブルが有ります。
例えばこの中には、
1, 100, 500, 400, マサル, 12/23
2, 200, 400, 300, メソ, 12/24
3, 300, 430, 200, フーミン, 12/25
4, 200, 300, 600, マサル, 12/26
5, 500, 250, 400, モエモエ 12/27
のようなデータが入っています。
そして、
SELECT * FROM foo WHERE dataA > 90 AND dataA < 210
というクエリーを発行しています。
しかしこの方法だと、
1, 100, 500, 400, マサル, 12/23
2, 200, 400, 300, メソ, 12/24
4, 200, 300, 600, マサル, 12/26
とマサルが二回出てきてしまいます。
データベースの設計が悪いと思うんですが、
どのように正規化すれば、宜しいでしょうか?
また、
6, 150, 500, 400, マサル, 12/28
のような感じでnumber,dataA,dataB,dataC,todayは違うけれどnameが同じ場合、
うまくnameの重複を無くして、INSERT出来るようにしたいです。
227:221
07/12/28 12:34:26
少しエスパーすると
t2に該当レコードがなくてもt1のレコードは返してほしいんだよね。
select distinct t1.id from t1, t2
where t1.id = t2
これだとt2に該当するレコードが無いとt1も出ないからダメなんだよね。
SQL> select * from t1;
ID
----------
1
2
3
SQL> select * from t2;
ID ID2 DATA
---------- ---------- --------------------
1 1 a
1 2 b
2 1 c
SQL> r
1 select t1.id, nvl(tmp.flag, 'NO HIT')
2 from t1
3 left outer join
4 (
5 select distinct t1.id, 'HIT' flag from t1, t2
6 where t1.id = t2.id
7 ) tmp
8 on t1.id = tmp.id
9* order by 1, 2
ID NVL(TM
---------- ------
1 HIT
2 HIT
3 NO HIT
これでよい?
nvlはOracleの独自ファンクションだから適当に改造してくれ。
228:226
07/12/28 13:33:19
誰か~。
229:NAME IS NULL
07/12/28 13:37:33
>>228
きちんと要件定義するのが先。
230:NAME IS NULL
07/12/28 13:39:46
マサルが重複していてはいけない理由が他の人に伝わってない。
俺もわからん。
231:NAME IS NULL
07/12/28 13:47:30
2件あるマサルのうち1件だけ取り出したいにしても
どっちのマサルが欲しいのかが不明。
232:220
07/12/28 14:23:58 p8DR0nlD
>>225
あ、そうか。
こういう場合はGROUP BYじゃなくて、
DISTINCTの方が正しいですね。
(結果は変わらないようですが)
>>227
> t2に該当レコードがなくてもt1のレコードは返してほしいんだよね。
その通りです。
確かに、書いていただいたSQL文だと、やりたい意図がかなり明確ですね。
(でもちょっと重そうなSQL文)
うーむ。どうしようかな。
>>226
エスパー向け問題ですね。
正規化の話としては、userテーブルなどを作って、
名前はそっちに持たせて、
fooテーブルにはそのidだけ入れとくってのが正解だと思います。
user (
id INTEGER PRIMARY KEY,
name TEXT NOT NULL
);
foo(
number INTEGER PRIMARY KEY
,dataA DECIMAL(13,6) NOT NULL
,datab DECIMAL(13,6) NOT NULL
,dataC DECIMAL(13,6) NOT NULL
,user_id INTEGER NOT NULL
,today TEXT NOT NULL
);
233:220
07/12/28 15:08:57 p8DR0nlD
>>227
すみません。急いで訂正。
いまのところ、GROUP BYで意図していた結果が得られていたので、
そのままにしていたのですが、実際に書いていたSQL文が、
文法的に間違いだということが分かりました。
t1 (
id INTEGER PRIMARY KEY,
name TEXT,
description TEXT
)
t2 (
id INTEGER PRIMARY KEY,
t1_id INTEGER,
data TEXT
)
SELECT t1.id, t1.name, t1.description, t2.id
FROM t1 LEFT JOIN t2 ON t1.id=t2.t1_id
GROUP BY t1.id
というクエリを投げて、
t2.idがNULLかどうかを見てt1の特定レコードに関連する
t2テーブルのレコードがあるか?を見ていました。
意図通りの結果を得られていたわけです(SQLite3)。
でも、SQLの文法としては間違いのようです。
間違い1:GROUP BYは集合関数なんだからDISTINCT使えよ
間違い2:GROUP BYには取得するカラム全部指定しなきゃダメ
というわけで、正しくは>>227以外にないということですかね?
234:227
07/12/28 19:51:20
>>233
たしかMySQLもGROUP BYの指定漏れは動く仕様だったと思う。
SQL標準からすると誤りなのは確か。
もちろんOracleではエラー。
なんか227は冗長な気がしてきた。
SQL> select * from t1;
ID NAME DESCRIPTIO
---------- ---------- ----------
1 tanaka manager
2 takahashi sales
3 satou developer
SQL> select * from t2;
ID T1_ID DATA
---------- ---------- ----------
1 1 computer
2 1 foma
3 2 wimax
SQL> r
1 select distinct t1.id,
2 t1.name,
3 t1.description,
4 nvl(t2.t1_id, -999) flag
5 from t1 left outer join t2
6 on t1.id = t2.t1_id
7* order by t1.id
ID NAME DESCRIPTIO FLAG
---------- ---------- ---------- ----------
1 tanaka manager 1
2 takahashi sales 2
3 satou developer -999
これでどうか
235:NAME IS NULL
07/12/28 21:51:43
>>233
そこまでわかってたら、これでいいんじゃ?
select t1.id, t1.name, count(t2.id)
from t1
left outer join t2 on t2.id = t1.id
group by t1.id, t1.name
236:NAME IS NULL
07/12/28 22:15:29
mysql 5.0.45
株価の週足を作ろうとする場合、
kabukaテーブルが
stockcode 銘柄コード
vol_date 出来高年月日
startingprice 始値
highprice 高値
lowprice 安値
closingprice 終値
volume 出来高
とあったとして
select max(highprice),min(lowprice),
sum(volume) from kabuka
where stockcode=~
and vol_date between yyyy-mm-dd1 and yyyy-mm-dd2
で週間高値・安値・出来高は得られますけど、yyyy-mm-dd1
とyyyy-mm-dd2は予め判っているとして、週初始値、週末終値
をこのsqlのなかで求める事って出来ますか?
237:NAME IS NULL
07/12/29 00:52:30
select句の中に週初始値、週末終値をそれぞれ求める
スカラー副問合せを書けばできると思うけど。
それかselect句の中でcase文を使ってごにょごにょやるとか。
238:NAME IS NULL
07/12/29 14:39:28
二つの列が一致しているレコードの数を知りたいのですが、どうすればよいでしょうか。
名前 都道府県 年齢
AAA 東京 32
BBB 東京 31
BBB 千葉 30
BBB 千葉 29
CCC 千葉 28
CCC null 27
名前と都道府県の両者が一致しているものを1件と数える場合、
3,4行目は同じなので、5を得たいです。
DBはDerbyで、
select count(distinct 名前, 都道府県) …
select count(名前) from (select 名前, 都道府県 from テーブル group by 名前, 都道府県)
はどちらも使えないみたいです…。
select count(distinct 名前)ならできるのに><
239:NAME IS NULL
07/12/29 14:59:01
SELECT count(*) FROM (SELECT ... GROUP BY 名前,都道府県);
240:NAME IS NULL
07/12/29 17:51:32
こういうのはできないんだっけ?
select count(distinct 名前||都道府県)
241:NAME IS NULL
07/12/29 21:15:50
table:tbl
__________
id,name
_________
123,aa
456,bb
789,cc
234,dd
____________
という表にSELECT * FROM tbl WHERE id=456でid直打ちした場合、
前後の行の有無を調べる方法を教えてください(idは不連続です)
242:NAME IS NULL
07/12/29 21:50:38
前後ってのはどのカラムをどういう順序で並べたときの前後なのか示さないと無意味。
243:NAME IS NULL
07/12/29 23:09:04
>>239
>>238をよく読め
244:239
07/12/29 23:53:36
ありゃ? なんか勘違いしてる?
> 名前と都道府県の両者が一致しているものを1件と数える場合、
> 3,4行目は同じなので、5を得たいです。
で、>>239だと思ったんだが、あぁ、1行目の意味はさっぱりだし、
Derbyもしらんので、>>239で違うのなら俺にはさっぱりわからんわ。
245:NAME IS NULL
07/12/30 05:57:29
>>239
>>238の下から3行目。すでにダメだと書いてあるだろ。
246:NAME IS NULL
07/12/30 17:15:18
>>241
直後は
SELECT min(id) FROM tbl WHERE id>456
直前は
SELECT max(id) FROM tbl WHERE id<456
で返り血の有無を判断すればいいんじゃね?
247:NAME IS NULL
07/12/31 11:36:08
>>246
頭いいなオマエ
248:NAME IS NULL
07/12/31 13:15:27 +l9W5+We
質問させていただきます。
年内のデータから、年初めと年終わりのデータを欲しいと思っています。
つまり
select * from hoge where hiduke >= '2007/1/1'
その中から hiduke = min( hiduke ) とmax(hiduke) したいのですが
どうすればいいのでしょう?
249:NAME IS NULL
07/12/31 15:34:47
select * from hoge
where hiduke =
(select min(hiduke) from hoge where hiduke >= '2007-01-01' and hiduke < '2008-01-01')
union
select * from hoge
where hiduke =
(select max(hiduke) from hoge where hiduke >= '2007-01-01' and hiduke < '2008-01-01');
250:NAME IS NULL
07/12/31 15:35:02 5qw/Iwgf
URLリンク(click.j-a-net.jp)
251:NAME IS NULL
07/12/31 17:44:17
whereのandでいいじゃん
252:NAME IS NULL
07/12/31 19:55:12
>>251
whereのandだと、なぜか引っかかるの0件。
たぶん、min(hiduke)で、はるか昔のとandになってるような。
>>249
サンクスです。
253:NAME IS NULL
07/12/31 21:18:19
そりゃ最大でかつ最小なんだから1件だけのとき以外は0件だろう
OR でいいのでは
254:NAME IS NULL
08/01/01 00:33:10 Q6OJPCZ+
あけましておめでとう(′∀`)ノシ
ところで1つの行から複数の行を返すSELECT文ってどう書くですか?
たとえばテーブルが
----+--
HOGE 3
のときに
----+--
HOGE 1
HOGE 2
HOGE 3
みたいな結果せっとが欲しいんですけど…
教えて!エロいひと!
255:254
08/01/01 01:30:53
日本酒飲みながらこんなの思いついたけど有り?
こんなダミーテーブル(FOO)を作る
REF
---
1
2
3
4
5
…
MAX(BAR.NUM)
んで抽出対象のテーブルBARに対して
NAME NUM
-----+---
HOGE 3
SELECT NAME,REF
FROM FOO,BAR
WHERE NUM >= REF
でいいのかな?
あんましCROSS JOHN使ったことないしなぁ…
(自宅には携帯しかないので判りにくくてすみません)
256:NAME IS NULL
08/01/02 05:19:27 8Xd67UwA
・DBとバージョン
mysql ver5
・テーブルデータ
aaa,bbb
-------
1,111
2,121
3,111
4,111
5,143
・欲しい結果
aaa,bbb
-------
2,121
4,111
5,143
・説明
2番目のカラムでかぶってるのがあったら
一番下から持ってくる方法をお願いします。
257:NAME IS NULL
08/01/02 05:51:31
mysql> select max(aaa) aaa, bbb from ab group by bbb order by 1;
+------+------+
| aaa | bbb |
+------+------+
| 2 | 121 |
| 4 | 111 |
| 5 | 143 |
+------+------+
3 rows in set (0.00 sec)
258:NAME IS NULL
08/01/02 06:04:25 8Xd67UwA
>>257
すばやい回答ありがとうございます。
259:NAME IS NULL
08/01/02 23:09:25 UHDITXaq
・DBとバージョン
mysql 5
・テーブルデータ
+------+------+
| id | bunrui-A | bunrui-B | bunrui-C.......................................
+------+------+
| 2 | aa | null | bb
| 4 | null | cc | dd
| 5 | ee | null | null
+------+------+
・欲しい結果
+------+------+
| id | youso1 | bunrui1 | youso2 | bunrui2.......
+------+------+
| 2 | aa | bunrui-A | bb | bunrui-C
| 4 | cc | bunrui-B | dd | bunrui-C
| 5 | ee | bunrui-A | null | null
+------+------+
・説明
類語データベースを作っています。
一つのレコードには同意語が品詞別にカラムに納められています。
新しい品詞が出る度に新しいカラムを足していき、品詞分類カラムが20を超えてしまいました。
一つのレコードあたり最大でも五種類の品詞の単語しか持たないため
一つのレコードで15以上のカラムがnullとなっています。
そのため、意味1、品詞1、意味2、品詞2、、、、という形にテーブルを整理し直したいのですが...
caseで場合分けしてnullで無い場合はinsertみたいにしようと思ったのですがうまくいきません...
教えて!エロイ人!
260:NAME IS NULL
08/01/03 07:53:56
品詞1と品詞2の違いは何?
違いがないんだったら、その「欲しい結果」を第一正規形にしろ。
261:NAME IS NULL
08/01/03 16:37:08 qHl7adYm
>>260
ググってきました。第一正規形 = 繰り返しグループの排除でOK?
説明が足りなかったのですが、今のテーブルは
+------+------+
| id | 意味分類id | | 意味 | 一般語 | 敬語 | 文語.......
+------+------+
| 2 | 1 | 食べる| 食べる、食う、 | 召し上がる | ヌル
| 4 | 2 | 考える |考える |ヌル |思考する
| 5 | 2 | よく考える |よく考える、深く考える| ヌル|熟考する
+------+------+
+------+------+
| id |意味分類
| 1 | 食に関する言葉
| 2 | 考えることに関する言葉
+------+------+
一般語、敬語、等の語の分類カラムは外国語です。
実は、259で言った品詞分類とは語の分類のことで、文語、敬語、ことわざ、重語、王語....etcみたいな感じです。
正規化するとこんな感じですか↓?
意味分類テーブル→そのまま
意味テーブル
+------+------+
| id | 意味分類id |意味 |
+------+------+
| 1 | 1 | 食べる |
| 2 | 2 l 考える |
| 3 | 2 | よく考える |
+------+------+
単語テーブル
+------+------+
| id | 意味ID | 単語 | 語の分類|
+------+------+
| 1 | 1 | 食べる、食う | 一般語
| 2 | 1 | 召し上がる | 敬語
| 3 | 2 | 考える | 一般語
| 4 | 2 | 思考する |文語
+------+------+
262:NAME IS NULL
08/01/03 19:53:28
> 新しい品詞が出る度に新しいカラムを足していき、
> 品詞分類カラムが20を超えてしまいました。
だったら品詞分類テーブルも作っといたほうが。
+--+----------
|id|品詞分類名
+--+----------
| 1|一般語
| 2|敬語
| 3|文語
+--+-----------
単語テーブルに「食べる、食う」とあるのは
正規化できてないだろう。
+--+------+----------+------------
|id|意味ID|品詞分類ID|単語
+--+------+----------+------------
| 1| 1| 1|食べる
| 2| 1| 1|食う
| 3| 1| 2|召し上がる
| 4| 2| 1|考える
| 5| 2| 3|思考する
+--+------+----------+------------
こうじゃね?
263:NAME IS NULL
08/01/05 02:10:08 YdrW63jX
以下のようなテーブルがあります。
それぞれの所属に対して同じ名前の人はいないとします。
ID 所属 名前
--------------------
01 社員 菊池
02 社外 矢薙
03 社外 小暮
04 社員 田中
05 社外 田中
06 社員 矢野
社員の菊池さんと矢野さん、社外協力者の田中さんの3人を取得したい場合、条件式を
(所属=社員 AND 名前=菊池) OR (所属=社員 AND 名前=矢野) OR (所属=社外 AND 名前=田中)
にしなければならないと思いますが、これを IN のようにスマートに記述する方法はありませんでしょうか?
文字列合成して IN ……というのも考えましたが、速度的にマズそうですし。
ちなみにMySQL 3.23です。
264:NAME IS NULL
08/01/05 06:23:14
SQLの標準としては
(所属, 名前) in (('社員', '菊地), ('社外', '田中'), ...)
と書けることになっている。
MySQLで書けるかどうかはシラネ。
265:NAME IS NULL
08/01/05 15:40:34 nKj5MD+j
>SQLの標準としては
> (所属, 名前) in (('社員', '菊地), ('社外', '田中'), ...)
>と書けることになっている。
MSSQL鯖使いの俺。
知らなかった!画期的だ!と思って試してみたが......
出来なかった.....orz
>文字列合成して IN ……というのも考えましたが、速度的にマズそうですし。
レコード数と抽出対象数でも変わると思うが、orでだらだら記述するより早いと思うよ。
あとはインデックスとか設計の問題だろ。
266:NAME IS NULL
08/01/05 15:43:01
SQL標準だったのか。
Oracle以外で使えるのを見たことがなかったので、
Oracleの拡張だと思ってた。
267:263
08/01/05 16:14:03
thxです。
>264
残念ながら、ウチの環境でも出来ませんでした……。
すげー便利そうなのに。
>265
ORってそんなに速くなかったんですね。
パターンとindexを変えつつ実測してみます。
268:NAME IS NULL
08/01/05 16:33:16
>>267
文字列連結して...なんてtrickyな方法は初心者のうちはやらんほうが良い。
どっちにしろ、大してメリットはない。
269:NAME IS NULL
08/01/05 16:45:57 nKj5MD+j
265だ。SQL鯖だが検証してみた。
3レコード抽出
200万件のテーブルだと
文字連結 3秒
or 1秒以下
1万件のテーブルだと、どちらも1秒以下
実行プランを見ると、1万件だと同じ、200万件のorだと内部で最適化している。
俺は、レスポンスが同じなら文字連結には可読性が高いというメリットがあると思う。