Mysql:标记从转储表中插入的行

问题描述 投票:2回答:2

我有一个转储表,由大量数据插入填充,我想通过分类将它们隔离在其他表上。

这是我的转储表,其中包含从文本文件中提取的数据。

==========================DUMP===============================
| Employee Name | Company | Family Tree Name | Relationship |
=============================================================
| Bryan Fury    | Guugle  | Jenny Fury       | Wife         |
|               |         | Peter Fury       | Son          |
|               |         | Mary Fury        | Daughter     |
| Paul Pheonix  | Soony   | Linda Phoenix    | Wife         |
|               |         | Peter Phoenix    | Son          |
|               |         | John Phoenix     | Son          |
| Gwen Zamora   | Aple    | Sebastian Zamora | Husband      |
|               |         | Ryan Zamora      | Son          |
=============================================================

我想将它们分成两个带有这种标识符的表

================EMPLOYEE===============
| Employee Name | Company |  Tagging  |
=======================================
| Bryan Fury    | Guugle  | Family 1  |
| Paul Pheonix  | Soony   | Family 2  |
| Gwen Zamora   | Aple    | Family 3  |
=======================================

==============FAMILY TREE===================
| Name            | Relationship|  Tagging  |
============================================
| Jenny Fury      | Wife        | Family 1  |
| Peter Fury      | Son         | Family 1  |
| Mary Fury       | Daughter    | Family 1  |
| Linda Phoenix   | Wife        | Family 2  |
| Peter Phoenix   | Son         | Family 2  |
| John Phoenix    | Son         | Family 2  |
| Sebastian Zamora| Husband     | Family 3  |
| Ryan Zamora     | Son         | Family 3  |
============================================
mysql sql database database-design
2个回答
0
投票

假设您的转储表有一个可用于在其插入顺序中获取记录的列,这是一种方法:

try
{
  $conn = new PDO("mysql:host=".DATABASE_HOST.";dbname=".DATABASE_NAME.";charset=UTF8", DATABASE_USER, DATABASE_PASS);
  $conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
}
catch(PDOException $e)
{
  trigger_error("Can not connect to database: ".$e->getMessage(), E_USER_ERROR);
  die;
}

$stm_employee = $conn->prepare('INSERT INTO employee(employee_name, company) VALUES(:emp, :comp)');
$stm_tree = $conn->prepare('INSERT INTO family_tree(name, relationship, tagging) VALUES(:name, :relation, :tag)');

$res = $conn->query('SELECT employee_name, company, family_tree, relationship FROM dump ORDER BY id');
$old_employee = '';
$old_tag = 0;
while($row = $res->fetch(PDO::FETCH_ASSOC))
{
  if($row['employee_name'] != $old_employee)
  {
    $stm_employee->execute(array(
      'emp' => $row['employee_name'],
      'comp' => $row['company']
    ));
    $old_tag = $conn->lastInsertId();
    $old_employee = $row['employee_name'];
    $stm_tree->execute(array(
      'name' => $row['family_tree'],
      'relation' => $row['relationship'],
      'tag' => $old_tag
    ));
  }
  else
  {
    $stm_tree->execute(array(
      'name' => $row['family_tree'],
      'relation' => $row['relationship'],
      'tag' => $old_tag
    ));
  }
}
$conn->query('TRUNCATE TABLE dump');

0
投票

经典的“规范化”。

假设这些是所需的两个表:

CREATE TABLE Employee (
    family_id INT UNSIGNED AUTO_INCREMENT,
    name ...,
    company ...,
    PRIMARY KEY(id)
) ENGINE=InnoDB;

CREATE TABLE FamilyTree (
    id INT UNSIGNED AUTO_INCREMENT,
    family_id INT UNSIGNED,
    name ...,
    relationship ...,
    PRIMARY KEY(id)
) ENGINE=InnoDB;

这是填充它们的SQL:

-- Create ids for each "family" (`id` will be automatically set):
INSERT INTO Employee (name, company)
    SELECT DISTINCT employee_name, company
        FROM Dump;

-- Build the other table:
INSERT INTO FamilyTree (name, relationship, family_id)
    SELECT d.family_tree_name, d.relationship,
           e.family_id
        FROM Employee AS e
        JOIN Dump AS d  ON d.employee_name = e.name
                       AND d.company = e.company;

这样可以减少输入,并且是使用SQL的一个很好的教训,而不是在编程语言中繁琐地编写类似SQL的操作。

如果存在裙带关系,你就会遇到问题。

© www.soinside.com 2019 - 2024. All rights reserved.