• ベストアンサー

大量の項目を対象に効率的に検索したい

たとえば、こちらに「こだわり条件で絞り込む」という機能があります。 http://www.athome.co.jp/bklist?ITEM=ks&ART=13&AREA=12&KEN=13&DOWN=1 MYSQLでこのような機能を実現する場合、 1項目1カラム、全てにインデックスを設定。 または 該当する項目を1カラムにまとめて格納し(CS,CATV,グルニエ,…)、その中に一致する文字の有無を判断させる。 どのような構造だと効率的に動くようになるのでしょうか?

質問者が選んだベストアンサー

  • ベストアンサー
  • Siegrune
  • ベストアンサー率35% (316/895)
回答No.3

市町村の指定だと、 データ上は1項目しかないはずなので in ('東京都千代田区',・・・)に選択した項目の内容を入れる。 (データ上にコードで持っていて、in句の中もコードを指定するほうが早いですが。) こだわり条件のほうでは、例えば、 「収納」を例とすると、 ウォークインクローゼット(0)床下収納(0) を、 「ウォークインクローゼット、床下収納」と格納し、 検索は一致する文字列を検索するという方法1と、 「11」(1文字目は、ウォークインクローゼット有無で1はあり。2文字目は、床下収納有無で・・・) と格納し、like演算子を利用して'11'を探す。 ウォークインクローゼットのみチェックなら、'1?'を探す。 とする方法2とあります。 ばらばらに項目として持つ方法3もありますが。 方法1:検索はやや遅い。プログラムも分かりやすいが、「ウォークインクローゼット」をただの「クローゼット」に変える等の名称変更の対応が面倒(データ全件修正必要)。 方法2:検索はやや早い。プログラムは分りにくくなり、追加や削除の対応が面倒。 (ビットマップインデックスが使えるなら、同じような考え方で、検索はより早くなります) 方法3:全件検索に近くなってしまい遅くなる可能性が高い。 (すべての項目に個別にインデックスをつけても、複数の条件を指定されたら、検索時にはどれか1個しかインデックスはつかえないのでほぼ一緒。) プログラムは分りやすく、追加や削除、変更への対応は簡単。 どれも一長一短なので、要件にあわせて何を優先するかで選んでください。

taurin1000kg
質問者

お礼

ありがとうございます。 >in ('東京都千代田区',・・・)に選択した項目の内容を入れる。 選択するたびにin()の中に追加して検索させるんですね。 >(データ上にコードで持っていて、in句の中もコードを指定するほうが早いですが。) コードを持っていく、指定するとは何ですか? 方法2は指定する項目が30あれば 00100010100011100000001100100 といったデータを格納するということですね。 方法1と2は管理がすごく大変そうです。 方法3が形としてはいいですが、遅いのが残念です。 Postgresqlなら高速に動き、管理も楽…MYSQLにはムリなのですね

全文を見る
すると、全ての回答が全文表示されます。

その他の回答 (4)

  • Siegrune
  • ベストアンサー率35% (316/895)
回答No.5

ANO.3ですが。 >(データ上にコードで持っていて、in句の中もコードを指定するほうが早いですが。) コードを持っていく、指定するとは何ですか? 物件テーブル上は、 101とか102とかコードでもっていて 住所マスタで、 101,'東京都千代田区' ・・・ を別に持つ。 画面は住所マスタから選択肢を表示し、 チェックされたら in('101','102'・・・) のようにコードでin句を組み立てるという意図でした。 >方法2は指定する項目が30あれば >00100010100011100000001100100 >といったデータを格納するということですね。 その通りです。 但し、全部1つにする必要はなく、条件の分類毎に1項目作ればいいと思います。 例えば、先ほどの回答では、「収納」が2桁、「・・・」がn桁・・・という感じです。 何も指定されていなければ、select文のwhere句の中に入れる必要ないので。 方法2の下に 「(ビットマップインデックスが使えるなら、同じような考え方で、検索はより早くなります)」 をつけたのは誤解を招いたかもしれません。 方法3のやり方で、方法2のような検索処理をしてくれるというイメージが近いです。 MySQLにはないようですのであまり書く意味が無かったですが。

taurin1000kg
質問者

お礼

良く分かりました。どうも有難うございました。

全文を見る
すると、全ての回答が全文表示されます。
  • yambejp
  • ベストアンサー率51% (3827/7415)
回答No.4

そんなに深く考えなくても 条件テーブル、物件テーブル、条件=物件テーブルの3つに分ければ それなりにはやく、拡張性も高い構成になります 条件テーブルに条件をカテゴライズするカラムを用意しておけばより 検索性があがります

taurin1000kg
質問者

お礼

