IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Administration SQL Server Discussion :

Besoin de deux colonnes autoincrémentées


Sujet :

Administration SQL Server

  1. #1
    Expert confirmé
    Avatar de Kropernic
    Homme Profil pro
    Analyste / Programmeur / DBA
    Inscrit en
    Juillet 2006
    Messages
    3 932
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Belgique

    Informations professionnelles :
    Activité : Analyste / Programmeur / DBA
    Secteur : Distribution

    Informations forums :
    Inscription : Juillet 2006
    Messages : 3 932
    Points : 4 239
    Points
    4 239
    Par défaut Besoin de deux colonnes autoincrémentées
    Hello,

    Je viens vous voir car je cherche une solution de contournement pour un problème qui n'en serait pas un si notre maison-mère consentait à migrer à la version suivante de sql server...

    Bref, dans une nouvelle DB, j'aurais bien voulu créer la table suivante :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    CREATE TABLE S_GM.T_CARD_CRD (
        CRD_ID    INT    IDENTITY(1,1) NOT NULL,
        EMP_ID    INT    NOT NULL,
        CRD_NUMBER    INT IDENTITY(1,1) NOT NULL,
        CRD_LOCKED BIT NOT NULL DEFAULT CAST(0 AS BIT),
        CONSTRAINT PK_T_CARD_CRD PRIMARY KEY CLUSTERED (
            CRD_ID
        ) WITH (FILLFACTOR = 80)
    );
    GO
    Évidemment, pas moyen vu qu'on ne peut avoir qu'une seule colonne IDENTITY par table (sinon, @@IDENTITY serait bien emmerdé pour nous retourner quelque chose ^^).
    Avec 2012+, il y a les séquences pour me dépanner. Mais ça n'existe pas encore chez moi (la migration est prévue cependant... faut juste que je trouve le temps de la faire...)

    Quelqu'un aurait-il une idée lumineuse pour contourner cette limitation "proprement" ?

    J'ai bien pensé à faire ceci mais j'ai l'impression que ça fait bricolage...
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    CREATE TABLE S_GM.T_CARD_CRD (
        CRD_ID    INT    IDENTITY(1,1) NOT NULL,
        EMP_ID    INT    NOT NULL,
        CRD_LOCKED BIT NOT NULL DEFAULT CAST(0 AS BIT),
        CONSTRAINT PK_T_CARD_CRD PRIMARY KEY CLUSTERED (
            CRD_ID
        ) WITH (FILLFACTOR = 80)
    );
    GO
     
    CREATE TABLE S_GM.T_CARD_NUMBER_CRN(
        CRD_ID    INT NOT NULL REFERENCES S_GM.T_CARD_CRD(CRD_ID),
        CRD_NUMBER INT IDENTITY(1,1) NOT NULL,
        CONSTRAINT PK_T_CARD_NUMBER_CRN PRIMARY KEY CLUSTERED(
            CRD_ID
        ) WITH (FILLFACTOR = 80)
    );
    GO
    Je pourrais aussi utiliser la colonne CRD_NUMBER comme clef primaire et carrément retirer la colonne CRD_ID mais je ne respecterais alors plus le principe de Tabourier (vous allez me dire, c'est un principe, pas une règle absolue...).

    Bref, quelle est la meilleure solution selon vous ? (ceux qui me diront de migrer vers une version 2012+ auront raison mais il me faut du temps )
    Kropernic

  2. #2
    Modérateur

    Homme Profil pro
    Administrateur de base de données
    Inscrit en
    Janvier 2005
    Messages
    5 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Administrateur de base de données
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2005
    Messages : 5 826
    Points : 12 371
    Points
    12 371
    Par défaut
    Bonjour,

    Au départ j'ai pensé à un trigger, et j'ai fait la grimace

    Ensuite, à une table pour simuler la SEQUENCE, mais cela peut s'avérer inefficace si la table supporte un grand nombre d'INSERT.
    Et puis ce n'est pas facile à gérer dans le code, car il est nécessaire de savoir combien de lignes on va insérer ...

    Ensuite j'ai pensé à une colonne calculée dont la formule serait AS(i) avec la table ci-dessous pour la colonne j, mais j'ai eu du rouge dans la console

    Je viens d'essayer en plaçant une contrainte de valuation par défaut à SCOPE_IDENTITY(), mais cela a des effets indésirables si l'on réalise plusieurs INSERT au sein de la même session.
    Par ailleurs la colonne doit être NULLable.

    Le test suivant peut-il convenir ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    USE ELSUKET
    GO
     
    CREATE FUNCTION dbo.f_zeSequence (@_i int)
    RETURNS int
    WITH SCHEMABINDING
    AS
    BEGIN
    	RETURN @_i
    END
    GO
     
    CREATE TABLE zeSequence
    (
    	i int NOT NULL IDENTITY(1,1)
    		CONSTRAINT PK_zeSequence PRIMARY KEY
    	, j AS (dbo.f_zeSequence(i)) PERSISTED NOT NULL
    	, c varchar(32) NOT NULL
    )
    GO
     
    INSERT INTO dbo.zeSequence (c) VALUES ('test'), ('zeSequence')
    GO 10
     
    SELECT *
    FROM dbo.zeSequence
    @++

  3. #3
    Expert confirmé
    Avatar de Kropernic
    Homme Profil pro
    Analyste / Programmeur / DBA
    Inscrit en
    Juillet 2006
    Messages
    3 932
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Belgique

    Informations professionnelles :
    Activité : Analyste / Programmeur / DBA
    Secteur : Distribution

    Informations forums :
    Inscription : Juillet 2006
    Messages : 3 932
    Points : 4 239
    Points
    4 239
    Par défaut
    Hello,

    Merci pour la suggestion (que j'analyserai dès que j'ai 10 minutes).

    Finalement, car il fallait bien que j'avance, je me suis débrouillé comme ceci :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    CREATE TABLE S_GM.T_CARD_CRD (
        CRD_ID    INT    IDENTITY(1,1) NOT NULL,
        EMP_ID    INT    NOT NULL,
        --CRD_NUMBER    INT IDENTITY(1,1) NOT NULL,
        CRD_LOCKED BIT NOT NULL DEFAULT CAST(0 AS BIT),
        CONSTRAINT PK_T_CARD_CRD PRIMARY KEY CLUSTERED (
            CRD_ID
        ) WITH (FILLFACTOR = 80)
    );
    GO
     
    CREATE TABLE S_GM.T_CARD_NUMBER_CRN(
        CRD_ID    INT NOT NULL REFERENCES S_GM.T_CARD_CRD(CRD_ID),
        CRD_NUMBER INT IDENTITY(1,1) NOT NULL,
        CONSTRAINT PK_T_CARD_NUMBER_CRN PRIMARY KEY CLUSTERED(
            CRD_ID
        ) WITH (FILLFACTOR = 80)
    );
    GO
     
    ALTER TABLE S_GM.T_CARD_NUMBER_CRN WITH CHECK ADD CONSTRAINT FK_CRN_TO_CRD FOREIGN KEY (CRD_ID) REFERENCES S_GM.T_CARD_CRD(CRD_ID);
    GO
    Je dois juste encore savoir quoi mettre comme numéro de départ pour le numéro de carte mais ça peut rester à 1 pour les tests de toute façon.
    Je pense que ça doit pouvoir faire le taff.

    Question annexe : Est-ce que je me fourvoie en pensant que je peux interdire l'update d'une colonne via un trigger ?
    Kropernic

  4. #4
    Expert éminent
    Avatar de StringBuilder
    Homme Profil pro
    Chef de projets
    Inscrit en
    Février 2010
    Messages
    4 154
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Chef de projets
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Février 2010
    Messages : 4 154
    Points : 7 403
    Points
    7 403
    Billets dans le blog
    1
    Par défaut
    Bonjour,

    Question à 1/4 de centime...

    A quoi sert cette seconde colonne IDENTITY ?

    Prendre par défaut la valeur de ID, et parfois, pouvoir en prendre une autre ?

    Pourquoi ne pas créer une seconde colonne NULLABLE, et créer une troisième colonne calculée retournant COALESCE(DEUXIEME_COLONNE, ID) ?
    On ne jouit bien que de ce qu’on partage.

  5. #5
    Expert confirmé
    Avatar de Kropernic
    Homme Profil pro
    Analyste / Programmeur / DBA
    Inscrit en
    Juillet 2006
    Messages
    3 932
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : Belgique

    Informations professionnelles :
    Activité : Analyste / Programmeur / DBA
    Secteur : Distribution

    Informations forums :
    Inscription : Juillet 2006
    Messages : 3 932
    Points : 4 239
    Points
    4 239
    Par défaut
    Cette DB va en fait servir à gérer des cartes de personnel.

    Le "souci", c'est qu'on ne démarre pas la numérotation à 0. C'est une refonte d'un ancien système (application en delphi6 avec db en Advantage Database Server).

    Je pourrais m'en passé en passant via une vue ou via une colonne calculée (je n'y avais pas pensé à celle-là) mais, je ne sais pas pourquoi, je craints la modif de la formule de calcul dans le script de la vue ou de la colonne calculée...

    Du coup, je pensais mettre cette seconde colonne en mettant la racine au numéro à partir duquel il faudra recommencer la numérotation mais au plus j'y pense, au plus je me dis que c'est complètement con... Je ne fais que déplacer le risque ailleurs... Va falloir que je trouve une "astuce", la bonne manière de faire.
    Kropernic

Discussions similaires

  1. [CR9] groupement en deux colonnes
    Par wargre dans le forum SAP Crystal Reports
    Réponses: 10
    Dernier message: 13/06/2006, 10h11
  2. Minimum entre deux colonnes
    Par keikun dans le forum Requêtes
    Réponses: 5
    Dernier message: 18/08/2005, 13h20
  3. zone de liste : affichage de deux colonnes
    Par niclalex dans le forum IHM
    Réponses: 3
    Dernier message: 27/10/2004, 22h51
  4. [CR] Faire un groupe sur deux colonnes, voir mon exemple
    Par Etienne51 dans le forum SAP Crystal Reports
    Réponses: 6
    Dernier message: 08/10/2004, 14h02
  5. Grep? besoin de la colonne d'une seq recherchee
    Par Marionnet' dans le forum Linux
    Réponses: 6
    Dernier message: 17/08/2004, 18h14

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo