2009-09-01 2 views
0

У меня 3 стола.Как обновить реляционную таблицу?

пользователей (идентификатор, почта, имя пользователя, и т.д ..)

Practices (номер, имя)

UsersPractices (идентификатор пользователя, practiceId)

Последняя является реляционная таблица, которая является пп ,

Я хотел бы обновить этот вариант, в зависимости от желания пользователя.

Это означает, что он может захотеть добавить или удалить некоторые свои действия.

Какой алгоритм я могу использовать для этого?

Должно ли быть лучше, чтобы эта работа (если есть способ) к движку базы данных? Или я должен написать свой собственный алгоритм для обработки данных, а затем выполнить мои запросы к db?

EDIT:

Чтобы было ясно:

___________________________ 
| UserId | PracticeId | 
|-----------|-------------| 
| 12  |  21  | 
|-----------|-------------| 
| 12  |  18  | 
|-----------|-------------| 

Может быть, пользователь попытается изменить свою практику с 21 до 15, но хочет сохранить такую ​​практику 18.

Так , из запроса я получу методы = array (15,18);

, что означает, что практика пользователей будет выглядеть следующим образом:

___________________________ 
| UserId | PracticeId | 
|-----------|-------------| 
| 12  |  15  | 
|-----------|-------------| 
| 12  |  18  | 
|-----------|-------------| 

SO, что является лучшим способом для достижения этой цели?

Должен ли я выбрать & проверить каждую практику, а затем удалить, если необходимо?

Удалите их все и добавьте новости.

+0

Я не совсем уверен, что вы здесь спрашиваете? – Amber

ответ

2

Предполагая, что у вас есть таблицы InnoDB, сделайте это как транзакцию.

Основная идея здесь состоит в том, чтобы стереть шифер, а затем создать/воссоздать ассоциации. Это проще, чем определение дельта каждого обновления (то есть проверка каждой строки по отдельности и определение того, является ли это действием INSERT, UPDATE или DELETE).

Вот исходный SQL вы должны использовать

BEGIN; 

DELETE FROM UsersPractices 
WHERE userId = [User ID]; 

INSERT INTO UsersPractices (
     userId 
    , practiceId) 
VALUES ([User ID], [Practice ID 1]) 
    , ([User ID], [Practice ID 2]) 
    ... 
    , ([User ID], [Practice ID N]); 

COMMIT; 
+0

Это то, что я предположил, кроме сделки, которая действительно может быть интересна здесь. –

+0

Сделка важна для работы этого шаблона. Он превращает этот многоступенчатый процесс в атомную единицу - если одна часть терпит неудачу, вся транзакция терпит неудачу, что препятствует необратимому уничтожению чей-то адата. Но вы не можете делать это с помощью таблиц MyISAM. –

1

Ознакомиться с Доктриной (http://www.doctrine-project.org/). Это структура реляционного сопоставления объектов (ORM) для PHP. Он может легко справиться с тем, что вы хотите выполнить.

+0

Я не использую Доктрину, но Zend Framework, которая имеет другое имплантование. –

+1

Вам не нужно использовать компонент Zend_Db_Table. Вы можете использовать Doctrine, даже в приложении Zend Framework. –

+0

Doctrine * должен * хорошо играть с ZF, если вы попытаетесь добавить его в свой проект. Из того, что я знаю, ZF не хватает ORM. Таким образом, вы можете либо бросить свое решение, либо пойти с заранее подготовленным. Вот статья о том, как совместить два: http://ruben.savanne.be/articles/integrating-zend-framework-and-doctrine –

0

Ну - самый простой способ я мог придумать, чтобы справиться с такого рода вещи было бы построить <select> элемент что-то вроде этого:

function getUserPractices($userId) { 
    $data = array(); 
    $result = mysql_query("SELECT Practices.* FROM UsersPractices LEFT JOIN Practices on UsersPractices.practiceId = Practices.id WHERE userId = '".mysql_real_escape($userId)."'"); 
    while ($row = mysql_fetch_array($result)) { 
    $data[$row['id']] = $row['name']; 
    } 
    return $data; 
} 

// assuming $user is your user row... 
$user_practices = getUserPractices($user['id']); 
$result = mysql_query("SELECT * FROM Practices ORDER BY name"); 
echo "<select multiple='multiple' name='practices[]'>"; 
while ($row = mysql_fetch_assoc($result)) { 
    echo "<option value='".$row['id']."'"; 
    if (isset($user_practices[$row["id"]])) echo " selected='selected'"; 
    echo ">".htmlentities($row['name'])."</option>"; 
} 
echo "</select>"; 

// This should result in an array $_POST['practices'] that contains practiceId's 
// will come back to write more about actually inserting the change into the db 
// but simplest way is to delete all of them based on userId then insert the new ones 
1

Если вы выполняете операторы SQL напрямую с помощью адаптера Zend_Db, вы можете создать запрос UPDATE на основе выбора, который пользователь хочет сделать.Например:

$db->query('UPDATE UsersPractices 
    SET practiceId = 
     CASE practiceId 
     WHEN 21 THEN 15 
     ELSE practiceId 
     END 
    WHERE userId = ?', 
    array($userId)); 

Это изменит practiceId до 15 только на строке, где находится practiceId 21. В других строках, это не имело бы никаких изменений в practiceId колонке.

+0

Это интересно, но похоже, что с ним будет сложно справиться, потому что мне нужно сделать выбор, получить существующие методы, а затем, используя ваш запрос, обновить и проверить. В любом случае, это может быть полезно в ближайшем будущем. –

+0

Вам нужно сделать выбор, чтобы получать текущие данные независимо от того, какое решение вы используете. –

Смежные вопросы