Apertura file .csv da esplora risorse e da macro con visualizzazione differente

Anonimo
2022-09-21T09:49:00+00:00

Buongiorno a tutti,

vi scrivo per chiedervi come posso bypassare un problema che ho riscontrato durante la scrittura di una macro con visual basic.

Nella macro che devo creare, devo aprire un file .csv, cancellare, ordinare e convertire alcune colonne per poi importare i dati "filtrati" su un altro foglio.

Il problema che ho riscontrato è che se il file .csv lo apro manualmente da esplorare risorse, ottengo una visualizzazione con i delimitatori di campo applicati (Foto 1), se il file lo apro utilizzando visualbasic (procedendo passo passo con f8 per vedere il comportamento della macro), il file viene aperto come riportato nella seconda foto.

Per semplificare di molto la macro volevo sapere se c'è la possibilità di far aprire tramite visualbasic il file .csv, in modo da ottenere la visualizzazione come da Foto1.

Qualcuno può aiutarmi per favore?

Microsoft 365 e Office | Excel | Per il lavoro | Windows

Domanda bloccata. Questa domanda è stata eseguita dalla community del supporto tecnico Microsoft. È possibile votare se è utile, ma non è possibile aggiungere commenti o risposte o seguire la domanda.

0 commenti Nessun commento

Risposta accettata dall'autore della domanda

Anonimo
2022-09-21T13:43:38+00:00

Ciao Ivan,

Per aprire il file, usando VBA, nello stesso formato di quello mostrato nella tua prima immagine, nel tuo codice, sostituisci l'istruzione

Workbooks.Open xFilePath

con:

Workbooks.Open FileName:=xFilePath, **Local:=True**

===

Regards,

Norman

Immagine

La risposta è stata utile?

2 persone hanno trovato utile questa risposta.
0 commenti Nessun commento

Risposta accettata dall'autore della domanda

Eleuterio Tedeschi 18,590 Punti di reputazione Moderatore volontario
2022-09-21T12:56:01+00:00

Secondo me il VBA non è la strada più veloce, stavolta, per cui ti propongo una alternativa che sono le Power Query:

let

Nomefile = Excel.CurrentWorkbook(){[Name="NomeFile"]}[Content]{0}[Column1], 

Origine = Csv.Document(File.Contents(Nomefile),[Delimiter=";", Columns=16, Encoding=1252, QuoteStyle=QuoteStyle.None]), 

#"Intestazioni alzate di livello" = Table.PromoteHeaders(Origine, [PromoteAllScalars=true]), 

#"Modificato tipo" = Table.TransformColumnTypes(#"Intestazioni alzate di livello",{{"Time\_ms", Int64.Type}}), 

#"Rimosse colonne" = Table.RemoveColumns(#"Modificato tipo",{"MsgProc", "MsgNumber", "Var1", "Var2", "Var3", "Var4", "Var5", "Var6", "Var7", "Var8", "TimeString", "PLC"}), 

#"Ordinate righe" = Table.Sort(#"Rimosse colonne",{{"Time\_ms", Order.Descending}}), 

#"Sostituito valore" = Table.ReplaceValue(#"Ordinate righe","34","RCE",Replacer.ReplaceText,{"MsgClass"}), 

#"Sostituito valore1" = Table.ReplaceValue(#"Sostituito valore","35","CAB",Replacer.ReplaceText,{"MsgClass"}), 

#"Sostituito valore2" = Table.ReplaceValue(#"Sostituito valore1","0","-",Replacer.ReplaceText,{"StateAfter"}), 

#"Sostituito valore3" = Table.ReplaceValue(#"Sostituito valore2","1","+",Replacer.ReplaceText,{"StateAfter"}), 

#"Sostituito valore4" = Table.ReplaceValue(#"Sostituito valore3","2","-",Replacer.ReplaceText,{"StateAfter"}), 

#"Sostituito valore5" = Table.ReplaceValue(#"Sostituito valore4","3","+",Replacer.ReplaceText,{"StateAfter"}), 

#"Sostituito valore6" = Table.ReplaceValue(#"Sostituito valore5","6","R",Replacer.ReplaceText,{"StateAfter"}), 

#"Aggiunta colonna personalizzata" = Table.AddColumn(#"Sostituito valore6", "TimeStm", each [Time\_ms]/1000000), 

#"Modificato tipo1" = Table.TransformColumnTypes(#"Aggiunta colonna personalizzata",{{"TimeStm", type datetime}}), 

#"Riordinate colonne" = Table.ReorderColumns(#"Modificato tipo1",{"TimeStm", "Time\_ms", "StateAfter", "MsgClass", "MsgText"}), 

#"Rimosse colonne1" = Table.RemoveColumns(#"Riordinate colonne",{"Time\_ms"}) 

in

#"Rimosse colonne1"

Ti allego il file di prova, in quanto ho inserito un foglio Dati che contiene B1 dove metterai il percorso del file e B2 dove c'è il nome del file.

La combinazione in B3 la fa una formula, ma tu potresti depositare percorso e nome con la selezione che facevi con:

Set xObjFD = Application.FileDialog(msoFileDialogFilePicker)

Detto questo, il codice MQuery che ti ho proposto carica, ordina, toglie le colonne e converte la 2ª e 3ª colonna con i segni ed i codici che avevi nel VBA restituendoti la tabella finita.

Per aggiornarla, basta un tasto destro sulla tabella->Aggiorna e PQ ricarica il csv convertendolo.

Il file lo trovi qui.

Ciao.

P.S. ti ho lasciato anche un codice che importa il csv line to line, ma con 300k righe non è proprio il caso vista la resa in termini di tempo

La risposta è stata utile?

1 persona ha trovato utile questa risposta.
0 commenti Nessun commento

5 risposte aggiuntive

