not необходимо поместить реализацию в файл заголовка, см. альтернативное решение в конце этого ответа.
В любом случае причина, по которой ваш код не работает, что при создании экземпляра шаблона компилятор создает новый класс с заданным аргументом шаблона. Например:
template
struct Foo
{
T bar;
void doSomething(T param) {/* do stuff using T */}
};
// somewhere in a .cpp
Foo f;
При чтении этой строки компилятор создаст новый класс (назовем его FooInt
), что эквивалентно следующему:
struct FooInt
{
int bar;
void doSomething(int param) {/* do stuff using int */}
}
Следовательно, компилятор должен иметь доступ к реализации методов, чтобы создать экземпляр с аргументом шаблона (в данном случае int
). Если эти реализации не были в заголовке, они не были бы доступны, поэтому компилятор не смог бы создать экземпляр шаблона.
Общим решением для этого является запись объявления шаблона в заголовок файла, затем реализовать класс в файле реализации (например, .tpp) и включить этот файл реализации в конец заголовка.
// Foo.h
template
struct Foo
{
void doSomething(T param);
};
#include "Foo.tpp"
// Foo.tpp
template
void Foo::doSomething(T param)
{
//implementation
}
Таким образом, реализация по-прежнему отделена от объявления, но доступен компилятору.
Другое решение состоит в том, чтобы сохранить реализацию отдельно и явно создать все экземпляры шаблона, которые вам понадобятся:
// Foo.h
// no implementation
template struct Foo { ... };
//----------------------------------------
// Foo.cpp
// implementation of Foo's methods
// explicit instantiations
template class Foo;
template class Foo;
// You will only be able to use Foo with int or float
Если мое объяснение isn ' t достаточно ясно, вы можете взглянуть на C ++ Super-FAQ по этому вопросу .
Я не удержался, чтобы написать пакетный скрипт для выполнения твоей задачи. Данный скрипт называется reshape.bat
, предоставьте входной текстовый файл в качестве аргумента командной строки, например:
reshape.bat "algtest_extract.txt"
Чтобы сохранить выходные данные в другом файле, скажем, algtest_reshaped.txt
, сделайте следующее: [116 ]
reshape.bat "algtest_extract.txt" > "algtest_reshaped.txt"
Вот код (см. Все пояснительные замечания):
@echo off
setlocal EnableExtensions DisableDelayedExpansion
rem // Define constants here:
set "_FILE=%~1" & rem // (file to process; `%~1` means first argument)
set "_COL=3" & rem // (number of columns in the output data)
set "_SEP=," & rem // (separator character for input and output data)
set "_PAD=" & rem // (if defined, fill up last row with empty cells)
rem // Read from file:
< "%_FILE%" call :PROCESS
endlocal
exit /B
:PROCESS
rem // Initialise variables:
set "REST=" & rem // (remaining text string after the first separator)
set "LINE=" & rem // (row collector for line/row to output)
set "IDX=0" & rem // (column counter for output data)
setlocal EnableDelayedExpansion
:READ
rem // Read some text, 1023 characters/bytes at most:
set "STR=" & set /P STR=""
rem // Terminate loop if no more data are available:
if not defined STR goto :END
rem // Precede with potential remainder from previous loop:
set "STR=!REST!!STR!"
:PARSE
rem // Extract everything behind the first separator:
if defined STR set "REST=!STR:*%_SEP%=!"
rem // No separator had been found, so read more text:
if "!REST!"=="!STR!" goto :READ
rem // Extract part in front of first separator:
for /F "delims=%_SEP%" %%I in ("ITEM=!STR!") do set "%%I"
rem // Increment column counter:
set /A "IDX+=1" & if !IDX! lss %_COL% (
rem // Output line/row not yet complete, so go on assembling:
set "LINE=!LINE!%_SEP%!ITEM!"
) else (
rem // Output line/row complete, hence return it:
echo(!LINE:*%_SEP%=!%_SEP%!ITEM!
rem // Reset row collector and column counter:
set "LINE=" & set /A "IDX=0"
)
rem // Keep on parsing using the remainder:
set "STR=!REST!" & goto :PARSE
:END
rem // Return potential remaining data:
if defined _PAD (set /A "IDX=_COL-IDX-1") else (set /A "IDX=0")
set "LINE=!LINE!%_SEP%!REST!"
for /L %%I in (1,1,%IDX%) do set "LINE=!LINE!%_SEP%"
if defined LINE echo(!LINE:*%_SEP%=!
endlocal
В notepad ++ нажмите Ctrl+H
, установите режим поиска в "Regular expression"
, затем используйте шаблон поиска
([^,]+,[^,]+,[^,]+),
и повторите поиск с
\1\n
UPD
используйте шаблон поиска ((?:[^,]+,){500})
, если вы хотите использовать 500 элементов вместо 3. Запятые в конце каждой строки можно заменить с помощью шаблона поиска ,$