Delphi excel поиск текста
Репутация: нет
Всего: нет
День добрый. Подскажите каким инструментом Delphi можно организовать поиск в Excel (2007), желательно с примером.
Поиск должен осуществляться ТОЛЬКО по столбцу A Excel, при этом, при нахождении нужного, необходимо записывать данные текущей строки из ячеек B, C в переменные/массив (неважно).
Результатом поиска является МНОЖЕСТВО строк. Хорошо бы если результатом поиска являлись бы строки или конкретные ячейки A101 .
P.S. Перерыл кучу материала ( в том числе книг), нашёл следующее -
Ссылка1 - поиск определяет только найдено (true) или ненайдено (false) - а хочется номер ячейки ( лучше строки) - чегото материального.
Ссылка2 - поиск данных на листе, в конце интересный repeat until которого я непонимаю, может через него можно выйти на нужное мне.
Ссылка3 - тоже поиск данных, который резко оканчивается Find().Activate; что этот активейт, куда он что возвращает, для меня загадка.
На вашем форуме почитал темы интересные про работу с Excel, но тем с подробным решением данной задачи так и не нашёл.
Репутация: 5
Всего: 130
Репутация: нет
Всего: 1
а еще лучше - запиши макрос, который бы делал то, что тебе нужно (имеется ввиду - нажми "запись макроса" и соверши нужные действия), а сгенеренный код транслируй в дельфи. Там же отличный поиск есть.
Репутация: 5
Всего: 130
Цитата(okkonst @ 6.9.2010, 23:34) |
а еще лучше - запиши макрос, который бы делал то, что тебе нужно (имеется ввиду - нажми "запись макроса" и соверши нужные действия), а сгенеренный код транслируй в дельфи. Там же отличный поиск есть. |
Репутация: нет
Всего: нет
Ребят спасиб. С макросами я ещё не работал, если честно то даже ммм не представляю что придётся делать. можете это описать как-то. как придётся транслировать .
А что касается цикла с проверкой каждой ячейки совпадает ли значение (true) то это наверное долго - в файле Excel 200 000 строк. и перебирать в цикле и обращаться к каждой ячейке это жёстко.
P.S. Возможно ли все данные их Excel как-то по-умному рассовать по массивам в Дельфи ? (получается 3 столбца(массива) of String по 200 000) так чтобы вначале программы это заняло секунд 15-20 или меньше. Мне кажется что потом в итоге это съэкономит кучу времени и сил. спасибо за ответы.
Репутация: 15
Всего: 108
Цитата(Dukalys @ 6.9.2010, 20:50 ) |
Ссылка3 - тоже поиск данных, который резко оканчивается Find().Activate; что этот активейт, куда он что возвращает, для меня загадка. |
выделяется найденная ячейка
координаты можно получить дав команды в стиле:
Код |
column:= ExcelWorksheet1.Columns.Column; row:=ExcelWorksheet1.Rows.Row; |
Репутация: нет
Всего: нет
Попробовал .
Итого - не работает.
подробнее:
Выдержки из первоисточника (книги):
1. "Если задана область ячеек и получена ссылка на неё, то количество столбцов будет определяться свойством Count коллекции Columns объекта Range, а количество строк - свойством Count коллекции Rows объекта Range". Доступ ко всем строкам и столбцам листа рабочей книги предоставляют коллекции Rows и Columns объекта ActiveSheet - активного листа рабочей книги.
2. "Мы определились, что ячейка всегда определяется объектами Range или Cells"
Такая многозначность + отсутствие в Delphi предввода методов, свойств (Excel. пусто) для работы с Excel меня загоняет в тупик.
Код |
FindRange := WB.ActiveSheet.Cells.Find(What:=Edit2.Text).Activate; //находит и выделяет |
Form1.Edit3.Text := IntToStr(WB.ActiveSheet.Rows.Row); //ролсрой
Form1.Edit4.Text := IntToStr(WB.ActiveSheet.Columns.Column);
Во всех эдитах значение = 1 (реальное расположение ПРАВИЛЬНО НАЙДЕННОЙ И ВЫДЕЛЕННОЙ ячейки = 'B3'=(2,3))
Методом подбора - получить какое либо свойство из FindRange (типа Row) так и не получилось.
Выкладываю пример программы - теста, с которой работаю. за основу взята криво написанная (в том числе и мной) программа из нета и неудачно адаптирована под поиск координат ячейки.
P.S. есть у когонить идеи по этому поводу . Я в нете коечто нарыл - Ссылко Похоже от туда можно коечто выдернуть, через 2 часика проверю и отпишусь.
Присоединённый файл ( Кол-во скачиваний: 8 )
pr138_1.zip 394,04 Kb
Репутация: 15
Всего: 108
Код |
. Form1.Edit3.Text := E.ActiveCell.Row; Form1.Edit4.Text := E.ActiveCell.Column; . |
Репутация: нет
Всего: нет
Цитата |
. Form1.Edit3.Text := E.ActiveCell.Row; Form1.Edit4.Text := E.ActiveCell.Column; . |
Оргомное спасибо код работает .
Ребят а вот смотрите заметил какую особенность при выполнении метода "Find" для Cells и для Range
Код |
FindRange := WB.ActiveSheet.Cells.Find(What:=Edit2.Text).Activate; |
Выделяет правильную ячейку 3,2
Код |
FindRange := WB.ActiveSheet.Range[Edit1.Text].Find(What:=Edit2.Text).Activate; |
Выделяет 4 ячейку вместо третьей и по выше приведённых свойствам возвращает 4,2
ну наверно можно просто -1 делать от значения Row ? или это особенность какаято ?
Репутация: 15
Всего: 108
Цитата(Dukalys @ 8.9.2010, 14:36 ) |
ну наверно можно просто -1 делать от значения Row ? или это особенность какаято ? |
Репутация: нет
Всего: нет
Несовсем догоняю что имеете ввиду здесь про последовательность (начало поиска - с начала документа или конца ?). результат поиска с начала документа - искомой строки, ссылается на последующую строку, вродебы всё время .
Репутация: 15
Всего: 108
хм. у тебя в приложенном проекте, если не ошибаюсь, было 2 кнопки, где реализовано 2-мя способами поиск, вот я и спрашиваю в какой последовательности запускаешь.
Репутация: нет
Всего: нет
Код |
Function FindValueInCell(ExcelWS : TExcelWorksheet; What : string; var CellsFound : TList) : Boolean; var Found : ExcelRange; Addr, Addr2 : String; Position : TPositionCell; begin Result := False; //Выполняем поиск в пределах используемого дипазона. //Поиск. MatchCase:=False - поиск не зависит от регистра букв. // xlPart - по сопадению // xlWhole - точное Found := ExcelWS.Cells.Find(What, EmptyParam, xlValues, xlWhole, xlByRows, xlNext, False, EmptyParam); if Assigned(Found) then begin Result := True; Addr := Found.Address[True, True, xlA1, EmptyParam, EmptyParam]; Position.Col := Found.Column; Position.Row := Found.Row; CellsFound.Add(Position); repeat Found := ExcelWS.Cells.FindNext(Found); if Assigned(Found) then begin Addr2 := Found.Address[True, True, xlA1, EmptyParam, EmptyParam]; // адрес совпал (круг завершен) if SameText(Addr, Addr2) then Break; |
Position.Col := Found.Column;
Position.Row := Found.Row;
CellsFound.Add(Position);
end;
// выход если не найдено
until not Assigned(Found)
end;
end;
1. Публиковать ссылки на вскрытые компоненты
2. Обсуждать взлом компонентов и делиться вскрытыми компонентами
Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, Rrader, Girder.
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
0 Пользователей: | |
« Предыдущая тема | Delphi: ActiveX/СОМ/CORBA | Следующая тема » |
[ Время генерации скрипта: 0.1370 ] [ Использовано запросов: 21 ] [ GZIP включён ]
P.s.
Весь код процедуры не обязателен. Нужен сам механизм поиска.
Поиск быстрого способа передачи значений Excel-массив-Excel
Всем доброго дня! Не судите строго, так как я только начинаю изучать VB. Пишу программу для.
Поиск в excel
О великие, о могущие и знающие. Помогите пожалуйста. Мне надо составить программу на vba.
Поиск в Excel
Привет всем, вот нашел такую тему но ответа на нее не было. НА данный момент тоже возник такой же.
Mawrat, Спасибо, что не прошел мимо.
Но к сожалению это немножко не то, что хотелось бы увидеть.
Необходимо организовать поиск именно средствами Delphi, а не VBA.
Сам нашел, как это сделать.
Ок, хорошо.
Предлагаю демонстрационный пример с реализацией всех этапов работы с Excel. Реализованы оба способа поиска и замены шаблона.
Прежде, чем экспериментировать с алгоритмом земены шаблона, необходимо последовательно нажать 3 верхние кнопки - произойдёт подключение (запуск) к Excel, создание рабочей книги, создание рабочего листа.
Для завершения работы необходимо нажать либо на кнопку "Закрыть Excel", либо на "Отключиться от Excel". В первом случае Excel будет передана команда на закрытие - Quit, затем произойдёт отключение приложения от Excel. Во втором случае - только отключение приложения от Excel. Сам Excel останется открытым и можно продолжить с ним работу.
Столкнулся с проблемой: нужно найти строку, в которой будут сразу 2 совпадения с разными строками поиска в разных ячейках, при этом искать следует не на конкретном листе, а по всей рабочей книге. Как я это пытаюсь сделать:
И тут, собственно, проблема. Я не совсем понимаю, как работать с типом Pointer. По идее, после условного оператора нужно запустить второй поиск по второй переменной, и, если оба элемента принадлежат одной строке, то вывести всю строку (7 элементов, начиная с ячейки, в которой найдено совпадение со значением переменной code). Однако, я просто не знаю, как это сделать, т.е. не ориентируюсь в полученной системе координат.
При работе с объектами Excel, если не ставится задача взаимодействия с пользователем, из кода следует исключать обращение к ActiveBook, ActiveSheet, а также к объекту Selected. Т. к. это замеляет работу и ведёт к ошибкам.
---
нужно найти строку, в которой будут сразу 2 совпадения с разными строками поиска в разных ячейках, при этом искать следует не на конкретном листе, а по всей рабочей книге.
можно добавить свой код для извлечения нужных значений из найденной строки.
---
Идея кода такая: открываем книгу и запускаем перебор всех листов этой книги. На каждом листе берём используемый диапазон ячеек и внутри него выполняем поиск первого шаблона. Если первый шаблон найден, то в той строке, где мы его нашли, выполняем поиск второго шаблона. Если и второй шаблон найден, то полагаем, что требуемая строка найдена. Далее, если требуется, обрабатываем эту строку, извлекаем из неё нужные данные. Затем продолжаем поиск далее.
---
В представленном коде не добавлена проверка на уже обработанные строки. Т. е. если в одной и той же строке окажется несколько шаблонов №1, то такая строка обнаружится несколько раз. Эту проблему можно устранить так: можно запоминать номер последней найденной строки и отменять повторные нахождения по этому же номеру через: if NumLast = NumCur then . И надо не забывать сбрасывать NumLast при переходе к обработке следующего листа. Т. е.: NumLast := 0; в начале обработки каждого листа.
Имеется приличного размера xls документ (ниже прикреплен аттач) ЛИСТ1
Формата имя/фамилия и тд .
Нужно что бы при поиске определенного текста в xls документа (по 1-2 критериям)
выводилась информация в таблицу StringGrid
очень медленно тащит,в частности просто зависает. да и вывод только 1 ячейки ,а нужна строка.
Искал по форуму похожие темы,видел решение но не те,везде вывод координат
аля "Поиск данных на листе Excel" найдено cell[1:8]
Мне нужно, что бы можно было искать допустим
искать либо пара имя и фамилия
edit1.text:='фамилия'
edit2.text:='Имя'
и возможность сингл (только по фамилии)
и все результаты выводились в таблице stringgrid
Прошу знающих людей помочь с проблемкой.
Delphi 7 + Excel: Поиск по ячейкам
Есть огромный фаил .xlsx, с 58000+ строками Примерно как выглядит: А B C 4 1 текст.
поиск по книге excel в delphi
Други, подскажите как реализовать поиск ячейки по всей книге excel в delphi? Сломал ноги. Не могу.
Поиск в Excel по листам - Delphi
Здравствуйте, мне срочно нужна помощь! Мне нужно написать программу, которая искала бы при вводе в.
Поиск и замена текста в Excel
Доброго времени суток! такая задача возникла: искать слово в книге Excel, которое в edit и менять.
Наибольшую скорость поиска можно достичь с помощью вызова VBA функций: FindFirst() и FindNext(). Делается так:
Mawrat, уважаемый модератор.
а как теперь сделать вывод результат найденного
тоесть если искали "Бобылева" нашло 5 результатов.
и мне бы ети 5 резузьтатов вывести в stringgrid таблицу на форме delphi
тоесть выводит полность строку со всей информацией из ячеек с найденным содержанием.
был бы очень признателен
Добавлено через 4 часа 40 минут
попробывал таким методом, выводит только 1 найденную строчку.
как сделать что бы вывело все найденные
А в строках 64-65 у Mawrat что происходит? Вывод найденной информации в Memo. Замени его на вывод в StringGrid:
Cпасибо,но вы меня наверно не совсем поняли)
сейчас сделаю в скриншотах . что и как)
Только мне нужно чтобы выводите не 1 результат а несколько, как ето показано в мемо.
Картинка в аттаче взгляните пожалуйста.
Все верно лепитса ровно 1 строчка,из найденного результата..
Но при поиске, находит 5 результатов, знаний не хватает по этому вывести все не могу..
Только 1 результат , послужит как пример..
Файл рабочей книги: T:\work\mama\Книг1а1.xls
Искомый текст: "БОБЫЛЕВА".
Найдено соответствие: Cell[7;3].Text = "БОБЫЛЕВА".
Найдено соответствие: Cell[11797;3].Text = "БОБЫЛЕВА".
Найдено соответствие: Cell[24350;3].Text = "БОБЫЛЕВА".
Найдено соответствие: Cell[33435;3].Text = "БОБЫЛЕВА".
Найдено соответствие: Cell[36069;3].Text = "БОБЫЛЕВА".
Найдено соответствий: 5
Найдено соответствие: Cell[7;3].Text = "БОБЫЛЕВА". - данное соответствие вывел
а вот остальные 4 неимею понятия.
Здравствуйте!
Прошу у разбирающихся помощи. Нужен кусок кода с реализацией метода Find для листа Excel. Задача простая: в некоем диапазоне найти ячейку, значение которой равно S, где S - тестовая строка, и поместить номер строки в переменную n. Программа написана, отлажена и нормально работает, но поиск сейчас реализован методом перебора. Претензия пользователя - скорость работы. Кажется мне, что если применить Find, то будет отрабатывать быстрее.
Большое спасибо за ответ! А можно по паре слов по поводу смысла параметров - LookIn:= -4123, LookAt:= 2, SearchOrder:= 1, earchDirection:= 1, MatchCase:= false, SearchFormat:= false - Это чтобы выйти хотя бы на какой-то уровень осознания
Большое спасибо за ответ! А можно по паре слов по поводу смысла параметров - LookIn:= -4123, LookAt:= 2, SearchOrder:= 1, earchDirection:= 1, MatchCase:= false, SearchFormat:= false - Это чтобы выйти хотя бы на какой-то уровень осознания
LookIn - способ поиска в ячейке. Данное значение ищет искомый текст даже в формулах (такой поиск стоит по умолчанию).Например, поиск "мимо" формул - 4163.
LookAt - стандартный параметр, не знаю на что он влияет, и какие еще значения может принимать.
SearchOrder - искать по строкам (можно искать по столбцам, но по умолчанию в поиске стоит по строкам).
SearchDirection - в какую строну идти (вверх документа или вниз). Мы идем вниз, собственно по данной причине перед поиском ставим указатель на первую ячейке.
MatchCase - если true, то ищет полное совпадение искомого текста. Например, в первой ячейке текст 'Чел', а во второй 'Человек'. Если матчкэйс стоит на true, и искомое слово - 'Чел' то он найдет только первое значение. А если false, то оба.
SearchFormat - дополнительный формат поиска в excel'e. С ним не сталкивался, как пользоваться не знаю.
P.S. Если устраивает простой стандартный поиск, то можно оставить только параметры what и after. Остальные не обязательны к заполнению, но лучше все-таки использовать полную конструкцию.
← →_guest_ ( 2013-12-17 13:51 ) [0]
Не могу разобрать текст по столбцам в Excel XP из Delphi XE4. А вообще задача конвертировать из csv в xls (если может кто подскажет другие способы кроме построчного). В бейсике макрос такой:
Columns("A:A").Select
Selection.TextToColumns Destination:=Range("A1"), DataType:=xlDelimited, _
TextQualifier:=xlDoubleQuote, ConsecutiveDelimiter:=False, Tab:=True, _
Semicolon:=False, Comma:=False, Space:=False, Other:=False, FieldInfo _
:=Array(Array(1, 1), Array(2, 1), Array(3, 1), Array(4, 1), Array(5, 1), Array(6, 1), _
Array(7, 1), Array(8, 1), Array(9, 1), Array(10, 1), Array(11, 1), Array(12, 1), Array(13, 1 _
), Array(14, 1), Array(15, 1), Array(16, 1), Array(17, 1), Array(18, 1), Array(19, 1), Array _
(20, 1), Array(21, 1), Array(22, 1), Array(23, 1), Array(24, 1), Array(25, 1), Array(26, 1), _
Array(27, 1), Array(28, 1), Array(29, 1), Array(30, 1), Array(31, 1), Array(32, 1), Array( _
33, 1), Array(34, 1), Array(35, 1), Array(36, 1), Array(37, 1), Array(38, 1), Array(39, 1), _
Array(40, 1), Array(41, 1), Array(42, 1), Array(43, 1), Array(44, 1), Array(45, 1), Array( _
46, 1), Array(47, 1), Array(48, 1), Array(49, 1), Array(50, 1), Array(51, 1), Array(52, 1), _
Array(53, 1), Array(54, 1), Array(55, 1), Array(56, 1), Array(57, 1), Array(58, 1), Array( _
59, 1), Array(60, 1), Array(61, 1), Array(62, 1), Array(63, 1), Array(64, 1), Array(65, 1), _
Array(66, 1), Array(67, 1), Array(68, 1), Array(69, 1), Array(70, 1), Array(71, 1), Array( _
72, 1)), TrailingMinusNu
Пробую так, открывая файл csv, а сохраняя в xls:
.
ExcelApp: TExcelApplication;
ExcelWB: TExcelWorkbook;
ExcelWS: TExcelWorksheet;
FieldInfo: OleVariant;
.
try
ExcelApp.ConnectKind := ckRunningOrNew;
ExcelApp.Connect;
ExcelApp.Workbooks.Add(CSVFileName, LOCALE_USER_DEFAULT);
ExcelWB.ConnectTo(ExcelApp.ActiveWorkbook);
ExcelWS.ConnectTo(ExcelWB.Worksheets[1] as _Worksheet);
ColMax := 72; //столбцов
FieldInfo := VarArrayCreate([0, ColMax], varVariant);
for I := 0 to ColMax do
FieldInfo[i] := VarArrayOf([i, 1]);
ExcelWS.Range["A1", "A100000"].TextToColumns(ExcelWS.Range["A1", "A1"], xlDelimited, xlDoubleQuote, False, True, False, False, False, False, "", FieldInfo, ".", "", True);
ExcelApp.ActiveWorkbook.SaveAs(XLSFileName, EmptyParam, EmptyParam,
EmptyParam, EmptyParam, EmptyParam, xlNoChanges, EmptyParam,
EmptyParam, EmptyParam, EmptyParam, 0, LOCALE_USER_DEFAULT);
Отрабатывает, но изменений нет.
Не могу найти примеров под Excel XP, все только под старые, а похоже много чего изменилось, например, не могу найти Selection чтобы Selection.TextToColumns и так далее. Подскажите, пожалуйста, в чем ошибка в моем коде.
Ega23 © ( 2013-12-17 14:18 ) [1]
Подготавливаешь вариантный массив из своих значений. Потом одним чохом вставляешь:
"
ChDir "D:\"
Workbooks.Open Filename:="D:\test.csv"
ActiveWorkbook.SaveAs Filename:="D:\test.xls", FileFormat:=xlNormal, _
Password:="", WriteResPassword:="", ReadOnlyRecommended:=False, _
CreateBackup:=False
End Sub
_guest_ ( 2013-12-17 15:10 ) [3]
> Ega23 © (17.12.13 14:18) [1]
Речь идет о десятках мегабайт, хотелось бы обойтись средствами самого Excel"а раз уж он это умеет.
> sniknik © (17.12.13 14:21) [2]
> универсальный пример, стартуешь макрос, делаешь "руками".
> смотришь что получилось
Макрос, сделанный "руками", я привел в самом начале, попробовал адаптировать, но не очень удачно. Не нашел: Selection, Columns и не очень разобрался с FieldInfo. В Делфи7 и Excel97 прекрасно отрабатывала связка ExcelWS.Columns[1].Select;
ExcelWS.Selection.TextToColumns;
сейчас не работает, я изменил код - результата не получил, если кто видит ошибку, подскажите.
_guest_ ( 2013-12-17 15:13 ) [4]
Т.е. файл то сохраняется, но без разбивки на столбцы, ошибок при работе не выдает :(
но вообще, нафиг не нужен, см. пример "моего" макроса.
← →_guest_ ( 2013-12-17 15:43 ) [6]
> sniknik © (17.12.13 15:18) [5]
Я далек от мысли, что Вы предлагаете мне поменять расширение файла, так как у меня после отработки Вашего макроса, по большому счету, только это и происходит, из чего заключаю, что преобразование у Вас происходит на этапе открытия файла. Какие настройки у пользователя будут стоять, я не знаю. У меня вот автоматом не преобразовывает, хотя расширение csv/tsv файла должно бы однозначно говорить о его содержимом. Вопрос пока для меня остается открытым.
_guest_ ( 2013-12-17 15:51 ) [7]
Поправочка: с расширением tsv (а в качестве разделителя используется таб) содержимое преобразуется автоматически. Надо полагать, что если разделителем поставить запятую, то и csv откроется правильно. С практической точки зрения, задача решена. Но все-таки на будущее хотелось бы довести и преобразование вручную до ума - может пригодиться, так что пока еще сам поэкспериментирую и подожду, вдруг кто поможет.
← →_guest_ ( 2013-12-17 15:59 ) [8]
Кроме того разделителем может оказаться и какой-либо другой символ. Так что на расширение файла полагаться наверно не стоит. По хорошему то надо бы пойти посмотреть biff, но что-то мне подсказывает, что это надолго, а со временем - не очень.
← →_guest_ ( 2013-12-17 17:10 ) [9]
Если кому интересен работающий вариант, то вот он:
ExcelWS.Range["A1", "A1"].EntireColumn.TextToColumns(ExcelWS.Range["A1", "A1"],
xlDelimited, xlDoubleQuote, False, True, False, False, False, False, EmptyParam,
null, ".", EmptyParam, True);
Чем EmptyParam лучше чем ""(пустая строка) в качестве ThousandsSeparator я не понимаю, но очевидно лучше :) я с вариантами почти не сталкиваюсь. С null тоже работает.
← →sniknik © ( 2013-12-17 18:30 ) [10]
> хотя расширение csv/tsv файла должно бы однозначно говорить о его содержимом.
csv не однозначный формат, с другой стороны то в каком виде читать настраивается, для примера полная (не уверен, тоже из макроса, что поставило то поставило) форма открытия
Workbooks.OpenText Filename:="D:\test.csv", Origin:=1251, StartRow:=1, _
DataType:=xlDelimited, TextQualifier:=xlDoubleQuote, ConsecutiveDelimiter _
:=False, Tab:=False, Semicolon:=False, Comma:=True, Space:=False, _
Other:=False, FieldInfo:=Array(Array(1, 1), Array(2, 1), Array(3, 1), Array(4, 1)) _
, TrailingMinusNumbers:=True
> Для csv существует спецификация
а ты думаешь откуда я свои знания почерпнул? именно в спецификации (справке excel) и написано -
Format - Должен иметь одно из следующих значений: «TabDelimited», «CSVDelimited», «Delimited» () или «FixedLength». Разделителем для формата «Delimited» может служить любой одиночный символ кроме символа прямых кавычек (").
sniknik © ( 2013-12-18 10:36 ) [15]
+
> кроме символа прямых кавычек (").
и его можно, просто до этого сменить TextDelimiter.
_guest_ ( 2013-12-18 11:12 ) [16]
> sniknik © (18.12.13 10:17) [14]
> sniknik © (18.12.13 10:36) [15]
Да я все это прекрасно понимаю. И код Ваш рабочий и спасибо еще раз за него. Я и хотел подчеркнуть возможные нюансы в работе с csv, что просто открытие файла в txcel"е не гарантирует его преобразования, это зависит от используемого разделителя. Меня как раз позабавило, что я переименовал расширение в tsv и тут же все заработало. Т.е. MS следует формальной логике, отталкиваясь от расширения.
Читайте также: