Форум программистов, компьютерный форум, киберфорум
Наши страницы
Delphi для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 5.00/4: Рейтинг темы: голосов - 4, средняя оценка - 5.00
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
1

Не умею открывать файлы, найденные "FindFirst"

19.05.2015, 15:48. Просмотров 720. Ответов 19
Метки нет (Все метки)

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

Для выбора папки использовал урок : http://valeev.org.ru/index.php?art=33
Для поиска файлов по маске (расширению) : http://www.cyberforum.ru/post492745.html

Delphi
1
2
3
4
... // кусочек необходимого кода
    if ExtractFileExt(Dir + SearchRec.Name) = EXT then
         Memo1.Lines.Add(Dir + SearchRec.Name);
...
Умею лишь загружать пути файлов в Memo.

Вопрос: можно ли найденные файлы отправлять на обработку к функциям?
Один добрый человек ранее помог реализовать с помощью OpenDialog:
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//Диалог открытия файлов.
  Od := OpenDialog1; //OpenDialog1 уже должен быть на форме.
  //Разрешаем множественный выбор файлов.
  Od.Options := Od.Options + [ofAllowMultiSelect];
  //Начальная установка директория в диалоге.
  //ParamStr(0) - полный путь исполняемого файла программы.
  //ExtractFilePath(ParamStr(0)) - директорий, в котором расположен исполняемый файл программы.
  if Od.InitialDir = '' then
    Od.InitialDir := ExtractFilePath(ParamStr(0));
  //Запуск диалога.
  if not Od.Execute then
    Exit;
  //Перебор выбранных файлов.
  for i := 0 to Od.Files.Count - 1 do
    if FileExists(Od.Files[i]) then //Если файл существует.
    begin
           Xls_Open_F1 (Od.Files[i], StringGrid1, StringGrid2);
           Xls_Save_F1 (Od.Files[i], StringGrid1, StringGrid2);
   end; 
...
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
19.05.2015, 15:48
Ответы с готовыми решениями:

В каждом слове текста замените "а" на букву "е", если "а" стоит на четном месте, и заменить букву "б" на сочетание "ак",
В каждом слове текста замените "а" на букву "е", если "а" стоит на четном...

Из слов "Работа", "крест", "тон" составить фразу "Кто не работает, тот не ест" и определить ее длину
Из слова "Работа","крест","тон" составить фразу:"Кто не работает, тот не ест" и...

На форме располагаются компоненты: редактор Edit; линейка ScrollBar; радионабор с опциями "Цветы", "Деревья", "Рыбы", "Звери"
Доброго времени суток, 2 курс 2 семестр, пришли, препод раздал задачи, сказал...

Тысячные числа исправлять к примеру с "1200" на "1 200", "12000" на "12 000" и т.д
Собственно числа исправлять к примеру с "1200" на "1 200", "12000" на "12 000",...

В слове Х перед каждой буквой "к", которой предшествует буква "с", вставить букву "н"
Привет всем) вот условие задачи:В слове Х перед каждой буквой "к", которой...

19
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
19.05.2015, 16:40 2
Для выбора папки используй перегруженную SelectDirectory, чтобы её использовать в uses пропиши FileCtrl;
Далее если версия ХЕ2+ то для поиска используй TDirectory.GetFiles с нужными параметрами.
А если старая версия, то используй TSearcRec и в параметрах сразу укажи искомое расширение. Зачем делать лишнюю проверку?
FindFirst(Dir + '*.xls', faAnyFile, SearchRec)
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
19.05.2015, 17:49  [ТС] 3
FaTaL-CS Спасибо за отзывчивость!
Версия старая, Delphi 7.
Поиск я попозже улучшу, у меня не получается использовать найденные файлы. Допустим мы нашли C:\test.xls и C:\home\111.xls, то далее мне бы хотелось вызвать их в процедуру Xls_Open_F1, а в интернете много примеров как только записать найденные файлы (пути файлов) в Listbox, Memo и т.д.
Попробовал сделать:
Delphi
1
2
3
4
5
if ExtractFileExt(Dir + SearchRec.Name) = EXT then
  begin
           Xls_Open_F1 (Dir + SearchRec.Name, StringGrid1, StringGrid2);
           Xls_Save_F1 (Dir + SearchRec.Name, StringGrid1, StringGrid2);
   end;
