QUERY CON CAMPI INDICIZZATI E NON

Antonio Tanzillo 0 Punti di reputazione
2026-05-12T08:36:58.87+00:00

La query: SELECT CODICE FROM ARTICOLI WHERE WEB =1 AND PREZZO_4 = 0

WEB INTEGER , PREZZO_4 CURRENCY

Ambiente vb6, Database Access 2000-2003 , ma ho provato anche altri formati di DB

Accesso ai dati sia in ADO che DAO (oledb), quindi jet3.5 opure jet 4.0 . Database compattato più volte.

Web è indicizzato , pezzo_4 no

Tempo di esecuzioe circa 3 minuti !! quando va bene , a volte anche 15 minuti

La cosa assurda è che se rimuovo l'indice WEB la query è istantanea

Ho provato anche SELECT CODICE FROM ( SELECT CODICE, PREZZO_4 FROM ARTICOLI WHERE WEB = 1) WHERE prezzo_4 = 0 uguale !

anche SELECT CODICE FROM ARTICOLI WHERE [WEB] =1 AND PREZZO_4 = 0

Come è possibile che con solo due campi e una query banale access si incastra in questo modo ?

Grazie

Microsoft 365 e Office | Access | Altro | Windows
0 commenti Nessun commento

2 risposte

Ordina per: Più recente
  1. Antonio Tanzillo 0 Punti di reputazione
    2026-05-15T14:55:51.59+00:00

    L’indice composito è da escludere in quanto potrei avere una infinità di altri campi da valutare insieme al campo WEB. L’opzione di usare (WEB +0 )  = 1 è interessante, ha funzionato, ma a questo punto tanto vale rimuovere l’indice,  no ?

    La tabella articoli contiene 110.000 record di cui  33.000   WEB =1

    La mia domanda è:  Come è possibile che questo BUG c’è con DAO motore Jet 3.5 e 4.0 ma anche con ADO (oledb.4.0) e con versioni di database access diverse,  dalla più vecchia , all’ultima in formato MDB. Ho fatto tante prove ma il risultato è sempre lo stesso.

    L’unica soluzione è rimuovere l’indice sul campo WEB

    Parliamo di una attesa di 5/10 minuti, a volte da errore “risorse di sistema insufficienti” . Mi aspettavo che il motore valutassi prima il primo campo , WEB , così da avere all’istate 33.000 record da valutare, e poi PREZZO_1 e poi altri a seguire se presenti.

     

    Cordiali Saluti

    La risposta è stata utile?


  2. Anonimo
    2026-05-12T14:41:50.79+00:00

    Nota: Questa risposta è stata tradotta automaticamente. Di conseguenza, può contenere errori grammaticali o espressioni strane.

    Ciao Antonio Tanzillo

    Posso immaginare che questo accada in una tabella abbastanza grande con molti dati, giusto? Tuttavia, non ho accesso allo stesso ambiente o al tuo dataset esatto, quindi non sono in grado di riprodurlo direttamente. Tuttavia, basandomi su ciò che ho esaminato, la spiegazione più probabile per questo comportamento è legata alla selettività dell'indice. In termini semplici, ecco cosa sta probabilmente accadendo nel tuo database:

    Se il valore WEB = 1 appare in una grande percentuale di righe, l'indice su WEB diventa a bassa selettività. Invece di restringere efficacemente il set di risultati, Access recupera una grande parte della tabella tramite l'indice.

    Internamente, il motore:

    • Utilizza l'indice su WEB per individuare le righe corrispondenti
    • Poi torna ripetutamente alla tabella principale (ricerca per segnalibro) per valutare PREZZO_4

    Quando questo accade milioni di volte, si verifica un intenso I/O casuale, che è significativamente più lento di una semplice scansione sequenziale della tabella.

    Questo spiega perché la query diventa quasi istantanea quando si rimuove l'indice - Access è costretto a eseguire una scansione completa, che in questo caso specifico è effettivamente più efficiente.

    Quindi potresti considerare 2 approcci:

    • Crea un indice composito (indice multi-colonna) su entrambi i campi insieme. Questo permette al motore di soddisfare entrambe le condizioni direttamente dall'indice senza dover tornare alla tabella. Esegui questo SQL (in una nuova query, Visualizzazione SQL): CREATE INDEX idx_WEB_PREZZO4 ON ARTICOLI (WEB, PREZZO_4) Dopo aver creato l'indice, compatta e ripara il database.
    • If you want to keep the existing index but avoid its usage, you can use a small expression trick: SELECT CODICE FROM ARTICOLI WHERE (WEB + 0) = 1 AND PREZZO_4 = 0 

    Spero che queste informazioni siano utili e ti diano un quadro più chiaro della situazione. Se hai altre domande, non esitare a chiedere.


    Se la risposta è utile, clicca su "Accetta risposta"" e vota favorevolmente la risposta positivamente. Se hai domande extra su questa risposta, clicca su "Commento".

    Nota: Segui i passaggi in la nostra documentazione per abilitare le notifiche via e-mail se desideri ricevere la notifica correlata per questa discussione.

    La risposta è stata utile?


Risposta

Le risposte possono essere contrassegnate come "Accettata" dall'autore della domanda e "Consigliata" dai moderatori, in modo da consentire agli utenti di sapere che la risposta ha risolto il problema dell'autore.