• ベストアンサー

テーブルの使い方について。

例えばミクシーのマイミクのようなデータは、どのようにデータベースに格納されているのでしょうか?? 以下の2つのパターンのいずれかだと思うのですが。。 パターン(1) マイミクのデータ専用のテーブルがある。 テーブル名 mymixi_t |-----------------| |USER_ID|MIMIXI_ID| |-----------------| |3   |6    | |-----------------| |512  |55    | |-----------------| |66   |6    | |-----------------| |3   |124   | |-----------------| パターン(2) ユーザープロフィールデータのテーブルの中にマイミクのカラムがある。 テーブル名 user_profile_t |-----------------| |USER_ID|USER_NAME|・・・|MYMIXI_ID| |-----------------|・・・|---------| |3   |A太   |・・・|86;48  | |-----------------|・・・|---------| |64   |B太   |・・・|32;45;678| |-----------------|・・・|---------| |1234  |C太   |・・・|8    | |-----------------|・・・|---------| |335  |D太   |・・・|11;14  | |-----------------|・・・|---------| 以上の2パターンのうち、どちらでしょうか?? また、MIXIではデータの量が膨大なため、同じ種類のデータが入るテーブルでも何個かにテーブルを分けている、とも聞いたのですが、これから人を集めようとするサイトならば、あまり気にせず、延々と縦長にデータを追加していって大丈夫なのでしょうか。どこらへんまでのデータ量なら、検索速度的に許容範囲なのでしょうか。 よろしくお願いします。 (仕様のせいか、テーブルの図がこれ以上見やすく書けませんでした。。)

  • MySQL
  • 回答数2
  • ありがとう数1

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

  • ベストアンサー
  • 0KG00
  • ベストアンサー率36% (334/913)
回答No.1

データを正規化するということは繰り返し項目をカラムを分けずに記述しますので、前者の方かと思います。検索もしやすいですし。 ただし、正規化をしすぎると性能面(検索時間)で劣る事になりますので多少は正規化を戻す事(後者のようなパターン)もあります。まあ、性能面を求められているケースでもないので前者でしょうね。

miraikako
質問者

お礼

回答ありがとうございます。 なるほど・・やはりどんどん縦長にすると検索時間に支障が出ることにはなるのですね。非常に参考になりました。ありがとうございした。

その他の回答 (1)

  • yambejp
  • ベストアンサー率51% (3827/7415)
回答No.2

後者の形式は、一つのフィールドに複数のIDを 書くというイミでしょうか? これはSQLのイミがないような書式です。 まっとうな設計者ならそんな書き方はしません。 MYMIXI_IDをプライマリキーとしたUSER_IDの整合表 テーブルをつけるのが妥当でしょう。 1テーブルで複数のフィールドを持つことは ままあることですのでそれは効率次第ですね。 もちろんMIXIで具体的にどうしているかは関係者 以外はわかりませんが。

miraikako
質問者

補足

回答ありがとうございます。 >一つのフィールドに複数のIDを書くというイミでしょうか? そういうことです。やはりそうはしない方が多いのでしょうか。 マイミクの件に関するお二人の回答はとても参考になったのですが、今度は、ミクシーの「日記のコメント」のデータはどのように格納されているのかが気になりだしてしまいました。例えば、nikkicomment_id12_t、nikkicomment_id45_t のように、ユーザーごとにテーブルを分けたりしているでしょうか??それとも、一つのテーブルで事足りるのでしょうか。このコメントのデータを一つのテーブルで格納するとなると、相当データが多くなってしまう気がするのですが。。どちらなのでしょう。ご教授よろしくお願いします。

関連するQ&A

  • データ量が多すぎると、テーブルを分けたほうがいい?

    質問があるのですが、よろしくお願いします。 例えば、ミクシーで、日記機能がありますが、もしミクシーがMySQLを使っているとしたら、あの日記に書き込まれるコメントのデータはどのようにテーブルに格納されているのでしょうか?? 一つのテーブルで済まそうとするとデータがかなり膨大になって検索に時間がかかるのではないかと思うのです。 例えばid1番からid100番までの日記のコメントのデータは、nikki_comment_100_tというテーブル、id101番からid200番までの日記のコメントのデータはnikki_comment_200_tというテーブル、というように、いくつかに分割して格納してたりするのでしょうか?それとも、一つのテーブルで十分事足りるのでしょうか?? また、もし前者のように分割して分けているとしても、それは顧客が多くデータが膨大なミクシーのような大規模なサイトならではのことで、これから人を集めようとしている現段階では小規模なサイトのデータベースなら、わざわざテーブルを分割してデータを格納することはない・・・とかそんな感じなのでしょうか? どなたか分かる方いらっしゃいましたら、よろしくお願いします。

    • ベストアンサー
    • MySQL
  • 複数のテーブルからデータを取得したい

    1つのテーブルから重複したデータを取り除いて表示するときに使う 【select distinct カラム名 from テーブル名;】 がありますよね。 それと同じようなことを複数のテーブルをまたいで行いたいのですがうまくいきません。 ちなみに両方のテーブルのカラム名は同じです。 【select distinct カラム名 from テーブル1 union select distinct カラム名 from テーブル2;】 としても重複を取り除いた後にテーブルを結合してるので結果的に両テーブルの重複した値を取り除くことができず。 そこで 【select distinct T1.カラム名, T2.カラム名 from テーブル1 T1. テーブル2 T2;】 としてみたのですが、クエリを実行中のまま反応がないので悩んでます。 ちなみに2つのテーブルのデータはそれぞれ2万件ほどです。 こういう時どういうsql文を組むのが正しいのでしょうか?

    • ベストアンサー
    • MySQL
  • 2テーブルが同じユーザテーブル参照するときの結合

    2つのテーブルで、同じユーザテーブルを参照してデータ取得したいのですが、 どうやって結合すれば良いのでしょうか? ■概要 ・ユーザがアクションに挑戦すると、結果を表示 ・その際、「アクション作成者」と「アクション挑戦者(ユーザ)」を表示したい ※「作成者」「挑戦者」は、同じ「user」テーブルで管理したい ■3テーブル ・「result」「action」「user」 ・「result」「action」テーブルには、それぞれ「user_id」カラムがある ・「result」テーブルには、「action_id」カラムがある。1対多? ■知りたいこと ・一気にまとめて一覧として取得する方法 ・最終的に「結果」と、「result」「action」それぞれに対応した「user」テーブルの「name」カラムを取得したい ■試してみたこと ・これだと「挑戦者名」が取得できない       SELECT *        FROM result r         LEFT JOIN `action` a ON r.`action_id` = a.`id`         LEFT JOIN `user` u ON r.`user_id` = u.`id` ・これだと「挑戦者」のユーザIDしか取得できない       SELECT *,a.user_id AS actionuser_id        FROM result r         LEFT JOIN `action` a ON r.`action_id` = a.`id`         LEFT JOIN `user` u ON a.`user_id` = u.`id`

    • ベストアンサー
    • MySQL
  • 【MySQL】1対1でテーブルをあえて分ける

    mysqlを使用してデータベースを作成しているのですが データベースでテーブルを分けるときって 【アカウントテーブル】 ID アカウント 名 アカウント パスワード 名前 住所 電話番号 職業 【職業テーブル】 職業ID 職業名 というような1対多というのはよく組むとおもうんですが 下記のような 【アカウント情報テーブル(アカウント情報)】 アカウントID アカウント 名 アカウント パスワード 【アカウント情報テーブル(プロフィール情報)】 アカウントID 名前 住所 電話番号 職業 1対1の関係でテーブルをジャンル(エンティティ)ごとに複数にわけて あとでリレーションして一個にまとめるというのはデータベース的にあまりよろしくないのでしょうか? 何故、こんなことしたいかというと、1テーブルあたりのカラム数がかなり多くなってくると PHPでデータベースを書き込んだり呼び出したりする時に毎度多くのカラムを取り扱わなければならず SELECTで、カラムを一個一個選んで行かないといけません。 しかし、取り扱いたいカラムは大抵の場合あるジャンルだけなので リレーションするかしないかで、あるジャンルのデータだけを取り扱えれば 効率がよくなるのでは? というのがあります。 また、視覚的にカラムの把握もしやすくなります。 この1対1テーブルは、DB設計的にどうなでしょうか?

    • ベストアンサー
    • MySQL
  • テーブル設計について

    二つのテーブルの行数は同じとします 1行に10カラム以上あるテーブルから1カラムだけ取得するのと idとvoteだけの2カラムで作ったテーブルから1カラムだけ取得する場合の処理スピードは速くなりますか? updateで更新する時のスピードもカラム数が多いと違いが出ますか? よろしくお願いします sprintf("SELECT vote FROM hoge WHERE id=%d", $id );

    • ベストアンサー
    • MySQL
  • MySqlのテーブルをPHPで比較して呼び出す方法

    説明が下手でうまく伝わらないかもしれないのですが、やりたいことは画像と合わせ説明させて頂きます。 テーブル内のそれぞれのカラムを呼び出すなどはなんとか出来るようになったので、違うパターンを勉強しております。 例えばmixiのようなSNSに紹介するサイトがあると仮定します。 そこで「山田2号」でログインをした場合、紹介されたのは誰々です。 という風にしてみたいと思います。 画像では、 山田2号でログイン中 「紹介者は下記の人です」 会員番号「1005」山田5号 会員番号「1006」山田6号 会員番号「1007」山田7号 会員番号「1008」山田8号 ・マッチ方法は山田2号のカラムnoの1002とカラムsnoの1002が同じ時にカラムsnoのマッチしたカラムnameを全て表示する。 という感じなのかなとイメージしているのですが実際にやってみると全然うまくいきません。 違うテーブルで会員を呼び出すなどで行っているのは public function getUser($id) { $stmt = $this->pdo->prepare(implode(' ', array( 'SELECT *', 'FROM `user`', 'WHERE `id` = ?', 'LIMIT 1', ))); $stmt->bindValue(1, $id, PDO::PARAM_INT); $stmt->execute(); if (!$stmt->rowCount()) { throw e('該当するユーザーが見つかりません。'); } return $stmt->fetch(); } としています。 この紹介用のテーブル名がsuserだとするとテーブル名変更のほかに条件指定はどのようにするのでしょうか? 自分なりにWHEREで条件をつけlimitも切ってみたりしたのですがうまくいきませんでした。 上記のわかりにくい説明で恐縮なのですが、アドバイスやヒントをいただけませんでしょうか? マッチの方法などがそもそも違うのでしょうか? どうぞよろしくお願いいたします。

    • ベストアンサー
    • PHP
  • 重複カラムを持つ2テーブルの統合について

    ほとんど同じテーブル構成の以下のようなテーブルAとテーブルBがあります。 【テーブルA】 |カラム1|カラム2|カラム3| 【テーブルB】 |カラム1|カラム2|カラム3|カラム4|カラム5| テーブルAには数万件のデータが入っていて、テーブルBのデータは数百件程度です。 テーブルAを破棄して、全てテーブルBにまとめたほうが良いでしょうか? (ほとんどデータが入らない、|カラム4|カラム5|分のデータ量が無駄になる気がしているのですが・・)

    • ベストアンサー
    • MySQL
  • アクセスログテーブルの構造について

    このジャンルでお願いします。 よくアクセスログの解析を無料で(リンクを貼ったりして)行ってくれるサービスがありますが、 そのデータベースの構造というかテーブルの構造はどのようになっているのでしょうか? 例えば、膨大なレコード数になると思うので それを利用するユーザー毎にテーブルを分けるとかするのでしょうか? あるいはユーザー毎、年毎、月毎、日毎、に分けるとか? 本来ならテーブルを分割したりするのは違うんじゃないかなぁと思ったりするのですが、 なので次のように、 CREATE TABLE `accesslog` ( `id` int NOT NULL auto_increment, `user_id` varchar(16), `created` datetime, `ip` varchar(64), FOREIGN KEY(`user_id`) REFERENCES `user`(`id`) ); ユーザーも全ての期間のデータも1つのテーブルで管理するのが普通だとは思うのですが、 アクセスログだけは利用するユーザー数にもよりますがやはり膨大になりますよね? そうすると1つのテーブルだと無理があると思うのです。 あるいは単にテキストファイルとして保存する方法もあるのかな?と思うのですが、 やはりなにかとSQLで操作したいのでMySQLなどのテーブルの設計が知りたいです。

  • 同じテーブル内同士で更新したい

    MySQLバージョン4.1.16を使用しています。 同じテーブル内で、user_idが「aaaa」のnumカラム値を 「bbbb」のnumカラム値でupdateしたいのですが、 次のようなsqlだとエラーが出てしまいます・・・ なんとかしてできる方法はないでしょうか? $sql = "UPDATE users SET num = (SELECT num FROM users WHERE user_id = 'bbbb') WHERE user_id = 'aaaa'"; Error Number: 1093 You can't specify target table 'users' for update in FROM clause テーブル「users」 +----------+---------+ |  user_id  |  num  | +----------+---------+ |  aaaa   |   1   |←成功すれば2になる +----------+---------+ |  bbbb   |   2   | +----------+---------+

  • フォームから2つのテーブルにデータを書き込みたい

    Accessで T_aテーブルとT_bテーブルがありそれぞれのフィールドが以下のようになっているとします。 T_a:フィールド名 データ型    ID  オートナンバー型    商品番号 テキスト型 主キー T_b:フィールド名 データ型    ID  オートナンバー型 主キー    商品番号 テキスト型 このときフォームから入力したデータをそれぞれのテーブルの商品番号に追加したいのですがどのようにすればよいのでしょうか。  よろしくお願いいたします。