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

MS SQL Server Discussion :

hasard sql server


Sujet :

MS SQL Server

  1. #1
    Membre habitué
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    745
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 745
    Points : 166
    Points
    166
    Par défaut hasard sql server
    Bonjour,

    Je vais essayer d'expliquer clairement ce dont j'ai besoin...

    Donc j'ai des annonceurs qui postent des annonces. Certains doivent avoir leurs annonces mises en valeur, je dois donc aller cherche de manière aléatoire les annonces de ces annonceurs. Et quand je dis de manière aléatoire, c'est autant les annonceurs que leurs annones.... Suis je clair?

    Donc j'ai une table annonceurs (annonceur_id, Nom, prenom, raisonsociales) et une table annonces (annonce_id, annonceur_id, descriptif, prix, misenvaleur(booléen))

    Donc je dois aller chercher 5 annonces avec, et c'est la que ca se complique un peu plus... s'il y a 5 annonceurs, une annonce de chaque, si 4 annonceurs, vérifier une annonce pour 3 annonceurs, 2 pour un etc, etc....

    Car encore un problème je dois toujours avoir 5 annonces.

    Voilà j'avoue petit problème de logique et conception , si vous aviez l'obligeance de m'aider je vous en serait très reconnaissant.

  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,

    Je n'ai pas compris pourquoi vous avez mis une colonne misEnValeur dans votre table Annonces (même si cela doit être le cas) et pas dans Annonceurs, ce qui vous aurait permis de trouver facilement lesquels le sont.
    D'autant que si à tout moment vous devez avoir au plus 5 annonceurs prioritaires, cela vous permet d'implémenter une contrainte de type CHECK pour vérifier que vous en avez au plus 5.

    En ce qui concerne l'ordre aléatoire, vous pouvez vous servir de la fonction NEWID().
    En effet, si nous exécutons plusieurs fois :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    WITH
    	CTE AS
    	(
    			SELECT 1 AS n
    		UNION
    			SELECT 2
    		UNION
    			SELECT 3
    	)
    SELECT n
    FROM CTE
    Nous obtenons toujours les chiffres dans le même ordre : 1, 2, 3.

    Si en revanche nous exécutons, toujours plusieurs fois:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    WITH
    	CTE AS
    	(
    			SELECT 1 AS n
    		UNION
    			SELECT 2
    		UNION
    			SELECT 3
    	)
    SELECT n
    FROM CTE
    ORDER BY NEWID()
    Nous n'obtenons pas les chiffres tout le temps dans le même ordre.

    Je vous propose la procédure stockée suivante, qui fonctionnera dès SQL Server 2005 :

    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
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    CREATE PROCEDURE PsGetAnnonces
    AS
    BEGIN
    	SET NOCOUNT ON
     
    	-- Recherche le nombre d'annonceurs prioritaires
    	DECLARE @nbAnnonceursPrioritaires TINYINT
     
    	SELECT @nbAnnonceursPrioritaires = COUNT(DISTINCT annonceur_id)
    	FROM dbo.Annonces
    	WHERE misenvaleur = 1
     
    	-- S'il y a 5 annonceurs prioritaires, on tire au "hasard" 5 annonces de ces annonceurs
    	IF @nbAnnonceursPrioritaires = 5
    	BEGIN
    		WITH
    			CTE_ANNONCEURS_PRIORITAIRES AS
    			(
    				SELECT DISTINCT annonceur_id
    				FROM dbo.Annonces
    				WHERE misenvaleur = 1
    			)
    		SELECT TOP 5 annonce_id, descriptif, prix
    		FROM dbo.Annonces AS A
    		JOIN AS CTE_ANNONCEURS_PRIORITAIRES AS C
    			ON C.annonceur_id = A.annonceur_id
    		ORDER BY NEWID()
    	END
    	ELSE -- il y a moins de 5 annonceurs prioritaires
    	BEGIN
    		WITH
    			-- Recherche les annonceurs prioritaires
    			CTE_ANNONCEURS_PRIORITAIRES AS
    			(
    				SELECT DISTINCT annonceur_id
    				FROM dbo.Annonces
    				WHERE misEnValeur = 1
    			),
    			-- Recherche les annonceurs non prioritaires
    			CTE_ANNONCEURS_NON_PRIORITAIRES AS
    			(
    					SELECT annonceur_id
    					FROM dbo.Annonceurs
    				EXCEPT
    					SELECT annonceur_id
    					FROM CTE_ANNONCEURS_PRIORITAIRES
    			),
    			-- Extrait les annonces des annonceurs prioritaires
    			CTE_ANNONCES_PRIORITAIRES AS
    			(
    				SELECT TOP (@nbAnnonceursPrioritaires) annonce_id,
    														descriptif,
    														prix,
    														ROW_NUMBER() OVER(ORDER BY NEWID())
    				FROM dbo.Annonces AS A
    				JOIN AS CTE_ANNONCEURS_PRIORITAIRES AS C
    					ON C.annonceur_id = A.annonceur_id
    			),
    			-- Extrait les annonces des annonceurs non prioritaires
    			CTE_ANNONCES_NON_PRIORITAIRES
    			(
    				SELECT TOP (5 - @nbAnnonceursPrioritaires) annonce_id,
    															descriptif,
    															prix,
    															ROW_NUMBER() OVER(ORDER BY NEWID())
    				FROM dbo.Annonces AS A
    				JOIN CTE_ANNONCEURS_NON_PRIORITAIRES AS NP
    					ON A.annonceur_id = NP.annonceur_id
    			)
    			SELECT annonce_id, descriptif, prix
    			FROM CTE_ANNONCES_PRIORITAIRES
    		UNION
    			SELECT annonce_id, descriptif, prix
    			FROM CTE_ANNONCES_NON_PRIORITAIRES			
    	END
    END
    On ne peut pas utiliser la clause ORDER BY combinée à tout opérateur ensembliste (UNION ici, mais aussi INTERSECT et EXCEPT), ni dans les vues et expressions de tables communes, comme ici.
    J'ai donc contourné le problème en me servant de la fonction ROW_NUMBER() qui permet d'introduire un ordre avec sa clause ORDER BY.

    Vous pouvez utiliser la clause TOP combinée à une variable si celle-ci est spécifiée entre parenthèses.

    @++

  3. #3
    Membre habitué
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    745
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 745
    Points : 166
    Points
    166
    Par défaut
    Car ce ne sont pas toutes les annonces de l'annonceur que l'on veut mettre en valeur, mais certaines annonces ponctuellement.

    Merci pour cette réponse étoffée et très complète, je vais tester tout cela et je te tiens au courant!

    Merci beaucoup !!

    Alex

Discussions similaires

  1. Pb migration Access / SQL server
    Par yoyo dans le forum MS SQL Server
    Réponses: 10
    Dernier message: 25/04/2005, 10h39
  2. Quel outil choisir pour un développement SQL-Server ?
    Par Mouse dans le forum Débats sur le développement - Le Best Of
    Réponses: 23
    Dernier message: 12/08/2003, 06h23
  3. [Kylix] sql server & kylix
    Par fehmitn dans le forum EDI
    Réponses: 1
    Dernier message: 23/08/2002, 19h44
  4. Backup BD SQL Server
    Par Ethmane dans le forum Administration
    Réponses: 3
    Dernier message: 07/06/2002, 00h42

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