0

vs2012 で c-interface を使用して SQLite を実装しています。

3 つのテーブルがあり、そのうちの 2 つは親であり、キーによってリンクされていません。3 番目は子で、2 つの親テーブルからの 2 つの外部キーを持つ必要があります。次のことを試しましたが、次のエラーが表示されて機能しません。

foreign key contraints failed

ここに私の実装があります: 最初の親テーブル:

CREATE TABLE Persons (
    ID   INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
    Name CHAR                              NULL    ,
    Age  INT                               NULL
);

2 番目の親テーブル:

CREATE TABLE Jobs (
    Job_ID      INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
    Description CHAR                              NULL    ,
    Country     CHAR
);

子テーブル

CREATE TABLE Persons_Jobs (
    Title   CHAR NULL,
    country CHAR NULL,
    ID      INT      ,
    Job_ID  INT      ,
    FOREIGN KEY (ID)     REFERENCES Persons(ID) ,
    FOREIGN KEY (Job_ID) REFERENCES Jobs(Job_ID)
);

テーブルが正常に作成され、最初の 2 つのテーブルのデータも正常に挿入されていることに注意してください。


更新 2:

挿入ステートメント:

void db_prepareInsertSql(sqlite3 *db){
    sqlite3_int64 rowPersonID,rowJobID;
    int i =0;
    char *sql;
    char str[100];  

    do{
        i = i+1;
        sprintf_s(str, "INSERT INTO Persons VALUES(NULL,'liena',%d);",i);
        sql = str;
        db_execute_sql(db,sql);
        fprintf(stdout,"Persons insertion");
        rowPersonID = sqlite3_last_insert_rowid(db);

        sprintf_s(str, "INSERT INTO Jobs VALUES(NULL,'Doc','SDN');");
        sql = str;
        db_execute_sql(db,sql);
        fprintf(stdout,"Jobs insertion");
        rowJobID = sqlite3_last_insert_rowid(db);

\\the error occurs here
        sprintf_s(str, "INSERT INTO Persons_Jobs VALUES('A','krt',%d,%d);",rowPersonID,rowJobID);
        sql = str;
        db_execute_sql(db,sql);
        fprintf(stdout,"Persons_Jobs insertion");
    }
    while(i!=10);
}

テーブルの作成:

void db_prepareCreateTablesSql(sqlite3 *db){    
    char *sql;
    char str[500];

    sprintf_s(str, "PRAGMA foreign_keys = ON;");
    sql = str;
    db_execute_sql(db,sql); 
    fprintf(stdout,"Enable foriegn-keys feature");

    sprintf_s(str, "CREATE TABLE IF NOT EXISTS Persons("  
         "ID            INTEGER     PRIMARY KEY  AUTOINCREMENT  NOT NULL,   " 
         "Name          CHAR                                    NULL    ,   "
         "Age           INT                                     NULL    );  ");
    sql = str;
    db_execute_sql(db,sql);
    fprintf(stdout,"table Persons");

    sprintf_s(str, "CREATE TABLE IF NOT EXISTS Jobs(" 
         "Job_ID        INTEGER     PRIMARY KEY  AUTOINCREMENT  NOT NULL,   " 
         "Description   CHAR                                    NULL    ,   " 
         "Country       CHAR                                            )");         
    sql = str;
    db_execute_sql(db,sql); 
    fprintf(stdout,"table Jobs");

    sprintf_s(str, "CREATE TABLE IF NOT EXISTS Persons_Jobs("  
         "Title         CHAR                                    NULL    ,   " 
         "country       CHAR                                    NULL    ,   " 
         "ID            INT                                             ,   "
         "Job_ID        INT                                             ,   "        
         "FOREIGN KEY   (ID)        REFERENCES      Persons(ID),"        
         "FOREIGN KEY   (Job_ID)    REFERENCES      Jobs(Job_ID))       ;");
    sql = str;
    db_execute_sql(db,sql); 
    fprintf(stdout,"table Persons_Jobs");

    db_prepareInsertSql(db);
}

デバッグすると、これが見つかりました: ここに画像の説明を入力

だから、私の問題は子テーブルにあります.2つの異なる親テーブルから2つの外部キーを指定するにはどうすればよいですか?

4

2 に答える 2

3

2 つのテーブル (PersonsおよびJobs) への 2 つの挿入により、2 つの異なる自動インクリメント値が生成される場合があります。したがって、(疑似コード)で両方をキャッチする必要があります。

INSERT INTO Persons VALUES(NULL,'liena',1);       // 1st table
rowPersonID = sqlite3_last_insert_rowid(db)       // catch PersonID

INSERT INTO Jobs VALUES(NULL,'Doc','SDN'); // 2nd table
rowJobID = sqlite3_last_insert_rowid(db)       // catch JobID

その後:

INSERT INTO Career VALUES('A','krt',%d,%d)",rowPersonID,rowJobID; 
于 2013-09-02T11:38:05.420 に答える
1

問題は次の行にあります。

 sprintf_s(str, "INSERT INTO Persons_Jobs VALUES('A','krt',%d,%d);",rowPersonID,rowJobID);

rowPersonIDとのタイプrowJobIDは次のsqlite3_int64とおりです。

sqlite3_int64 rowPersonID,rowJobID;

これは 64 ビット型%dですが、整数の 32 ビットが必要です。整数にキャストするか、I64d64 ビット数値をフォーマットするために使用する必要があります。

sprintf_s(str, "INSERT INTO Persons_Jobs VALUES('A','krt',%I64d,%I64d);", rowPersonID,rowJobID);
于 2013-09-02T14:06:46.387 に答える