2014-04-11 12 views
0

학생이 MySQL 데이터베이스에서 가지고있는 모든 강좌를 가져 오려고합니다. 이 스 니펫은 1 코스 만 가져 오지만 총 6 개가 있습니다 (그리고 나서 15 초 걸립니다). option 태그의 selected 속성을 사용하여 이미 설정된 코스를 표시하려고합니다. 나는 이것이 쿼리가 오랫동안 실행되도록하는 원인이라고 생각한다.
내 데이터베이스 디자인에 문제가 있습니까? 쿼리를 어떻게 개선합니까?쿼리를 실행하는 데 너무 많은 시간이 걸립니다.

이것은 데이터베이스의 구조입니다. 나는 중간 테이블을 생성 user_courses :

사용자 :
USER_ID

users_courses :
USER_ID
course_id_1
course_id_2
course_id_3
course_id_4
course_id_5 01 23, course_id_6
course_id_7

과정 :
제프

CREATE INDEX _index_course ON courses(course_id); 
CREATE INDEX _index_user_course ON users_courses(course_id_1); 
+2

색인이 무엇입니까? –

+0

이 스 니펫에는 아무 것도 없습니다. –

+0

프로파일 링을 몇 번하면 연결에 얼마나 많은 시간이 걸리는지 알 수 있습니다. – pomaxa

답변

5

당신은이 언급 한,

<?php 
    session_start(); 
    $_SESSION['user_id'] = 1; 
    require ('../mysqli_connect.php'); 

    echo '<table><tr><td><select name="course_id_1">'; 

    // checking if a user has already chosen a 1st course (out of 6) 
    $query = "SELECT c.course_id 
       FROM courses AS c 
       INNER JOIN users_courses AS u 
       ON c.course_id = u.course_id_1 
       WHERE u.user_id = {$_SESSION['user_id']}"; 
    $result = mysqli_query($dbc, $query); 

    // if yes, assign the selected course from the database to a variable 
    if (mysqli_num_rows($result) == 1) { 
     $row = mysqli_fetch_array($result, MYSQLI_ASSOC); 
     $selected_course = $row['course_id']; 
    } 

    // fetch courses, and make 'None' the first option in the drop down menu 
    $query = "SELECT course_id, course_name 
       FROM courses 
       ORDER BY (course_name = 'None') DESC, course_name"; 
    $result = mysqli_query($dbc, $query); 

    // create the drop down menu 
    while ($row = mysqli_fetch_array($result, MYSQLI_ASSOC)) { 
     // select default value 
     if ($selected_course == $row['course_id']) { 
      $selected =' selected'; 
     } else { 
      $selected=''; 
     } 

     echo '<option value="' . $row['course_id'] . '"' . $selected . '>' 
       . htmlspecialchars($row['course_name']) . '</option>'; 
    } 

    echo '</select></td></tr>'; 

    mysqli_free_result($result); 
    mysqli_close($dbc); 
?> 
+0

SQL 주입 공격이 왜 열려 있습니까? 텍스트 데이터를 입력하지 않습니다. –

+0

당신은 ('$ _SESSION' 변수로부터) 사용자가 여러분에게 가져다 준 물건을 가져 와서 데이터베이스 서버로 직접 전달합니다. @Palpatim에서 제공 한 링크를 읽으십시오. – Kryten

1

이이 인덱스를 생성 ... 이것을 시도
COURSE_NAME을 Course_ID에 여기 문제의 수.

1) 테이블 구조에 대한 설명으로 누락 된 인덱스 또는 기본 키로 설정 한 것과 같은 몇 가지 공통적 인 문제를 진단하기에 충분하지 않습니다. 이러한 선택은 성능에 큰 영향을 줄 수 있습니다.

2) 귀하의 users_courses 테이블이 비정규 화됩니다. 다 대다 관계를 모델링하는 더 일반적인 f}은 조인 된 각 테이블에 대해 하나의 외부 키가있는 테이블을 갖는 것입니다. 이 경우, 테이블과 같을 것이다 :

USERS_COURSES 
------------- 
user_id 
course_id 

그리고 7 개 코스 사용자는 해당 테이블의 7 개 레코드가있는 것입니다. "첫 번째 선택"과 같은 우선 순위를 알기 위해 실제로 모델에서 중요한 경우 조인 테이블을 적절한 열로 확장 할 수 있습니다.

3) 귀하의 PHP 코드는 SQL injection attacks에 대해 열려 있습니다. 사용자 입력을 직접 쿼리에 삽입하기 때문입니다. 문제를 해결하고 항상 바인드 변수를 사용하는 연습을 채택해야합니다.

관련 문제