Mysql
 sql >> Baza danych >  >> RDS >> Mysql

Błąd 1005 w MySQL (ze składni klucza obcego?)

Twoje błędy są spowodowane nieprawidłową składnią klucza obcego.

Jednak Myślę, że powinieneś używać pól identyfikatorów zamiast tworzyć złożone klucze główne ciągów . Jest kilka problemów z Twoją metodą...

  • Utrudni to DB łączenie tabel w porównaniu z użyciem pola liczb całkowitych (ID) do łączenia (trudniejsze ==dłuższy czas przetwarzania).

  • Prawidłowe jest posiadanie wielu osób o tym samym imieniu, nawet przy użyciu drugiego inicjału.

  • Co się stanie, jeśli będziesz musiał zmienić czyjeś imię? Albo dlatego, że był źle przechowywany, albo pobrali się, albo coś... Oznacza to, że będziesz musiał nie tylko zaktualizować swojego employee tabela, ale works table i dowolna inna tabela, której nazwa została użyta jako klucz obcy.

Spójrz na to:http://sqlfiddle.com/#! 2/2dc8c/3/0

Dodałem identyfikator stołu do każdego stołu . Jest to unsigned int , co oznacza, że ​​nie może być ujemna (ponieważ nie miałoby to większego sensu). Jest to również auto_increment , co oznacza, że ​​za każdym razem, gdy dodasz wiersz do tabeli, ten identyfikator zostanie wygenerowany automatycznie i wzrośnie o 1.

    create table Employee (
          Employee_ID int unsigned auto_increment primary key,

          Lastname    varchar(10),
          FirstName   varchar(10),
          MidInitial  char(1),

          gender      char(1),

          street      varchar(10),
          city        varchar(10),

          unique (Lastname, FirstName, MidInitial)
      );

Możesz dodać rzeczy do tej tabeli w ten sposób:

    insert into Employee (Employee_ID, LastName, FirstName, MidInitial) 
                   values (null,       'Smith',  'John',    'K');

null stanie się automatycznie wygenerowanym identyfikatorem. Będzie unikalny dla każdego rzędu.

Ponadto unikalne ograniczenie oznacza, że ​​kombinacja tych pól musi być unikalna w tabeli. Jednak przy wystarczająco dużej firmie założę się, że dwie osoby będą miały to samo nazwisko. W prawdziwym życiu sugerowałbym usunięcie tego unikalnego ograniczenia.

Wprowadziłem podobne zmiany w tabeli firmowej...

     create table company(
         company_ID      int unsigned auto_increment primary key,

         company_name    varchar(20),
         city            varchar(10),

         unique (company_name)
    );

Można dodać takie rzeczy jak:

     insert into company values (null, 'Taco Bell', 'Paris'); 

Więc... dla works ....zamiast w kółko zapisywać w tej tabeli pełne imię i nazwisko każdej osoby oraz pełną nazwę firmy, teraz musimy tylko przechowywać identyfikatory.

    create table Works (
         works_id      int unsigned auto_increment primary key,

         employee_id   int unsigned, 
         compay_id     int unsigned,  

         salary        numeric(8,2), 

         foreign key (employee_id) references Employee (employee_id), 
         foreign key (compay_id) references company (company_id) 
    );

Możesz dodawać rzeczy do works tak:

    insert into Works values (null, 1, 1, '10.00');

Ponieważ John Smith był naszym pierwszym pracownikiem, jego Employee_ID będzie wynosić 1. Aby to sprawdzić, po prostu spróbuj select * from Employee where FirstName='John' and LastName='Smith' . Taco Bell również otrzyma company_id =1. Wstawiając te wartości do works , oznacza to, że John pracuje teraz w Taco Bell.

Proponuję również dodać pola, takie jak start_date i end_date i job_title do twojego stołu roboczego. I chciałbyś zwrócić szczególną uwagę na wszelkie unikalne ograniczenia dla tej tabeli. Ludzie mogą pracować w tej samej firmie więcej niż raz. Mogą też wykonywać różne prace.

Jeśli chcesz odzyskać swoje dane, użyj takiego zapytania:

  select FirstName, MidInitial, LastName, 
         Company_Name, 
         Salary 

  from   employee

         join works 
           on works.employee_id = employee.employee_id

         join company 
           on works.company_id = company.company_id 

co jest tylko wymyślnym sposobem powiedzenia tego:

  select FirstName, MidInitial, LastName, 
         Company_Name, 
         Salary 

  from   employee, works, company

  where  employee.employee_id = works.employee_id and

         company.company_id = works.company_id  

