powered by simpleCommunicator - 2.0.59     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / C++ [игнор отключен] [закрыт для гостей] / C++ & Excel
17 сообщений из 17, страница 1 из 1
C++ & Excel
    #37567334
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Нарыл libxl пока искал... Задача-то тривиальная, - прочесть значения в нескольких ячейках. Номера ячеек известны.

кто-нибудь уже пользовался этим инструментом, есть что-нибудь попроще?
...
Рейтинг: 0 / 0
C++ & Excel
    #37567366
egorych
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
scymaksесть что-нибудь попроще?есть. в билдере есть компоненты для работы с екселем, в Qt тоже есть класс соответствующий, выбирай на вкус
...
Рейтинг: 0 / 0
C++ & Excel
    #37567402
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
egorych,

ну это здорово конечно, а именно вот из MVSC 2005 / 2008 / 2010 есть что-нибудь тоже встроенное?
...
Рейтинг: 0 / 0
C++ & Excel
    #37567560
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Уже пришла в голову мысль сделать страшное :)


Java + JNI :)
...
Рейтинг: 0 / 0
C++ & Excel
    #37568113
egorych
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
scymaks, Qt отлично монтируется на студию любой из этих версий, например
...
Рейтинг: 0 / 0
C++ & Excel
    #37568136
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
egorych,

хочется просто максимально простое и лаконичное решение. Qt во-первых большой.
...
Рейтинг: 0 / 0
C++ & Excel
    #37568324
Elin
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Самое простое - OLE & COM ;)

а если серьезно, то на сайте у мс есть формат ексельного файла 95-2003.
написать ф-цию для того что бы прочитать 2-3 ячейки не особо сложно будет.
...
Рейтинг: 0 / 0
C++ & Excel
    #37568340
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Elin,

можно немного более четко и подробно что вы имели ввиду?
...
Рейтинг: 0 / 0
C++ & Excel
    #37568654
Фотография Ex_Soft
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
> Задача-то тривиальная, - прочесть значения в нескольких ячейках. Номера ячеек известны.
>
> есть что-нибудь попроще?
тынць ?
_________________
"Helo, word!" - 17 errors 56 warnings
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
C++ & Excel
    #37569486
scymaks
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Ex_Soft,

чето не хватает моего уровня мозгов понять )

решил с libxl работать. как в студии подключить dll?
...
Рейтинг: 0 / 0
C++ & Excel
    #37572362
Фотография Ex_Soft
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
scymaksпонять
Все просто, как арбуз:
1. Подключаемся
2. Выбираем/Добавляем
Код: sql
1.
2.
select * from [Sheet1$A1:B10]
insert into [Sheet1$] (F1,F2) values (11,121)
...
Рейтинг: 0 / 0
Период между сообщениями больше года.
C++ & Excel
    #38824424
Фотография SashaMercury
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Здравствуйте.
Мне нужно подготовить файл excel для импорта его в таблицу БД. (Кстати, делаете ли вы так ?) Думаю, что мне не составит большого труда написать код vba для анализа документа. Но тут я подумал, а может быть стоит разобраться и сделать на Си. Точнее мне хочется это сделать именно на Си. Как вы считаете, это правильная идея ?
...
Рейтинг: 0 / 0
C++ & Excel
    #38824428
Фотография SashaMercury
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Хотя наверное нет. Это, вероятно, равносильно тому, если бы я предложил сажать деревья используя стерилизованные медицинские инструменты. В общем, это слишком грязная работа для Си, верно ?
...
Рейтинг: 0 / 0
C++ & Excel
    #38824510
RWolf
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SashaMercury,

нерационально, много мороки.
тут идеально подойдёт vba или delphi.
...
Рейтинг: 0 / 0
C++ & Excel
    #38824537
m_Sla
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Мороки много, это точно.
Нужно было читать данные из exel. Перелопатил пол интернета, информации очень мало.
В итоге сделал так:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
154.
155.
156.
157.
158.
159.
160.
161.
162.
163.
164.
165.
166.
167.
168.
169.
170.
171.
172.
173.
174.
175.
176.
177.
178.
179.
180.
181.
182.
183.
184.
185.
186.
187.
188.
189.
190.
191.
192.
193.
194.
195.
196.
197.
198.
199.
200.
201.
202.
203.
204.
205.
206.
207.
208.
209.
210.
211.
212.
213.
214.
215.
216.
217.
218.
219.
220.
221.
222.
223.
224.
225.
226.
227.
228.
229.
230.
231.
232.
233.
/////////////////////////////////////////////////////
void MainWindow::get_data_from_exel()
{
    // Инициализируем COM
    CoInitialize(NULL);

    // Получаем идентификатор CLSID
    CLSID clsid;

    HRESULT hr = CLSIDFromProgID(L"Excel.Application", &clsid);
    if(FAILED(hr))
    {
        MessageBoxW(NULL, L"CLSIDFromProgID() failed", L"Error", 0x10010);
    }
    else
    {
        VARIANT result;
        VARIANT parm;

        // Получаем доступ к СОМ объекту
        IDispatch *pXlApp;
        hr = CoCreateInstance(clsid, NULL, CLSCTX_LOCAL_SERVER, IID_IDispatch, (void **)&pXlApp);
        if(FAILED(hr))
        {
            MessageBoxW(NULL, L"Excel not registered properly", L"Error", 0x10010);
        }
        else
        {
            //Делаем ексель видимым
            parm.vt = VT_I4;
            parm.lVal = 1;
            AutoWrap(DISPATCH_PROPERTYPUT, NULL, pXlApp, L"Visible", 1, parm);

            // Получаем доступ к коллекции Книг
            IDispatch *pXlBooks;
            VariantInit(&result);
            AutoWrap(DISPATCH_PROPERTYGET, &result, pXlApp, L"Workbooks", 0);
            pXlBooks = result.pdispVal;

            // Открываем книгу
            IDispatch *pXlBook = 0;

            OPENFILENAMEW ofn;
            wchar_t szFile[260];
            // Initialize OPENFILENAME
            ZeroMemory(&ofn, sizeof(ofn));
            ofn.lStructSize = sizeof(ofn);
            ofn.hwndOwner = 0;
            ofn.lpstrFile = szFile;
            ofn.lpstrFile[0] = '\0';
            ofn.nMaxFile = sizeof(szFile)/sizeof(szFile[0]);
            ofn.lpstrFilter = L"Exel\0*.xlsx\0";
            ofn.nFilterIndex = 1;
            ofn.lpstrFileTitle = NULL;
            ofn.nMaxFileTitle = 0;
            ofn.lpstrInitialDir = L"C:\\";
            ofn.Flags = OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST;
            if( GetOpenFileNameW(&ofn)==TRUE )
            {
                parm.vt = VT_BSTR;
                parm.bstrVal = SysAllocString(szFile);

                AutoWrap(DISPATCH_PROPERTYGET, &result, pXlBooks, L"Open", 1, parm);
                pXlBook = result.pdispVal;
                SysFreeString(parm.bstrVal);

                // Читаем содержимое ячейки
                IDispatch *pXlSheet = 0;
                IDispatch *pXlCells = 0;

                AutoWrap(DISPATCH_PROPERTYGET, &result, pXlApp, L"ActiveSheet", 0);
                pXlSheet = result.pdispVal;

                AutoWrap(DISPATCH_PROPERTYGET, &result, pXlSheet, L"Cells", 0 );
                pXlCells = result.pdispVal;

                //Запрос диапазона, который необходимо обработать
                exel_dialog1->exec();
                QRect r=exel_dialog1->result;

                table->setRowCount(r.height());
                for(int cell_y=r.top() , y=0; cell_y<=r.bottom(); ++cell_y, ++y)
                {
                    for(int cell_x=r.left(), x=0; cell_x<=r.right(); ++cell_x, ++x)
                    {
                        QString text=QString::fromStdWString(get_cell_item( pXlCells, cell_x, cell_y));
                        table->setData(table->index(y, x, QModelIndex()),text);
                    }
                }

                // Закрываем exel
                AutoWrap(DISPATCH_METHOD, NULL, pXlApp, L"Quit", 0 );

                // Освобождаем память...
                pXlCells->Release();
                pXlSheet->Release();
                pXlBook->Release();
            }//if( GetOpenFileNameW(&ofn)==TRUE )

            pXlBooks->Release();
            pXlApp->Release();
        }
    }

    // Закрываем COM
    CoUninitialize();
}
/////////////////////////////////////////////////////
// AutoWrap() - Automation helper function
// autoType может быть:
//   DISPATCH_METHOD
//   DISPATCH_PROPERTYGET
//   DISPATCH_PROPERTYPUT
//   DISPATCH_PROPERTYPUTREF
HRESULT MainWindow::AutoWrap(int autoType, VARIANT *pvResult, IDispatch *pDisp, const wchar_t *ptName, int cArgs...)
{
    // Begin variable-argument list...
    va_list marker;
    va_start(marker, cArgs);

    if(!pDisp)
    {
        MessageBoxW(NULL, L"NULL IDispatch passed to AutoWrap()", L"Error", 0x10010);
        return -1;
    }

    // Variables used...
    DISPPARAMS dp = { NULL, NULL, 0, 0 };
    DISPID dispidNamed = DISPID_PROPERTYPUT;
    DISPID dispID;
    HRESULT hr;

    std::wstring error_text;
    std::wstring Name = ptName;

    // Get DISPID for name passed...
    hr = pDisp->GetIDsOfNames(IID_NULL, (WCHAR**)&ptName, 1, LOCALE_USER_DEFAULT, &dispID);
    if(FAILED(hr))
    {
        error_text = L"IDispatch::GetIDsOfNames(\"" + Name + L"\") failed w/err " + QString::number(hr,16).toStdWString();
        MessageBoxW(NULL, error_text.c_str(), L"AutoWrap()", 0x10010);
        return hr;
    }

    // Allocate memory for arguments...
    VARIANT *pArgs = new VARIANT[cArgs+1];
    // Extract arguments...
    for(int i=0; i<cArgs; i++)
    {
        pArgs[i] = va_arg(marker, VARIANT);
    }

    // Build DISPPARAMS
    dp.cArgs = cArgs;
    dp.rgvarg = pArgs;

    // Handle special-case for property-puts!
    if(autoType & DISPATCH_PROPERTYPUT)
    {
        dp.cNamedArgs = 1;
        dp.rgdispidNamedArgs = &dispidNamed;
    }

    // Make the call!
    hr = pDisp->Invoke(dispID, IID_NULL, LOCALE_SYSTEM_DEFAULT, autoType, &dp, pvResult, NULL, NULL);
    if(FAILED(hr))
    {
        error_text = L"IDispatch::Invoke(\"" + Name + L"\"=%08lx) failed w/err " + QString::number(hr,16).toStdWString();
        MessageBoxW(NULL, error_text.c_str(), L"AutoWrap()", 0x10010);
        return hr;
    }
    // End variable-argument section...
    va_end(marker);
    delete [] pArgs;

    return hr;
};
/////////////////////////////////////////////////////
std::wstring MainWindow::get_cell_item(IDispatch *Cells, int x, int y)
{
    std::wstring cell_item;
    IDispatch *Cell = 0;
    IDispatch *Interior = 0;
    VARIANT result, x_variant, y_variant;

    x_variant.vt = VT_I4;
    x_variant.lVal = x;
    y_variant.vt = VT_I4;
    y_variant.lVal = y;
    AutoWrap(DISPATCH_PROPERTYGET, &result, Cells, L"Item", 2, x_variant, y_variant );
    Cell = result.pdispVal;
    AutoWrap(DISPATCH_PROPERTYGET, &result, Cell, L"Interior", 0 ); // Заливка
    Interior = result.pdispVal;

    AutoWrap(DISPATCH_PROPERTYGET, &result, Cell, L"Value", 0 );
    switch(result.vt)
    {
    case VT_BSTR: //Строка?
        cell_item = result.bstrVal;
        // Отсекаем отпуск "от"
        if(cell_item.length() < 3) cell_item = L"";

        break;
    case VT_R8: // Число?

        if(result.dblVal > 8.0) // Смена 11 часов?
        {
            // Запрос цвета заливки
            // делфи - vVarCell.OlePropertyGet("Interior").OlePropertyGet("ColorIndex");
            AutoWrap(DISPATCH_PROPERTYGET, &result, Interior, L"ColorIndex", 0 );
            // заливка есть?
            if(result.lVal == -4142 || result.lVal == 2)cell_item = L"1";//первая смена
            else cell_item = L"2";//вторая смена

            //cell_item = QString::number(result.lVal).toStdWString();
        }
        else
        {
            cell_item = L"";
        }

        break;
    }

    // Закрасить обработанные ячейки в exel
    x_variant.lVal = 35;
    AutoWrap(DISPATCH_PROPERTYPUT, &result, Interior, L"ColorIndex", 1, x_variant );

    Interior->Release();
    Cell->Release();
    return cell_item;
}
/////////////////////////////////////////////////////

...
Рейтинг: 0 / 0
C++ & Excel
    #38824965
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SashaMercuryЗдравствуйте.
Мне нужно подготовить файл excel для импорта его в таблицу БД. (Кстати, делаете ли вы так ?) Думаю, что мне не составит большого труда написать код vba для анализа документа. Но тут я подумал, а может быть стоит разобраться и сделать на Си. Точнее мне хочется это сделать именно на Си. Как вы считаете, это правильная идея ?

Не стоит.
...
Рейтинг: 0 / 0
C++ & Excel
    #38824998
Фотография SashaMercury
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Всем спасибо :) В целом я до этого дошел через 5 минут после того как подумал про это.
Хотя вот шел по улице вечером, и подумал. Если бы мы могли видеть этот файл как массив строк, причём все ячейки/строка разделены символами ECELL, а каждая строка символами ELINE, то с этим файлом можно было бы работать очень просто. Только для того чтобы мы могли видеть эти файлы так, нужно написать интерфейс для работы с Excel
...
Рейтинг: 0 / 0
17 сообщений из 17, страница 1 из 1
Форумы / C++ [игнор отключен] [закрыт для гостей] / C++ & Excel
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]