MYSQLですむ方法があるんですね! http://www.athome.co.jp/bklist?ITEM=ks&ART=13&AREA=12&KEN=13&DOWN=1 こちらの場合は 価格、間取り、建物面積、土地面積、駅からの徒歩、築年数、情報公開日、アピール、画像、人気のこだわり条件、という検索条件があります。 >条件テーブル、物件テーブル、条件=物件テーブルの3つに分ければ こういうことでしょうか。 条件テーブル(人気のこだわり条件): 条件ごとにbool型のカラムに0か1を入れる。 --------------------------------------- id | CS | CATV | グルニエ | … --------------------------------------- 11220|0  |1   |0      | … 11221|1  |1   |1      | … 物件テーブル: 価格、間取り、建物面積、土地面積、駅からの徒歩、築年数、情報公開日、アピール、画像 --------------------------------------- id | 価格 | 間取り | 建物面積 | … --------------------------------------- 11220|2220  |3LDK   |110.98  | … 11221|3220  |1K    |500.00  | … 条件=物件テーブル: こちらは何の目的でしょうか。 >条件テーブルに条件をカテゴライズするカラムを用意 カテゴリー化したカラムを条件テーブルに追加 --------------------------------------- id | CS | CATV | 水周り | … --------------------------------------- 11220|0  |1   |0      | … 11221|1  |1   |1      | … ということですか?

全文を見る
すると、全ての回答が全文表示されます。
  • nora1962
  • ベストアンサー率60% (431/717)
回答No.2

そもそも、このような検索ならビットマップインデックスを使用できるPostgresqlのほうが向いているのではないでしょうか。 MySQLを選択せざるを得ない理由があるのなら別ですが。

taurin1000kg
質問者

お礼

http://www.athome.co.jp/bklist?ITEM=ks&ART=13&AREA=12&KEN=13&DOWN=1 いろんな検索、表示順序の変更、何件中何件、1ページ目、とりあえず保存機能、いろいろ機能がありますが、画像は格納する予定はありませんが、こういったものはPostgresqlでやるのが基本ですか? 情報を登録したり更新したりするのは自分一人だけです。 >そもそも、このような検索ならビットマップインデックスを使用できる >Postgresqlのほうが向いているのではないでしょうか。 MYSQLは機能の豊富さも充実していて、それでありながら一番高速、業界でもシェアNO1、最強のデータベースはMYSQLらしいので、パフォーマンスが落ちなければ、できればMYSQLでやりたいと思っています。

全文を見る
すると、全ての回答が全文表示されます。
回答No.1

全て(出来る限り)の項目をBOOL型にする。 >1項目1カラム、全てにインデックスを設定。 ほとんどの項目は有るか無いかになるのでインデックスを作っても無駄。 >該当する項目を1カラムにまとめて格納し(CS,CATV,グルニエ,…)、その中に一致する文字の有無を判断させる。 最悪の手法でしょう。

taurin1000kg
質問者

お礼

>全て(出来る限り)の項目をBOOL型にする。 それぞれの項目に入れるデータは「0と1」か「trueとfalse」どちらのほうが軽いですか? >ほとんどの項目は有るか無いかになるのでインデックスを作っても無駄。 これらのカラム全部インデックス付けていないのですか。 格納するデータが1カラムに何種類以上でインデックスは役に立ちますか?

全文を見る
すると、全ての回答が全文表示されます。

関連するQ&A

  • 大量のカラムが検索対象の場合の効率的なDBの構造

    phpからmysqlのクエリを作りコンテンツを検索・絞り込みさせようと考えています。 説明するのが苦手なため画像での説明になってしまいますが、 データベースの構造 http://blog-imgs-54.fc2.com/s/k/s/sksfiosjdijf34/20120614-1.jpg 絞り込みページのイメージ http://blog-imgs-54.fc2.com/s/k/s/sksfiosjdijf34/20120614-2.jpg 種類テーブルだけは「名前」が決まれば「仲間」と「原産地」が決まるので正規化することができましたが、他はできないと思います。 現在所在地テーブルはできそうですが、市によって町名が重なってしまうところがあるので正規化していません。 特徴テーブルは、種類による一般的な特徴よりも実際の特徴を優先しているので、同じ種類でも特徴がそれぞれ違います。 テーブルを分けている理由は、その方が管理しやすいと思ったからです。 特徴テーブル、日付テーブルも同じ理由です。 コメントテーブルのデータは検索しません。 「番号」には主キーを、種類テーブルは「名前」のみ、その他のカラムには全てインデックスをつけます。コメントテーブルはつけません。 そして、絞り込みページでは、 それぞれのカラムでソートさせる機能もあります。 「絞り込み」を押すと選択した条件に全て一致するコンテンツを絞り込みます。 「詳細へ」を押すと詳細のページに入り、 詳細のページでは、そのフィールドの全てのカラムのデータを表示させます。 もっと早く検索でき、効率的な構造にしたいのですが、アドバイスをいただけないでしょうか。

    • ベストアンサー
    • MySQL
  • 中で自由にいろいろ扱えるダイアログ(?)を使うには

    http://www.athome.co.jp/bklist?ITEM=ks&ART=13&AREA=13&KEN=15&DOWN=1 こちらを開くと、いきなり中心に何かが開きますが、 この何かは、「地域から探す」の「市区郡」の「変更」を押すと開くダイアログです。 この何かというのはダイアログというのですか? チェックボックスやDB、画像、CSS、Javascriptなど自由にやっているようですが、 こちらと同じようなことをしたいです。 背景が暗くなるなど、凄く難しいでしょうか。 参考にできるサイトはありませんか? こういったサイトをみつけましたが、 http://css-eblog.com/javascript/floating-popup-window.html iframeはSSLなどを使わないとマズイ的なことが紹介されていましたので、 iframeを使わずに実現したいと考えています。 ドンピシャなライブラリがあればいいですが、できれば自作したいと思っています。

  • MySQLのインデックスについて

    MySQLのデータベースの設計についての質問です。 AとBの2つのカラムがそれぞれ一致する項目を選びたいのですが、この際AとBの文字列をハッシュにするなどし、これを新たにカラムにしインデックスにしたほうが高速でしょうか? ちなみに、常に、決まったAとBをセットにし選ぶつもりです。 よろしくお願い致します。

    • ベストアンサー
    • MySQL
  • DB+CSV

    今、仕事を受注してPHP+MySQLで情報サイトの開発を行っているのですが お客さんが結構頻繁に仕様を変更を要求してきたり ・共通項目は20カラムほど ・非共通カラムは60~70カラム 計80~90(100)カラムx7種類って感じになりそうです。 でこの非共通カラム部分をCSV形式で管理するのはどうかな?っと思ったのですが (正規化して共通部分とそうでない部分をわけろって言われそうですが) デーブル設計を 主キーカラム(オートナンバー) 共通項目Aカラム 共通項目Bカラム 共通項目Cカラム 情報タイプ(7種類ほど) CSVを格納するカラム CSV部分の設計は 「項目名(値)」って感じにそればいいかなって思いました。 (や)や仕切り部分「,」に関してユーザが入力した場合はPHP上で全角に置換してデータベースに格納 例) A(1),B(あいうえお),C(0)・・・・・・ A(0),B(かきくけこ),C(0)・・・・・・ A(0),B(たちつけと),C(1)・・・・・・ A(1),B(かきくけこ),C(0)・・・・・・ で検索時にはWhere部分を 非共通項目のカラム名をitemとしたら item like '$A(1)%' And item like '$C(0)%' って感じで検索させればいいかな?と思ったのですが ・そもそもこういう設計(DB+CSV)は駄目ですか? ・もしこういう設計でやった場合のデメリットはなんですか? ・やはり項目ごとにカラムを作った方がいいですか?

    • ベストアンサー
    • MySQL
  • 数字データ『0』の処理について

    宜しくお願い致します。 MySQLのDBに、smallint unsigned not null設定のカラムに格納してある『0』の数字データをPHPから読み出す際に、『0』として認識してしまいます。『0』として認識してしまうので、2点の問題が発生しています。 1、一度登録した後のデータをPHPの入力フォームから呼び出し、変数に格納すると、『0』がフォーム内に入ってしまう点 2、入力フォームとDBのデータを比較して、修正の有無をチェックする際にも、『0』として認識するので、修正せずに入力フォームを空の状態で送信すると、修正が有ると認識してしまう DBの『0』を空のカラムとして認識できればこの2点の問題は解決できそうなのですが、回避する方法はありませんか?

    • ベストアンサー
    • PHP
  • MySQLで同じデータにフラグ付け出来ますか?

    データベースの初心者です。MySQLを使用してSQL文を試しましたが、うまくいきません。 わかりやすく教えていただけますか? 下のような2つのテーブルで、テーブル2の項目カラムに存在するデータが、 テーブル1の区分にあれば、一致する行(NOカラムの5~7)だけに、 フラグ”1”を付けたいのです。(区分カラムに、"*"で始まるデータは除きます) 区分に、データが全て埋まっていれば簡単に出来るのですが、 先頭行のみデータがあって、次の区分まで、Nullが入っています。 テーブル1 NO 区分 フラグ 1  aaaaa   null 2  null     null 3  null     null 4  null     null 5  bbbbb   null 6  null     null 7  *nozoku  null 8  ccccc null 9  null null テーブル2 NO 項目 1  bbbbb 2  eeeee よろしくお願いします。

    • ベストアンサー
    • MySQL
  • 作成したSQLの単体テスト【エビデンスの取り方】

    作成したSQLの単体テストをするにあたって、エビデンスの取り方に悩んでおります。 テストケースとしては、 抽出した項目が正しく設定されているか、ホワイトボックスの観点から、 条件に一致する場合、しない場合で期待した値が設定されているか、などです。 抽出したものは50件のレコードで、カラムは15個程度あるとします。 エビデンスは今まではプリントスクリーンで画面キャプチャを取得して、 エクセルに張り付けていました。(SQLを使わないものの単体テスト) そしてインプットとアウトプットのデータを、テストケースのNoに合わせたファイル名にして、 フォルダに格納しておりました。 しかしSQLのテストとなると、どのようにまとめればいいか悩んでおります。 例えばあるカラムが正しい値になっているかというのは、抽出した60件のレコードのうち1レコードをコピーして、エクセルに張り付け、「このカラムのところに○○という値が設定されているため正しい」というようにするのでしょうか。 そうなるとカラムが15個あるので、15個のカラムが正しい値に設定されているかのチェックは 最低でも15個のテストケースが出来上がります。 テストケース(1):カラムAAAの値が○○であること テストケース(2):カラムBBBの値が△であること テストケース(3):カラムCCCの値が□であること    ・    ・    ・ テストケース(15):カラムYYYの値がXであること 1つの1つのテストケースに対して1レコードをコピーして、 「このカラムはこの値になっているから正しい」ということを繰り返すことになるのでしょうか。 そしてインプットとなるデータは、そのデータをDBでつかえるようにインサート文を用意すれば良いのでしょうか。 意味が伝わりにくい文章になってしまいましたが、エビデンスの取り方という点で、 どのように工夫すれば良いのか教えていただきたく、質問致しました。

  • PHP+MySQLで比較サイトが作りたいです

    初めまして。もしお力を貸していただけるならと思い質問させていただきます。 この度、ジャンルは違うのですがこのような比較サイトを作りたいと考えています。 参考URL http://creditcard.zaitsu-labs.com/?r=aw12031400664031&gclid=CJrNopbj9rICFShKpgod8iMAww 希望としては、このような検索機能と、参考サイト左下部にある、チェックした項目の比較機能です。 このようなサイトを作成する場合はMysqlに画像データや表示すべき全ての値を格納して、 取得する必要があると思うのですが、一般的な方法としての制作の流れもしくは、すべき作業はどのようなものなのでしょうか? 当方、PHPとMySQLの初心者参考書程度のごく初歩的な知識しかありませんので、実際に組むPHPのプログラムやMySQLの 操作方法等の具体的なものではなく、作業全体の流れを把握し、まず、自分が勉強すべきことを明らかにしていきたいと考えています。 また、この内容について説明のあるオススメの参考書やサイトがありましたら、併せて教えていただきたいです。 説明が不十分で申し訳ありません。もし快くお答えいただける方がいれば大変嬉しく思います。

    • ベストアンサー
    • MySQL
  • データの保存について

    phpで会員制サイトの制作を勉強しています。 データベースへはPDOで接続しています。 MySQLデータベースを使用しています。 現在、記事投稿サイトの作成を勉強しています。 できれば、記事の内容に「記事を投稿した投稿者のページ」へのリンクと、 投稿者のページに「今まで投稿した記事の履歴」がリンクつきで表示されるようにしたいです。 そこで、まだ勉強を始めたばかりなので、今ある知識だと下のような方法しか思いつきませんでした。 1、記事データ保存用のテーブルと、ユーザー情報保存用のテーブルを作成 2、記事データ保存用のテーブルのカラムにユーザーIDを格納するカラムを作成 3、記事ページからはユーザーIDを元にユーザー情報保存用のテーブルからユーザー情報を検索して投稿者のページのリンクを設置 4、投稿者ページの記事履歴には記事テーブルの全てデータからユーザーIDカラムのIDが一致するものをSELECTする 勉強とはいえ、作成中のサイトを少しでもしっかりした作りにしたいので、他にもっと良い方法があれば知りたいです! ご回答、よろしくお願いします。

    • ベストアンサー
    • PHP
  • dreamweaverCS4のライブラリ機能の設定

    dreamweaverのCS4を使ってWEB制作をしております。 ヘッダー部分が共通な10ページ程があるので 今まで使ったことがなかった「ライブラリ機能」 を設定して効率よく作業したいと考えてるのですが、 うまくいきません。 サイト定義を行い、まずはindexファイルのヘッダー部分を選択し アセットウィンドウを出し新規ライブラリ項目をクリックしても 選択箇所をドロップしてもなにも変化がないのです! サイトの定義の「ファイルを格納する場所」は mydocuments直下にしてるのですが、なにか問題があるのでしょうか。 どなたかお分かりになる方、いらっしゃいましたらお願い致します。

    • ベストアンサー
    • CSS