Ordina per: Più utili
  1. Anonimo
    2022-09-21T14:03:50+00:00

    Secondo me il VBA non è la strada più veloce, stavolta, per cui ti propongo una alternativa che sono le Power Query:

    let

    Nomefile = Excel.CurrentWorkbook(){[Name="NomeFile"]}[Content]{0}[Column1],

    Origine = Csv.Document(File.Contents(Nomefile),[Delimiter=";", Columns=16, Encoding=1252, QuoteStyle=QuoteStyle.None]),

    #"Intestazioni alzate di livello" = Table.PromoteHeaders(Origine, [PromoteAllScalars=true]),

    #"Modificato tipo" = Table.TransformColumnTypes(#"Intestazioni alzate di livello",{{"Time_ms", Int64.Type}}),

    #"Rimosse colonne" = Table.RemoveColumns(#"Modificato tipo",{"MsgProc", "MsgNumber", "Var1", "Var2", "Var3", "Var4", "Var5", "Var6", "Var7", "Var8", "TimeString", "PLC"}),

    #"Ordinate righe" = Table.Sort(#"Rimosse colonne",{{"Time_ms", Order.Descending}}),

    #"Sostituito valore" = Table.ReplaceValue(#"Ordinate righe","34","RCE",Replacer.ReplaceText,{"MsgClass"}),

    #"Sostituito valore1" = Table.ReplaceValue(#"Sostituito valore","35","CAB",Replacer.ReplaceText,{"MsgClass"}),

    #"Sostituito valore2" = Table.ReplaceValue(#"Sostituito valore1","0","-",Replacer.ReplaceText,{"StateAfter"}),

    #"Sostituito valore3" = Table.ReplaceValue(#"Sostituito valore2","1","+",Replacer.ReplaceText,{"StateAfter"}),

    #"Sostituito valore4" = Table.ReplaceValue(#"Sostituito valore3","2","-",Replacer.ReplaceText,{"StateAfter"}),

    #"Sostituito valore5" = Table.ReplaceValue(#"Sostituito valore4","3","+",Replacer.ReplaceText,{"StateAfter"}),

    #"Sostituito valore6" = Table.ReplaceValue(#"Sostituito valore5","6","R",Replacer.ReplaceText,{"StateAfter"}),

    #"Aggiunta colonna personalizzata" = Table.AddColumn(#"Sostituito valore6", "TimeStm", each [Time_ms]/1000000),

    #"Modificato tipo1" = Table.TransformColumnTypes(#"Aggiunta colonna personalizzata",{{"TimeStm", type datetime}}),

    #"Riordinate colonne" = Table.ReorderColumns(#"Modificato tipo1",{"TimeStm", "Time_ms", "StateAfter", "MsgClass", "MsgText"}),

    #"Rimosse colonne1" = Table.RemoveColumns(#"Riordinate colonne",{"Time_ms"})

    in

    #"Rimosse colonne1"

    Ti allego il file di prova, in quanto ho inserito un foglio Dati che contiene B1 dove metterai il percorso del file e B2 dove c'è il nome del file.

    La combinazione in B3 la fa una formula, ma tu potresti depositare percorso e nome con la selezione che facevi con:

    Set xObjFD = Application.FileDialog(msoFileDialogFilePicker)

    Detto questo, il codice MQuery che ti ho proposto carica, ordina, toglie le colonne e converte la 2ª e 3ª colonna con i segni ed i codici che avevi nel VBA restituendoti la tabella finita.

    Per aggiornarla, basta un tasto destro sulla tabella->Aggiorna e PQ ricarica il csv convertendolo.

    Il file lo trovi qui.

    Ciao.

    P.S. ti ho lasciato anche un codice che importa il csv line to line, ma con 300k righe non è proprio il caso vista la resa in termini di tempo

    Molto gentile Eleuterio,

    molto più veloce rispetto al mio VBA,

    grazie mille!😀

    La risposta è stata utile?

    0 commenti Nessun commento
  2. Anonimo
    2022-09-21T10:27:54+00:00

    Il problema che ho riscontrato è che se il file .csv lo apro manualmente da esplorare risorse, ottengo una visualizzazione con i delimitatori di campo applicati (Foto 1), se il file lo apro utilizzando visualbasic (procedendo passo passo con f8 per vedere il comportamento della macro), il file viene aperto come riportato nella seconda foto.

    Buongiorno a te,

    si può fare, ma devo vedere il tuo codice, potresti dover avere bisogno di rivedere il processo di import.

    Ciao.

    P.S. magari anche qualche riga del csv aiuterebbe a contestualizzarti la risposta, puoi condividere il file denaturato da dati sensibili?

    Grazie EleuterioTedeschi,

    di seguito il codice della macro:

    _______________________________________________________________________

    Sub OpenNewBox()

    Dim xFilePath As String

    Dim xObjFD As FileDialog

    Set xObjFD = Application.FileDialog(msoFileDialogFilePicker)

    With xObjFD

        .AllowMultiSelect = False 
    

    9 .Filters.Add "Excel Files", "*.csv", 1

        .Show 
    
        If .SelectedItems.Count > 0 Then 
    
            xFilePath = .SelectedItems.Item(1) 
    
        Else 
    
            Exit Sub 
    
        End If 
    
    End With 
    
    Workbooks.Open xFilePath 
    

    ' Apri ArchivioRCE0

    Worksheets("ArchivioRCE0").Activate 
    
    Range("A1").Select 
    

    '

    ' Sistemazione colonne

    '

    Range("C2").Select 
    
    Application.CutCopyMode = False 
    
    ActiveCell.FormulaR1C1 = "=IF(RC[-2]>1,CONCATENATE(RC[-2],"","",RC[-1]),)" 
    
    Range("C2").Select 
    
    Selection.Copy 
    
    Columns("C:C").Select 
    
    ActiveSheet.Paste 
    
    Application.CutCopyMode = False 
    
    Selection.Copy 
    
    Columns("D:D").Select 
    
    Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks \_ 
    
        :=False, Transpose:=False 
    
    Application.CutCopyMode = False 
    
    Selection.TextToColumns Destination:=Range("D1"), DataType:=xlDelimited, \_ 
    
        TextQualifier:=xlDoubleQuote, ConsecutiveDelimiter:=False, Tab:=False, \_ 
    
        Semicolon:=True, Comma:=False, Space:=False, Other:=False, FieldInfo \_ 
    
        :=Array(Array(1, 1), Array(2, 1), Array(3, 1), Array(4, 1), Array(5, 1), Array(6, 1), \_ 
    
        Array(7, 1), Array(8, 1), Array(9, 1), Array(10, 1), Array(11, 1), Array(12, 1), Array(13, 1 \_ 
    
        ), Array(14, 1), Array(15, 1), Array(16, 1)), TrailingMinusNumbers:=True 
    
    Columns("A:C").Select 
    
    Selection.Delete Shift:=xlToLeft 
    
    Range("A1").Select 
    

    '

    ' Elimina colonne non utilizzate

    '

    Range("B:B,E:N,P:P").Select 
    
    Range("P1").Activate 
    
    Selection.Delete Shift:=xlToLeft 
    

    '

    ' Ordina decrescente

    '

    Range("A1").Select 
    
    ActiveWorkbook.Worksheets("ArchivioRCE0").Sort.SortFields.Clear 
    
    ActiveWorkbook.Worksheets("ArchivioRCE0").Sort.SortFields.Add Key:=Range( \_ 
    
        "A2:A300000"), SortOn:=xlSortOnValues, Order:=xlDescending, DataOption:= \_ 
    
        xlSortNormal 
    
    With ActiveWorkbook.Worksheets("ArchivioRCE0").Sort 
    
        .SetRange Range("A1:E300000") 
    
        .Header = xlYes 
    
        .MatchCase = False 
    
        .Orientation = xlTopToBottom 
    
        .SortMethod = xlPinYin 
    
        .Apply 
    
    End With 
    

    '

    ' Converte testo RCE/CAB

    '

    Columns("C:C").Select 
    
    Selection.Replace What:="34", Replacement:="RCE", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    
    Selection.Replace What:="33", Replacement:="CAB", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    

    '

    ' Converte testo +/-

    '

    Columns("B:B").Select 
    
    Selection.Replace What:="0", Replacement:=" -", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    
    Selection.Replace What:="1", Replacement:=" +", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    
    Selection.Replace What:="2", Replacement:=" -", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    
    Selection.Replace What:="3", Replacement:=" +", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    
    Selection.Replace What:="6", Replacement:=" R", LookAt:=xlPart, \_ 
    
        SearchOrder:=xlByRows, MatchCase:=False, SearchFormat:=False, \_ 
    
        ReplaceFormat:=False 
    

    '

    ' Converti tempo

    '

    Columns("B:B").Select 
    
    Selection.Insert Shift:=xlToRight, CopyOrigin:=xlFormatFromLeftOrAbove 
    
    Range("B2").Select 
    
    ActiveCell.FormulaR1C1 = "=RC[-1]/1000000" 
    
    Range("B2").Select 
    
    Selection.Copy 
    
    Range("B3:B300000").Select 
    
    ActiveSheet.Paste 
    
    Columns("B:B").Select 
    
    Application.CutCopyMode = False 
    
    Selection.Copy 
    
    Columns("A:A").Select 
    
    Selection.PasteSpecial Paste:=xlPasteValuesAndNumberFormats, Operation:= \_ 
    
        xlNone, SkipBlanks:=False, Transpose:=False 
    
    Columns("A:A").Select 
    
    Application.CutCopyMode = False 
    
    Selection.NumberFormat = "dd/mm/yyyy hh:mm:ss.000" 
    
    Columns("B:B").Select 
    
    Selection.Delete Shift:=xlToLeft 
    
    Range("A1").Select 
    
    ActiveCell.FormulaR1C1 = "TimeStm" 
    
    Range("A2").Select 
    

    '

    ' Elimina intestazione colonna + e RCS/CAB

    '

    Range("B1:C1").Select 
    
    Selection.ClearContents 
    

    '

    ' Adatta larghezza colonna

    '

    Columns("A:E").Select 
    
    Columns("A:E").EntireColumn.AutoFit 
    

    '

    '

    ' Blocca finestra

    '

    Range("A1").Select 
    
    With ActiveWindow 
    
        .SplitColumn = 0 
    
        .SplitRow = 1 
    
    End With 
    
    ActiveWindow.FreezePanes = True 
    

    '

    ' Copia su Analisi RCE

    '

    Columns("A:D").Select 
    
    Selection.Copy 
    
    Windows("Analisi RCE\_.xlsm").Activate 
    
    Range("A1").Select 
    
    ActiveSheet.Paste 
    

    '

    ' Applica filtro

    '

    Cells.Select 
    
    Selection.AutoFilter 
    

    ' Chiudi Archivio RCE0

    Workbooks("ArchivioRCE0.csv").Close SaveChanges:=False 
    

    End Sub

    _______________________________________________________________________

    Questo è il codice fatto per "bypassare" il problema, ma applicato a 300.000 celle inizia a diventare pesante.

    DI seguito, link per scaricare il .csv, alleggerito di qualche riga.

    https://we.tl/t-9VBt8ZEw0v

    La risposta è stata utile?

    0 commenti Nessun commento
  3. Eleuterio Tedeschi 18,590 Punti di reputazione Moderatore volontario
    2022-09-21T09:55:03+00:00

    Il problema che ho riscontrato è che se il file .csv lo apro manualmente da esplorare risorse, ottengo una visualizzazione con i delimitatori di campo applicati (Foto 1), se il file lo apro utilizzando visualbasic (procedendo passo passo con f8 per vedere il comportamento della macro), il file viene aperto come riportato nella seconda foto.

    Buongiorno a te,

    si può fare, ma devo vedere il tuo codice, potresti dover avere bisogno di rivedere il processo di import.

    Ciao.

    P.S. magari anche qualche riga del csv aiuterebbe a contestualizzarti la risposta, puoi condividere il file denaturato da dati sensibili?

    La risposta è stata utile?

    0 commenti Nessun commento