Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.72/18: Рейтинг темы: голосов - 18, средняя оценка - 4.72
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663

Сравнение строк в двух Excel-файлах

18.08.2015, 14:36. Показов 3530. Ответов 13
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Доброго дня. Есть два файла Excel. Как сравнить строку одного файла со строкой другого файла и в зависимости от результата сравнения предпринять те или иные действия? Понятно, что if и циклом. Трудности с лексикой Excel.
Спасибо.
0
Лучшие ответы (1)
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
18.08.2015, 14:36
Ответы с готовыми решениями:

Поиск одинаковых строк в файлах
Доброго дня.Подскажите как реализовать поиск дубликатов строк, в выбранных файлах. К примеру в Memo искомый текст и есть 10 txt...

Удаление пустых строк в текстовых файлах
Дан текстовый файл, в котором встречаются пустые строки. Надо написать программу которая эти пустые строки из текстового файла удалит, и...

Сравнение строк в нескольких файлах excel, копирование несовпадающих строк и их вывод в сводный файл
Добрый день, только только начал разбираться с VBA в excel, поэтому прошу помощи (схожие темы находил, но не смог преобразовать их...

13
управление сложностью
 Аватар для Почтальон
1693 / 1306 / 259
Регистрация: 22.03.2015
Сообщений: 7,545
Записей в блоге: 5
18.08.2015, 15:04
Ну да, циклом бежите по первому файлу и ищите во втором.
Что конкретно не получается ???
1
 Аватар для Dinkin
783 / 556 / 136
Регистрация: 31.05.2013
Сообщений: 3,145
Записей в блоге: 3
18.08.2015, 15:31
Просто циклом не получиться. Верстка файлов может быть совсем разная, но при открытии таблицы будут сходны.
Скорее всего точный результат Вы получите если изначально себе по ячейкам разложите значения (к примеру в тот же TStringGrid) и уж их сравнивать.
PS На форуме масса примеров импорта Excel в TStringGrid
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
18.08.2015, 16:02  [ТС]
Не получается с синхронизацией вариантов первого и второго файла и сравнение.
Чего то не сообразить. Хотел оптимального кода. Боюсь такого понаписать, что долго будет думать и в 10 раз длиннее получится. Пробую, но пока лезут ошибки экселя.
Вообще..
Есть первый файл - в нем на первом листе 500 строк. В диапазоне 1-45 столбец.
Есть второй файл - в нем на первом листе 450 строк. В диапазоне 1-40 столбец.
Задача- если диапазон 1-40 i-ой строки первого файла равен диапазону 1-40 ?-ой строки второго файла,
то диапазон 41-45 i-ой строки первого файла копируем в диапазон 41-45 ?-ой строки второго файла.

Цитата Сообщение от Dinkin Посмотреть сообщение
импорта Excel в TStringGrid
хотел обойтись без гридов - структура файлов почти одинаковая.
0
 Аватар для Dinkin
783 / 556 / 136
Регистрация: 31.05.2013
Сообщений: 3,145
Записей в блоге: 3
18.08.2015, 16:28
Sergey_03, Смотрите это XML верстка, если вы в ней понимаете, то в любом случае придется парсить сами файлы и сравнивать ряд моментов (не совсем приятно рыскать в xml). А если документы как вы описали не большие, то делаете луче импорт в удобный для вас формат в программе и циклом сравниваете. Это сэкономит Вам как время, так и нервы.
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
19.08.2015, 11:53  [ТС]
Написал такое, но не работает. Слишком много итераций. Наверное есть другой алгоритм. Прошу совета.
C++
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
String In9=""; String Out13="";
    for(int i9=0; i9<StringGrid9->RowCount;i9++)
    {
        for(int ii9=0; ii9<35;ii9++)
            {
                In9 += StringGrid9->Cells[ii9][i9];
            }
        for(int i13=0; i13<StringGrid13->RowCount;i13++)
            {
                for(int ii13=0; i13<35;ii13++)
                    {
                        Out13 += StringGrid13->Cells[ii13][i13];
                    }
                 if(In9==Out13)
                     {
                       StringGrid13->Cells[36][i13]=StringGrid9->Cells[36][i9];
                       StringGrid13->Cells[37][i13]=StringGrid9->Cells[37][i9];
                       StringGrid13->Cells[38][i13]=StringGrid9->Cells[38][i9];
                       StringGrid13->Cells[39][i13]=StringGrid9->Cells[39][i9];
                       StringGrid13->Cells[40][i13]=StringGrid9->Cells[40][i9];
                       StringGrid13->Cells[41][i13]=StringGrid9->Cells[41][i9];
                     }
                 Out13="";
            }
        In9="";
    }
0
 Аватар для Dinkin
783 / 556 / 136
Регистрация: 31.05.2013
Сообщений: 3,145
Записей в блоге: 3
19.08.2015, 12:02
Да чет непонятное у Вас сравнение.

Сделал по Вашему условию так (но сам код не проверял, интуитивно что работает)

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
void __fastcall TForm1::Button1Click(TObject *Sender)
{
bool status =true;//указатель того что таблицы равны
 
//теперь начинаем сравнение таблиц
for(int i=1;i<41;++i)
   for(int j=1;j<41;++j)
       if(StringGrid1->Cells[j][i]!=StringGrid2->Cells[j][i])  //не сошлись, значит херово
         {
             status =false;
             break;
         }
//теперь если значения сошлись, то копируем значения
 
if(status)
   {
    StringGrid2->RowCount=StringGrid1->RowCount;
       for(int i=1;i<StringGrid1->RowCount;++i)
        for(int j=1;j<StringGrid1->ColCount;++j)
              StringGrid2->Cells[j][i]!=StringGrid1->Cells[j][i];
 
   }
}
//---------------------------------------------------------------------------
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
19.08.2015, 12:07  [ТС]
Там не так немного.
Там типа такого, только столбцы другие немного-
Цитата Сообщение от Sergey_03 Посмотреть сообщение
Есть первый файл - в нем на первом листе +-500 строк. В диапазоне 1-45 столбец.
Есть второй файл - в нем на первом листе +-450 строк. В диапазоне 1-40 столбец.
Задача- если диапазон 1-40 i-ой строки первого файла равен диапазону 1-40 ?-ой строки второго файла,
то диапазон 41-45 i-ой строки первого файла копируем в диапазон 41-45 ?-ой строки второго файла.
По гридам все распихал.
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33376 / 21500 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
19.08.2015, 12:20
Лучший ответ Сообщение было отмечено BRcr как решение

Решение

Sergey_03, гриды не нужны. Достаточно прочитать содержимое строк (по 40 ячеек) из обоих файлов в два разных StringList-а (ну, или в какие-то другие контейнеры, по желанию), и потом уже проходить по этим контейнерам и сравнивать их содержимое. Как только i-я строка из 1-го контейнера равна j-ой строке из второго - номер строки у тебя есть, просто берешь недостающий кусок строки из первого файла, и пишешь во второй.

Вот так 200 строк из xls-файла читаются меньше, чем за секунду:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
    Variant mExcel = CreateOleObject("Excel.Application"); // Запускаем экземпляр Excel
    mExcel.OlePropertyGet("WorkBooks").OleProcedure("Open", WideString("d:\\test\\1.xls"));
    // mExcel.OlePropertySet("Visible", True); // Делаем экземпляр видимым, с этой строкой - медленнее
 
    Variant mSheet = mExcel.OlePropertyGet("Workbooks").OlePropertyGet("Item", 1).
                            OlePropertyGet("Worksheets").OlePropertyGet("Item", 1);
 
    for(int i = 1; i < 101; i++)
    {
        // AN - 40-ой столбец
        mSheet.OlePropertyGet(WideString("Range"),WideString().sprintf(L"A%d:AN%d", i, i)).OleProcedure(WideString("Select"));
        mExcel.OlePropertyGet("Selection").OleFunction("Copy");
 
        String s = Clipboard()->AsText; // пишешь это в контейнер для последующего сравнения
    }
Сразу (без сохранения) сравнивать будет медленнее, насколько я понимаю. В крайнем случае, чтобы многократно не читать второй файл - его содержимое точно нужно где-то сохранить...
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
19.08.2015, 15:26  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
гриды не нужны. Достаточно.....
Нифига не догнать, как это прикрутить к этому -
Написал
C++
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
void __fastcall TForm1::Button8Click(TObject *Sender)
{
        String In;
 
        Variant app, books, book, sheet;
        app = CreateOleObject("Excel.Application");
        books = app.OlePropertyGet("Workbooks");
        books.OleFunction("Open", WideString(Edit8->Text));
        book = books.OlePropertyGet("item", 1);
        sheet = book.OlePropertyGet("WorkSheets", 4); //номер листа
 
        Variant app2, books2, book2, sheet2, Cell2;
        app2 = CreateOleObject("Excel.Application");
        books2 = app2.OlePropertyGet("Workbooks");
        books2.OleFunction("Open", WideString(Edit9->Text));
        book2 = books2.OlePropertyGet("item", 1);
        sheet2 = book2.OlePropertyGet("WorkSheets", 4);
 
        for(int i=1;i<501;i++)
            {
 
                String Loop= sheet.OlePropertyGet("Cells", i, 4);
                String Adr= sheet.OlePropertyGet("Cells", i, 2);
                for(int i2=1;i2<501;i2++)
                    {
                        String Loop2= sheet2.OlePropertyGet("Cells", i2, 4);
                        String Adr2= sheet2.OlePropertyGet("Cells", i2, 2);
                        if(Loop==Loop2&&Adr==Adr2)
                          {
                            for(int ii=40;ii<46;ii++)
                                {
                                    In=sheet.OlePropertyGet("Cells", i, ii);
                                    sheet2.OlePropertyGet("Cells", i2, ii).
                                    OlePropertySet("Value",WideString(In));
                                }
                          }
                    }
            }
        app.OleProcedure("Quit");
        app.Clear();
        app=NULL;
        book2.OleProcedure("Save");
        app2.OleProcedure("Quit");
        app2.Clear();
        app2=NULL;
        return;
}
работает, но пол часа ждать надо. 250000 итераций - не годится.
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33376 / 21500 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
19.08.2015, 15:56
Цитата Сообщение от Sergey_03 Посмотреть сообщение
Задача- если диапазон 1-40 i-ой строки первого файла равен диапазону 1-40 ?-ой строки второго файла,
то диапазон 41-45 i-ой строки первого файла копируем в диапазон 41-45 ?-ой строки второго файла.
Это твое задание? Зачем тут 250К итераций? Читаешь содержимое второго файла в StringList, как я показал. Потом построчно идешь по содержимому первого файла: прочел i-ю строку, проверил через IndexOf, есть ли она в сохраненном StringList-е, если есть - то читаешь диапазон WideString().sprintf(L"AO%d:AS%d", i, i) и пишешь его во второй файл по тому индексу, который вернул IndexOf... Итого на двух файлах по 500 строк - 1000 итераций. Где 250 тысяч?
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
19.08.2015, 16:04  [ТС]
индекс может быть разный. в разных файлах может сместиться. Максимум в файлах может быть 500 строк. Например
в первом файле их 340, во втором 420. Или в первом 350, во втором 351. До какого то момента может совпадать, потом смещение.Или я опять туплю.
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33376 / 21500 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
19.08.2015, 16:06
Цитата Сообщение от Sergey_03 Посмотреть сообщение
индекс может быть разный
Какой индекс? У тебя что, файлы редактируются в то время, как ты их обрабатываешь? Если нет - то ничего страшного не произойдет. Это рабочий алгоритм.
1
21 / 9 / 4
Регистрация: 15.12.2014
Сообщений: 663
19.08.2015, 17:09  [ТС]
Цитата Сообщение от Sergey_03 Посмотреть сообщение
Нифига не догнать, как это прикрутить к этому -
Цитата Сообщение от volvo Посмотреть сообщение
Вот так 200 строк из xls-файла читаются меньше, чем за секунду:
можно полный вариант - я не понимаю. Гуглю-ищу - каша...
И сравнивать достаточно значения во вторых и четвертых ячейках....

Добавлено через 55 минут
И еще вопрос - мне нужно лист 4 использовать.
Пробую подставить в
C++
1
2
3
4
5
6
7
Variant mExcel = CreateOleObject("Excel.Application"); // Запускаем экземпляр Excel
    mExcel.OlePropertyGet("WorkBooks").OleProcedure("Open", WideString(Edit8->Text));
 
    Variant mSheet = mExcel.OlePropertyGet("Workbooks").OlePropertyGet("Item", 1).
                            OlePropertyGet("Worksheets").OlePropertyGet("Item", 4); 
        String s = Clipboard()->AsText; // пишешь это в контейнер для последующего сравнения
    }
- ошибка эксель
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
19.08.2015, 17:09
Помогаю со студенческими работами здесь

Сравнение строк в двух файлах
Есть два txt файла, надо их сравнить и произвести удаление строк из первого файла, если во втором эти строки присутствуют. Наверное так,...

Сравнение строк в 2х файлах
Условие на фото. BufferedReader reader = new BufferedReader(new InputStreamReader(System.in)); String name1 =...

Сравнение столбцов в двух файлах
Доброго времени суток, задача следующая: есть шаблонный файл с большим количеством элементов и стоблцов, каждая строка соответствует...

Сравнение строк в разных файлах
В данном файле в первой строке кол-во последующих строк,со второй строки- запись в формате &quot;событие_год&quot;. Нужно вывести в...

Сравнение VBA- проектов в двух файлах
Нужна помощь. Есть два файла &quot;.accdb&quot; с формами (две ветки одного проекта) Нужно сравнить их и всё полезное перенести из одного файла в...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
14
Ответ Создать тему
Новые блоги и статьи
Инструменты COM: Сохранение данный из VARIANT в файл и загрузка из файла в VARIANT
bedvit 28.01.2026
Сохранение базовых типов COM и массивов (одномерных или двухмерных) любой вложенности (деревья) в файл, с возможностью выбора алгоритмов сжатия и шифрования. Часть библиотеки BedvitCOM Использованы. . .
Киев стоит - украинская песня
zorxor 28.01.2026
wfWdiRqdTxc О Господи, Вечный, Ты . . . Я помоги, Бесконечный. . . Я прошу Ты. . . Я погибаю, спаси. . . Я прошу Тебя Вечный. . .
Загрузка PNG с альфа-каналом на SDL3 для Android: с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 28.01.2026
Содержание блога SDL3 имеет собственные средства для загрузки и отображения PNG-файлов с альфа-каналом и базовой работы с ними. В этой инструкции используется функция SDL_LoadPNG(), которая. . .
Загрузка PNG с альфа-каналом на SDL3 для Android: с помощью SDL3_image
8Observer8 27.01.2026
Содержание блога SDL3_image - это библиотека для загрузки и работы с изображениями. Эта пошаговая инструкция покажет, как загрузить и вывести на экран смартфона картинку с альфа-каналом, то есть с. . .
влияние грибов на сукцессию
anaschu 26.01.2026
Бифуркационные изменения массы гриба происходят тогда, когда мы уменьшаем массу компоста в 10 раз, а скорость прироста биомассы уменьшаем в три раза. Скорость прироста биомассы может уменьшаться за. . .
Воспроизведение звукового файла с помощью SDL3_mixer при касании экрана Android
8Observer8 26.01.2026
Содержание блога SDL3_mixer - это библиотека я для воспроизведения аудио. В отличие от инструкции по добавлению текста код по проигрыванию звука уже содержится в шаблоне примера. Нужно только. . .
Установка Android SDK, NDK, JDK, CMake и т.д.
8Observer8 25.01.2026
Содержание блога Перейдите по ссылке: https:/ / developer. android. com/ studio и в самом низу страницы кликните по архиву "commandlinetools-win-xxxxxx_latest. zip" Извлеките архив и вы увидите. . .
Вывод текста со шрифтом TTF на Android с помощью библиотеки SDL3_ttf
8Observer8 25.01.2026
Содержание блога Если у вас не установлены Android SDK, NDK, JDK, и т. д. то сделайте это по следующей инструкции: Установка Android SDK, NDK, JDK, CMake и т. д. Сборка примера Скачайте. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru