Повышение производительности Go кода

221
02 ноября 2018, 16:30

Как я могу оптимизировать производительность Go кода?
ОС: Windows 8.1 x32-64.
Суть работы: приложение подключается последовательно к более 50 БД (локальных БД), копирует данные в .temp файл (потому что эти БД могут использовать другие приложения, а как мы знаем невозможно редактировать БД когда его использует другое приложение), считывает данные из .temp файла и записывает считанные дынные с БД в текстовый файл "query.txt".

Приметка: в БД может быть от 10 строк до 7 тысяч строк. На все это уходит секунд 6-7 на мощном ноутбуке, а если ещё и запускать на более слабых пк/ноутбуках то может занять более 25 сек.

Код:

func fileCopyProcedure(ptSource string, ptDest string) {
    sourceFile, err := os.Open(ptSource)
    if err != nil {
        fmt.Println(err)
    }
    defer sourceFile.Close()
    destFile, err := os.Create(ptDest)
    if err != nil {
        fmt.Println(err)
    }
    defer destFile.Close()
    _, err = io.Copy(destFile, sourceFile)
    if err != nil {
        fmt.Println(err)
    }
    err = destFile.Sync()
    if err != nil {
        fmt.Println(err)
    }
    sourceFileInfo, err := sourceFile.Stat()
    if err != nil {
        fmt.Println(err)
    }
    destFileInfo, err := destFile.Stat()
    if err != nil {
        fmt.Println(err)
    }
    if sourceFileInfo.Size() == destFileInfo.Size() {
    } else {
        fmt.Println(err)
    }
}
func DB_Handler(path string) {
    var db *sql.DB
    err := fileCopyProcedure(path, "tmp.dat")
    if err != nil {
        fmt.Println(err)
    }
    db, err = sql.Open("sqlite3", "tmp.dat")
    if err != nil {
        fmt.Println(err)
    }
    defer db.Close()
    rows, err := db.Query("select cr_value, fx_value, orm_value, speend_value, sc_source_value, datainfo, secure_only from cookies")
    if err != nil {
        fmt.Println(err)
    }
    defer rows.Close()
    for rows.Next() {
        var sql_cr_value string
        var sql_fx_value string
        var sql_orm_value string
        var sql_speend_value string
        var sql_sc_source_value string
        var sql_datainfo string
        var sql_secure_only string
        err = rows.Scan(
            &sql_cr_value,
            &sql_fx_value,
            &sql_orm_value,
            &sql_speend_value,
            &sql_sc_source_value,
            &sql_datainfo,
            &sql_secure_only,
        )
        if err != nil {
            fmt.Println(err)
        }
        if sql_cr_value != "" && sql_orm_value != "" && sql_datainfo != "" {
            var cprInfo = fmt.Sprintf("%s   %s  %s  %s  %s  %s\r\n",
                sql_cr_value,
                sql_fx_value,
                sql_orm_value,
                sql_speend_value,
                sql_sc_source_value,
                sql_datainfo,
                sql_secure_only,
            )
            var hkInfo = fmt.Sprintf("%s\r\n",
                sql_datainfo,
            )
            wfile, err := os.OpenFile(
                "data.txt",
                os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0600,
            )
            if err != nil {
                fmt.Println(err)
            }
            defer wfile.Close()
            if _, err = wfile.WriteString(cprInfo); err != nil {
                fmt.Println(err)
            }
            wfile, err = os.OpenFile(
                "opx.txt",
                os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0600,
            )
            if err != nil {
                fmt.Println(err)
            }
            defer wfile.Close()
            if _, err = wfile.WriteString(hkInfo); err != nil {
                fmt.Println(err)
            }
        }
    }
    err = rows.Err()
    if err != nil {
        fmt.Println(err)
    }
}

Как можно ускорить данные процесс?

Answer 1

Если это "50 локальных БД", да ещё обслуживаемых одним инстансом MySQL-сервера, то тупо выполняешь пакет запросов (хоть кучей, хоть по одному)

SELECT * INTO OUTFILE 'file1.tmp' FROM db1.table1;
SELECT * INTO OUTFILE 'file2.tmp' FROM db1.table2;
-- .....
SELECT * INTO OUTFILE 'fileX.tmp' FROM dbX.tableX;

а потом командой ОС

copy *.tmp all_data.txt

собираешь всё в один файл.

Всем этим можно рулить, ясное дело, из чего угодно - в т.ч. и из golang.

Как это сделать ещё быстрее - я лично представить пока не могу.

READ ALSO
Ошибка при INSERT данных в MySQL

Ошибка при INSERT данных в MySQL

Работаем с MacOS и SQL MariaDB (если это важно) Создал базу данных gregs_list и не заполненную таблицу my_contacts

235
Запрос Select не воспринимает переменную из кода

Запрос Select не воспринимает переменную из кода

В интернете нашла кучу подсказок, как в запрос insert добавить определенные переменные из кода, но нашла лишь одно упоминание про вставку переменной,...

243
Подсказка на css. Как треугольнику задать border?

Подсказка на css. Как треугольнику задать border?

Есть иконка (сделанная на html + css) и при наведении на неё курсора, выпадает подсказка

169