Niektóre uwagi dotyczące bazy danych...

  • Wybierz konwencję nazewnictwa i trzymaj się jej! Jeśli chcesz użyć CamelCase , używaj go wszędzie. Jeśli you_want_to_use podkreśla w swoich imionach, używaj ich wszędzie. Istnieje mnóstwo konwencji nazewnictwa do wyboru:poprzedzenie atrybutów (kolumny/pola) nazwą tabeli, używanie popularnych skrótów (lub nie), gdzie używa się wielkich liter (lub nie)… to głównie sprowadza się do osobistych preferencji, ale tam są tam artykuły o zaletach i wadach korzystania z niektórych z nich. Ostatnia uwaga, _tylko dlatego, że możesz użyć spacji w nazwie__, nie oznacza, że ​​powinieneś. `Almost all` bazy danych pozwalają [you use spaces] w nazwach, jeśli chcesz, ale później może to spowodować wiele problemów.

  • Nazwy tabel nie powinny być w liczbie mnogiej. To jest moje zirytowanie i oto dlaczego:Wiemy, że stół będzie zawierał wiele rekordów... wiele osób/osób, wielu pracowników, wiele firm, wiele wpisów dowolnego typu lub rodzaju. Każdy wiersz opisuje tylko jeden tych rzeczy. Czasami po prostu nie ma sensu, aby imię było w liczbie mnogiej. Innym razem jest to wątpliwe - jak works stół. Jeśli czasami robisz to w liczbie mnogiej, a czasami w liczbie pojedynczej, później może to być mylące. Po prostu czyniąc wszystko w liczbie pojedynczej, nadal ma to sens i nie przełączasz się tam iz powrotem ani nie musisz wyszukiwać dokładnej nazwy podczas pisania zapytań.

  • Typy danych są ważne i staraj się być spójnym w różnych tabelach dla podobnych pól (jak wszystkie id s ten sam typ; zrób wszystkie pola logiczne jako bity lub liczby całkowite lub cokolwiek innego, po prostu zrób je takimi samymi). Do wyboru są różne rozmiary typów liczb całkowitych. Pomyśl o rozmiarze, wydajności i tym, co jest odpowiednie dla Twoich potrzeb. Zdecyduj, czy naprawdę potrzebujesz nvarchar, czy też varchar jest w porządku.

    • Daty nie powinny nigdy być przechowywane jako ciąg. Użyj odpowiedniej daty, daty i godziny, godziny lub typu danych sygnatury czasowej . Pomoże ci to znacznie później, gdy będziesz musiał je odzyskać, porównać lub użyć w obliczeniach. Kolejną ważną decyzją jest sposób obsługi stref czasowych . Lubię przechowywać wszystko w UTC i obsługiwać wszelkie przesunięcia strefy czasowej w interfejsie użytkownika, gdy informacje są prezentowane użytkownikowi. Dzięki temu wszystko jest spójne i nie muszę się martwić, czy wiersz został wstawiony o godzinie 18:00 na podstawie czasu komputera mojego użytkownika, czasu przeglądarki użytkownika, czasu mojej bazy danych lub czasu serwera.

  • Dołącz ID pole to jest unikalne dla rzędu w każdej tabeli. Najprostszym sposobem na to jest użycie auto_increment (mysql) lub identity(1,1) (serwer sql), aby baza danych śledziła je dla Ciebie. Te wartości można zresetować lub ponownie umieścić w razie potrzeby.

  • Naucz się używać normalizacji .

  • Dowiedz się, jakie transakcje zrobić i dlaczego są ważne... nawet jeśli ich nie używasz.

  • Dowiedz się o różnych rodzajach złączeń . To jedno z najlepszych wyjaśnień jakie kiedykolwiek widziałem. Najważniejszą rzeczą, na którą należy zwrócić uwagę, jest to, czy sprzężenie powinno być sprzężeniem zewnętrznym, czy wewnętrznym.

  • Dowiedz się więcej o Wstrzykiwaniu SQL i co ważniejsze, jak aby temu zapobiec (ten link dotyczy PHP).

  • Jeśli używasz PHP, nie używaj starego mysql_ klasa. Zamiast tego użyj PDO lub MySQLi_ . Informacje...

  • Wielką zaletą baz danych jest integralność danych, walidacja i sanityzacja . Użytkownicy będą chcieli umieszczać w tabelach wszelkiego rodzaju niechlujne, brudne dane. Czy to MO czy Missouri? Kobieta, F, kobieta, dziewczyna, czy tak? Czy pensja 15,00 za godzinę, 50 tys. rocznie czy 3 tys. to wypłata? Czy to 31.12.2013, 31.12.2013, 31.12.2013, 31.12.2013 czy trzydziesty piąty dwa tysiące trzynasty?

  • Zdecyduj, czy chcesz zezwolić na NULL albo nie. To komplikuje sprawę z powodu trójstanowej logiki i będziesz musiał to sprawdzić później. Niektórzy decydują się na użycie zamiast tego pustego ciągu. NULL jest bardziej stanem niż rzeczywistą wartością i oznacza nieokreśloną lub nieznaną - wartość może być dowolna. używam null ponieważ pusty ciąg jest czasami prawidłową wartością pola. Na przykład ustawienie Middle_Initial równanie pustego ciągu może oznaczać, że osoba nie ma środkowego inicjału lub po prostu nie wiesz, co to jest. Dla mnie te rzeczy są inne. Dla innych różnica nie ma znaczenia. Pomyśl tylko o liczbach... czy 0 to samo nieznane?

  • Jeśli nic więcej, po prostu bądź konsekwentny.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Sumowanie kolumny oddzielonej przecinkami w MySQL 4 (nie 5)

  2. Podczas odczytu danych wystąpił błąd krytyczny

  3. Zapytanie SQL wybierające z użyciem złączeń, grupowania i funkcji agregujących

  4. Przechowywanie bardzo dużych liczb całkowitych w MySQL

  5. Symfony nie obsługuje jednoczesnych żądań