performance issue: const Table make a copy at runtime lookup. #4354

Closed
Parashurama opened this Issue Jun 17, 2016 · 0 comments

Projects

None yet

2 participants

@Parashurama
Contributor
Parashurama commented Jun 17, 2016 edited

Here is a strange bug in codegen for this code.

import tables
import sets
import strutils

#const FRUITS = ["banana", "apple", "grapes"]
#let FRUITS = ["banana", "apple", "grapes"].toSet
const FRUITS = {"banana":0, "apple":0, "grapes":0}.toTable

proc main() =
    let L = "a long list of words".split()
    for word in L:
        if word notin FRUITS:
            echo(word)

main()

and the generated C code in release mode (also happen in debug mode).
The const Table is reassigned (and copied) to a new variable at each iteration.
This bug also happen for Hashset.

N_NIMCALL(void, main_119436_2908203768)(void) {
    TY104611* L0;
    L0 = nsuSplitCharSet(((NimStringDesc*) &TMP29), TMP30, ((NI) -1));
    {
        NimStringDesc* word_119602_2908203768;
        NI i_119645_2908203768;
        NI L_119647_2908203768;
        word_119602_2908203768 = (NimStringDesc*)0;
        i_119645_2908203768 = ((NI) 0);
        L_119647_2908203768 = (L0 ? L0->Sup.len : 0);
        {
            while (1) {
                if (!(i_119645_2908203768 < L_119647_2908203768)) goto LA3;
                word_119602_2908203768 = L0->data[i_119645_2908203768];
                {
                    Table119020 LOC6;
                    NIM_BOOL LOC7;
                    memset((void*)(&LOC6), 0, sizeof(LOC6));
                    memset((void*)(&LOC6), 0, sizeof(LOC6));
                    genericSeqAssign((&LOC6.data), TMP31, (&NTI119023));
                    LOC6.counter = ((NI) 3);
                    LOC7 = (NIM_BOOL)0;
                    LOC7 = contains_119604_30748785(LOC6, word_119602_2908203768);
                    if (!!(LOC7)) goto LA8;
                    printf("%s\012", word_119602_2908203768? (word_119602_2908203768)->data:"nil");
                    fflush(stdout);
                }
                LA8: ;
                i_119645_2908203768 += ((NI) 1);
            } LA3: ;
        }
    }
}

This bug can be worked around by using let Table but then we need to duplicate the table if we also need to use the const table at compiletime.

@Araq Araq added a commit that closed this issue Aug 4, 2016
@Araq Araq fixes #4354 baeec11
@Araq Araq closed this in baeec11 Aug 4, 2016
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment