2012-11-27 3 views
0

J'ai une table avec une colonne de noms d'ordinateurs ping-able qui me sont donnés dans le cadre d'une table plus grande. Les noms d'ordinateur peuvent contenir un nom de domaine en pointillés et/ou être une adresse IP. J'ai besoin de séparer le nom de l'ordinateur et le nom de domaine dans leurs propres colonnes.La requête de mise à jour d'accès ne permet pas de mettre à jour des enregistrements spécifiques

Par exemple:

ComputerFullName | ComputerName | Domain 
comp1    |    | 
1.2.0.1   |    | 
comp3.place.com |    | 
1.2.1.45.place.com |    | 

je peux utiliser la requête suivante pour remplir Domaine:

UPDATE Example 
SET Domain = SWITCH(
    ComputerFullName LIKE '#*.#*.#*.#*.*', MID(ComputerFullName, INSTR(1, REPLACE(ComputerFullName, '.', ' ', 1, 3), '.') + 1) 
    , ComputerFullName LIKE '#*.#*.#*.#*', NULL 
    , INSTR(1, ComputerFullName, '.') <> 0, MID(ComputerFullName, INSTR(1, ComputerFullName, '.') + 1) 
); 

J'ai essayé plusieurs requêtes pour mettre à jour la colonne ComputerName, était le plus prometteur:

UPDATE Example 
SET ComputerName = SWITCH(
    ComputerFullName LIKE '#*.#*.#*.#*.*', LEFT(ComputerFullName, INSTR(1, ComputerFullName, Domain) - 2) 
    , ComputerFullName LIKE '#*.#*.#*.#*', ComputerFullName 
    , INSTR(1, ComputerFullName, '.') <> 0, LEFT(ComputerFullName, INSTR(1, ComputerFullName, '.') - 1) 
    , TRUE, ComputerFullName 
); 

Cette tentative et toutes les autres ont renvoyé une erreur indiquant "Microsoft Office Access ne peut pas mettre à jour tous les enregistrements dans la requête de mise à jour ... L'accès n'a pas mis à jour 2 domaine (s) en raison d'un échec de conversion de type ... »

Le tableau résultant ressemble:

ComputerFullName | ComputerName | Domain 
comp1    |    | 
1.2.0.1   |    | 
comp3.place.com | comp3  | place.com 
1.2.1.45.place.com | 1.2.1.45  | place.com 

La table que je veux est:

ComputerFullName | ComputerName | Domain 
comp1    | comp1  | 
1.2.0.1   | 1.2.0.1  | 
comp3.place.com | comp3  | place.com 
1.2.1.45.place.com | 1.2.1.45  | place.com 

Une suggestion? En travaillant avec la réponse ci-dessous j'ai réalisé pourquoi ma requête ci-dessus ne fonctionne pas. Access évalue chaque valeur possible dans l'instruction SWITCH même si la condition est fausse. Pour cette raison, le paramètre de longueur des fonctions LEFT étaient des nombres négatifs lorsqu'il n'y avait pas de domaine.

+0

Je vais clarifier la question. comp1 et 1.2.0.1 devraient être dans la colonne ComputerName. – mjoshawa

+0

Cela se produit localement dans Access. Je pourrais utiliser une fonction pour cela (comme l'itération à travers un jeu d'enregistrements), mais d'après mon expérience une requête Access SQL est beaucoup plus rapide. Il pourrait potentiellement y avoir des dizaines de milliers d'enregistrements. – mjoshawa

Répondre

2

Je pense que @HansUp faisait référence à l'appel d'une fonction depuis votre requête pour diviser vos noms. Essayez cette fonction:

Function SplitName(ByRef CFN As String, PartWanted As Integer) As String 
    Dim CFN2 As String 
    Dim I As Integer 
    CFN2 = Replace(CFN, ".", "") 
    If IsNumeric(CFN2) Then 'assume it's an IP address 
     CFN = CFN & "|" 
    Else 
     Select Case Len(CFN) - Len(CFN2) 'we count the dots 
      Case Is > 1 'at least 2 dots means computer & domain names 
       I = InStrRev(CFN, ".") 
       I = InStrRev(CFN, ".", I - 1) 
       Mid(CFN, I) = "|" 
      Case Is = 1 ' 1 dot means domain name only 
       CFN = "|" & CFN 
      Case Else '0 dots means computer name only 
       CFN = CFN & "|" 
     End Select 
    End If 
    SplitName = Split(CFN, "|")(PartWanted) 
End Function 

Le paramètre PartWanted serait un 0 (pour obtenir le nom de l'ordinateur) ou 1 (pour obtenir le nom de domaine). Donc, votre requête ressemblerait à:

UPDATE Example 
SET Computername = SplitName([ComputerFullName],0), Domain = SplitName([ComputerFullName],1); 

Cela fonctionne assez vite. Je l'ai testé et il a fallu 13 secondes pour appeler cette fonction 2 millions de fois (cela n'incluait pas la mise à jour actuelle, juste l'appel).

+0

Je ne savais pas que vous pouviez appeler une fonction depuis l'intérieur de la requête. Je vais essayer cet après-midi. Je vous remercie. – mjoshawa

+0

Vous pouvez aussi longtemps que vous exécutez la requête à partir d'Access. Cela ne fonctionnera pas si vous frappez simplement la base de données via ODBC ou un autre lien. –

+0

Cela a fonctionné aussi bien que vous l'avez dit. Merci beaucoup. – mjoshawa

Questions connexes