• Skip to main content
  • Skip to search
  • Skip to footer
Cadence Home
  • This search text may be transcribed, used, stored, or accessed by our third-party service providers per our Cookie Policy and Privacy Policy.

  1. Community Forums
  2. Custom IC SKILL
  3. Export to CSV efficiently? (code review)

Stats

  • Replies 7
  • Subscribers 144
  • Views 982
  • Members are here 0

Export to CSV efficiently? (code review)

UsableLoki
UsableLoki 1 month ago

I wrote this function to export a list to a generated CSV file.  However the for loop takes hours to run (albeit I am exporting 100,000+ items, but still, the commands that generate these items change things in my project and those only take a few minutes).  I tried to create a 2nd order string buffer because I figured that fprintf to port may have been a bottleneck but this made it run even slower (ran all night and still wasn't done).  Can someone please offer any improvements to this?  I left the previously direct way of export via fprintf commands commented out.

procedure(writeListsToCSV(headerList ListOfLists fileNameSuffix location)
  let((buffer buffer2 comma currentDateTime DateTimeList TimeList year month day time fileName fileHandle lengthHeader)
  ; Get current date and time;;; getCurrentTime() ; => "Jan 26 18:15:18 1993"
    DateTimeList = parseString(getCurrentTime() )
    year = nth(3 DateTimeList)
    month = nth(0 DateTimeList)
    when(month == "Jan" month = "01")
    when(month == "Feb" month = "02")
    when(month == "Mar" month = "03")
    when(month == "Apr" month = "04")
    when(month == "May" month = "05")
    when(month == "Jun" month = "06")
    when(month == "Jul" month = "07")
    when(month == "Aug" month = "08")
    when(month == "Sep" month = "09")
    when(month == "Oct" month = "10")
    when(month == "Nov" month = "11")
    when(month == "Dec" month = "12")
    day = nth(1 DateTimeList)
    time = buildString( parseString( nth(2 DateTimeList) ":") "")

    currentDateTime = buildString( list(year month day time) "_")

    /* I couldn't get this to work, "/" as last character returns "\/" and the compiler hates "\"
    print(getchar(location strlen(location)))
    printf("\n")
    when(not(getchar(location strlen(location)) == "/")
    strcat(location "/")
    )
    */

    ; todo:need to incorporate isReadable(filePath) and getWorkingDir() for better flow
    fileName = strcat(location
                      "/"
                      currentDateTime
                      "_"
                      fileNameSuffix
                      ".csv")

    ; Write the headers
    buffer = strcat(buildString(headerList ",") "\n")

    printf("\nFor loop begins at: %s\n" getCurrentTime())
    lengthHeader = length(headerList) - 1
    ; Write the list values to the file
    for(j 0 length(ListOfLists)-1
        buffer2 = ""
        for(i 0 lengthHeader
            ;print(type(nth(i nth(j ListOfLists)))) ;;if missing values then check possible value type here
            ;printf("\n")

            if(i < lengthHeader then comma = "," else comma = "\n");buffer = strcat(buffer ",") )
            case(type(nth(i nth(j ListOfLists)))
                ('string
                    buffer2 = strcat(buffer2 nth(i nth(j ListOfLists)) comma)
                    ;fprintf(fileHandle nth(i nth(j ListOfLists)))
                )
                ('flonum
                    buffer2 = strcat(buffer2 sprintf(nil "%f" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%f" nth(i nth(j ListOfLists))))
                )
                ('list
                    buffer2 = strcat(buffer2 sprintf(nil "%L" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%L" nth(i nth(j ListOfLists))))
                )
                ('float
                    buffer2 = strcat(buffer2 sprintf(nil "%f" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%f" nth(i nth(j ListOfLists))))
                )
                ('int
                    buffer2 = strcat(buffer2 sprintf(nil "%d" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%d" nth(i nth(j ListOfLists))))
                )
                ('fixnum
                    buffer2 = strcat(buffer2 sprintf(nil "%d" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%d" nth(i nth(j ListOfLists))))
                )
                ('t
                    buffer2 = strcat(buffer2 sprintf(nil "%s" nth(i nth(j ListOfLists))) comma)
                    ;fprintf(fileHandle sprintf(nil "%s" nth(i nth(j ListOfLists))))
                )
            )
            ;when(i < lengthHeader fprintf(fileHandle ",") )
        )
        buffer = strcat(buffer buffer2)
        ;fprintf(fileHandle "\n")
    )
    printf("\nFor loop ends at: %s\n" getCurrentTime())

    ; Open the file for writing
    fileHandle = outfile(fileName)
    ; Write
    fprintf(fileHandle buffer)
    ; Close the file
    close(fileHandle)
    printf("\nClosed file handle at: %s\n" getCurrentTime())
    printf("\nCSV GENERATED AT: %s\n" fileName)
    )
)

  • Sign in to reply
  • Cancel
Parents
  • AaronSymko
    AaronSymko 1 month ago

    You can use the SKILL profiler to pinpoint where your code has bottlenecks. For example, in the CIW, type the following:

    profile( 'time)
    writeListsToCSV(/*enter args here*/)
    profileSummary( ?file "/tmp/profile.results")

    Then, an inventory of runtimes will be listed in tabular format in /tmp/profile.results

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Cancel
  • UsableLoki
    UsableLoki 1 month ago in reply to AaronSymko

    Btw, how do you format type your code into here so it even picks up the IDE structure tags?

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Cancel
Reply
  • UsableLoki
    UsableLoki 1 month ago in reply to AaronSymko

    Btw, how do you format type your code into here so it even picks up the IDE structure tags?

    • Cancel
    • Vote Up +1 Vote Down
    • Sign in to reply
    • Cancel
Children
No Data

Community Guidelines

The Cadence Design Communities support Cadence users and technologists interacting to exchange ideas, news, technical information, and best practices to solve problems and get the most from Cadence technology. The community is open to everyone, and to provide the most value, we require participants to follow our Community Guidelines that facilitate a quality exchange of ideas and information. By accessing, contributing, using or downloading any materials from the site, you agree to be bound by the full Community Guidelines.

© 2025 Cadence Design Systems, Inc. All Rights Reserved.

  • Terms of Use
  • Privacy
  • Cookie Policy
  • US Trademarks
  • Do Not Sell or Share My Personal Information