вышло ужасно и бестолково. Все из-за незнания и малого кол-ва примеров с FindFirst, где только показывается записи в Memo как выше по ссылкам.
0
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
19.05.2015, 18:10 4
Ну тогда кидайте полностью код и что Вам нужно сделать. А то я что-то понять не могу до конца.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
19.05.2015, 21:11  [ТС] 5
Цитата Сообщение от FaTaL-CS Посмотреть сообщение
Ну тогда кидайте полностью код и что Вам нужно сделать. А то я что-то понять не могу до конца.
мне не понятно, как в :
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
if FindFirst(Dir + '*.*', faAnyFile, SearchRec) = 0 then
    repeat
      if (SearchRec.Name = '.') or (SearchRec.Name = '..') then
        Continue;
      if (SearchRec.Attr and faDirectory) <> 0 then
        FindIt(Dir + SearchRec.Name)
      else
    if ExtractFileExt(Dir + SearchRec.Name) = EXT then
         l.Items.Add(Dir + SearchRec.Name);
         if ExtractFileExt(Dir + SearchRec.Name) = EXT then
 
            list.Items.Add(ChangeFileExt(searchrec.Name,''));
    until
      FindNext(SearchRec) <> 0;
  FindClose(SearchRec);
  end;
вместо
Delphi
1
  list.Items.Add(ChangeFileExt(searchrec.Name,''));
вызвать функцию
Delphi
1
Xls_Open_Ivanov (OpenDialog, StringGrid1, StringGrid2);
Добавлено через 1 минуту
то бишь найденные файлы передать на обработку, а не запись в листы или Memo ...
0
northener
пофигист широкого профиля
3423 / 2323 / 630
Регистрация: 15.07.2013
Сообщений: 13,742
19.05.2015, 21:55 6
Цитата Сообщение от Пётр Нефедов Посмотреть сообщение
то бишь найденные файлы передать на обработку, а не запись в листы
Ты сначала найди все нужные файлы и запиши их имена в стринглист, а потом передай этот список в процедуру обработки файлов. Так будет правильнее.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
19.05.2015, 23:00  [ТС] 7
Цитата Сообщение от northener Посмотреть сообщение
передай этот список в процедуру обработки файлов
Вот подскажите, пожалуйста, как будет выглядеть функция Что будет вместо OpenDialog в :
Delphi
1
Xls_Open_Ivanov (OpenDialog, StringGrid1, StringGrid2);
0
northener
пофигист широкого профиля
3423 / 2323 / 630
Регистрация: 15.07.2013
Сообщений: 13,742
20.05.2015, 00:50 8
Цитата Сообщение от Пётр Нефедов Посмотреть сообщение
Вот подскажите, пожалуйста, как будет выглядеть функция Что будет вместо OpenDialog в :
Код Delphi
1
Xls_Open_Ivanov (OpenDialog, StringGrid1, StringGrid2);
Я не знаю что будет "вместо" в какой-то мне совершенно неизвестной процедуре Xls_Open_Ivanov
Но если бы я писал процедуру обработки этих файлов, я бы написал процедуру типа
Delphi
1
procedure TMyForm.ProcessingFiles(Sl: TStrings; ...);
Добавлено через 4 минуты
P.S.
Исторически не люблю изменять файлы найденные циклом FindFirst-FindNext внутри этого цикла. Во времена MS DOS'а нарывался на неприятности.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
20.05.2015, 08:20  [ТС] 9
Цитата Сообщение от northener Посмотреть сообщение
совершенно неизвестной процедуре Xls_Open_Ivanov
Примерно как здесь:
Delphi
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
procedure Xls_Open_(XLSFile:string; Grid:TStringGrid);
 const
  xlCellTypeLastCell = $0000000B;
var
  ExlApp, Sheet: OLEVariant;
  i, j, r, c:integer;
begin
  //создаем объект Excel
  ExlApp := CreateOleObject('Excel.Application');
 
  //делаем окно Excel невидимым
  ExlApp.Visible := false;
  //открываем файл XLSFile
  ExlApp.Workbooks.Open(XLSFile);
 
  //создаем объект Sheet(страница) и указываем номер листа (1)
  //в книге, с которого будем осуществлять чтение
  Sheet := ExlApp.Workbooks[ExtractFileName(XLSFile)].WorkSheets[1];
  //активируем последнюю ячейку на листе
  Sheet.Cells.SpecialCells(xlCellTypeLastCell, EmptyParam).Activate;
 
    // Возвращает номер последней строки
    r := ExlApp.ActiveCell.Row;
    // Возвращает номер последнего столбца
    c := ExlApp.ActiveCell.Column;
 
    //устанавливаем кол-во столбцов и строк в StringGrid
    Grid.RowCount:=r;
    Grid.ColCount:=c;
    //считываем значение из каждой ячейки и копируем в нашу таблицу
     for j:= 1 to r do
       for i:= 1 to c do
         Grid.Cells[i-1,j-1]:= sheet.cells[j,i];
 //закрываем приложение Excel
 ExlApp.Quit;
 //очищаем выделенную память
 ExlApp := Unassigned;
 Sheet := Unassigned;
end;
А вызов идет при нажатии на кнопку с функцией OpenDialog
Delphi
1
Xls_Open_Ivanov (OpenDialog, StringGrid1, StringGrid2);
0
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
20.05.2015, 11:15 10
Ну например сделай так:
Delphi
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
var
  sl  : TStringList;
// Процедура поиска файлов по расширению
procedure FindFiles (Dir, EXT : string);
var
  SearchRec  : TSearchRec;
begin
  if FindFirst(Dir + '*.*', faAnyFile, SearchRec) = 0 then
    repeat
      if (SearchRec.Name = '.') or (SearchRec.Name = '..') then
        Continue;
      if (SearchRec.Attr and faDirectory) <> 0 then
        FindFiles(Dir + SearchRec.Name + '\', EXT)
      else
    if ExtractFileExt(Dir + SearchRec.Name) = EXT then
         sl.Add(Dir + SearchRec.Name);
    until
      FindNext(SearchRec) <> 0;
  FindClose(SearchRec);
end;
 
procedure TForm1.Button1Click(Sender: TObject);
var
  i : integer;
begin
  sl := TStringList.Create;
  FindFiles ('Папка в которой надо искать\', '.xls');
  for i:=0 to sl.Count - 1 do
    Xls_Open_(sl.Strings[i], Ваш_TStringGrid);
  sl.Free;
end;
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
20.05.2015, 19:03  [ТС] 11
Цитата Сообщение от FaTaL-CS Посмотреть сообщение
Ну например сделай так:
Спасибо, но работает только:
Delphi
1
2
3
4
5
6
7
8
9
10
procedure TForm1.Button1Click(Sender: TObject);
var
  i : integer;
begin
  sl := TStringList.Create;
 // FindFiles ('Папка в которой надо искать\');
  for i:=0 to sl.Count - 1 do
    Xls_Open_(sl.Strings[i], Ваш_TStringGrid);
  sl.Free;
end;
'.xls' пришлось убрать, а FindFiles не вызывается - ничего не происходит. Оставил свою поисковую процедуру.
Есть еще вопрос: как сделать поиск не только файлов '.xls', но и чтобы название файлов, к примеру, при этом начиналось на 'Петров_' и далее произвольные символы?
0
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
20.05.2015, 21:02 12
Цитата Сообщение от Пётр Нефедов Посмотреть сообщение
Спасибо, но работает только:
Застрелите меня!!!
Я не пойму что Вам надо? Конечно не будет работать FindFiles если Вы его закоментировали!
Я же Вам написал полностью рабочий код, который ищет файлы Excel и передаёт их в Вашу процедуру.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
20.05.2015, 21:18  [ТС] 13
Цитата Сообщение от FaTaL-CS Посмотреть сообщение
Конечно не будет работать FindFiles если Вы его закоментировали!
Я не тупой, закомментировал, потому что не работает эта строка.
Delphi
1
FindFiles ('Папка в которой надо искать\', '.xls');
Ошибка "[Error] Unit1.pas(1725): Too many actual parameters"
Без ".xls" компилятор не ругается, но тогда не срабатывает ваша функция FindFiles
0
northener
пофигист широкого профиля
3423 / 2323 / 630
Регистрация: 15.07.2013
Сообщений: 13,742
20.05.2015, 23:06 14
Цитата Сообщение от Пётр Нефедов Посмотреть сообщение
Ошибка "[Error] Unit1.pas(1725): Too many actual parameters"
Неправильно скопировал код из #10
0
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
21.05.2015, 11:00 15
Пётр Нефедов, Скопируй полностью мой код и будет тебе счастье.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
21.05.2015, 22:14  [ТС] 16
Цитата Сообщение от FaTaL-CS Посмотреть сообщение
Скопируй полностью мой код и будет тебе счастье.
Я прошу прощение за поспешность моих выводов, так как очень спешил проверить код и словил ошибки, сейчас же удалось запустить без ошибок, но тогда "отваливается" функция выбора директории. Пока решаю проблему.

Скажите еще, пожалуйста: можно ли для критерия поиска кроме расширения (.xls) указать часть имени файла? Допустим "если файл XLS" и "имя файла начинается на Петров_", то ... "Иванов_" то ... или лучше рассматривать список найденных файлов, и из него выбирать нужные? Но как тогда организовать такой метод?
0
northener
пофигист широкого профиля
3423 / 2323 / 630
Регистрация: 15.07.2013
Сообщений: 13,742
22.05.2015, 01:10 17
Цитата Сообщение от Пётр Нефедов Посмотреть сообщение
Скажите еще, пожалуйста: можно ли для критерия поиска кроме расширения (.xls) указать часть имени файла? Допустим "если файл XLS" и "имя файла начинается на Петров_", то ... "Иванов_" то ...
Не путай критерий поиска с критерием анализа того, что найдено поиском.
И не надо поиск скрещивать с обработкой. Вполне можешь получить "конец света".

Ещё раз. Сначала найди, потом анализируй и обрабатывай.
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
22.05.2015, 11:11  [ТС] 18
Цитата Сообщение от northener Посмотреть сообщение
Ещё раз. Сначала найди, потом анализируй и обрабатывай.
Спасибо за совет)
Я переживаю и тороплюсь, отсюда глупые ошибки.
Сделал поиск с помощью кода FaTaL-CS , выбор директории выбрал как в уроке по ссылке выше. Найденный правда список записал в Memo, и там уже смотрю каждую строку и вхождение подстроки:
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
procedure TForm1.Button3Click(Sender: TObject);
var
  i,j : Integer;
  Od : TOpenDialog;
  sFolder,find: String;
begin
if GetFolderDialog(Application.Handle, 'Выберите папку', sFolder) then
    FindFiles(sFolder);
 
find := 'Петров'; // часть имени файла
  for i := 0 to Memo1.Lines.Count-1 do
 
  If Pos(find, Memo1.Lines[i])>0 then
  begin
    Memo1SelStart := Pos(find,Memo1.Lines[i])-1;
           Xls_Open_Excel (Memo1.Lines[i], StringGrid1, StringGrid2);
           Xls_Save_Excel (Memo1.Lines[i], StringGrid1, StringGrid2);
  end;
Прошу прощения за ошибки, тороплюсь(

Не по теме:

Расписал как работает, так как вдруг в будущем кому-нибудь пригодится сообщение/тема.

0
FaTaL-CS
70 / 70 / 23
Регистрация: 14.10.2013
Сообщений: 527
22.05.2015, 14:38 19
Меня заинтересовало, что делают эти 2 процедуры?
Delphi
1
2
Xls_Open_Excel (Memo1.Lines[i], StringGrid1, StringGrid2);
           Xls_Save_Excel (Memo1.Lines[i], StringGrid1, StringGrid2);
Понятно что сначала из файла заполняются Гриды, но что потом сохраняется?
0
Пётр Нефедов
5 / 5 / 2
Регистрация: 04.10.2010
Сообщений: 206
22.05.2015, 15:31  [ТС] 20
Цитата Сообщение от FaTaL-CS Посмотреть сообщение
но что потом
Сначала из Excel в Grid, потом из Grid в новый файл Excel.
0
22.05.2015, 15:31
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
22.05.2015, 15:31

Дана строка. Заменить все буквы "м" на "н". Заменить все вхождения сочетаний букв "про" на "нет"
2.Дана строка. 1) Заменить все буквы м на н. 2) Заменить все вхождения...

Замените в слове Х все буквы "а" на сочетание "ку", а сочетание "ку" на букву "б"
Написать программу, заменяющую в слове Х все буквы &quot;а&quot; на сочетание &quot;ку&quot;, а...

Работа с компонентами "TDateTimePicker", "TMonthCalendar" и "TCalendar"
Всем привет, помогите пожалуйста разобраться с этими вопросами... 1. Как...


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

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru