2013-05-04 2 views
3

Я пишу класс matrix шаблона, который печатает как файл и std::cout, то есть:функции шаблона для печати Thrust вектора

matrix<float> myMat; 
... 
myMat.cout(...)   // print to std::cout 
myMat.write("out.txt") // print to file 

И разделит общую основную функцию печати, которую я пытаюсь реализовать как шаблон, так как я видел разные примеры, которые используют thrust::copy для записи данных как в std::cout, так и в файлы.

Ниже представлен скелет из того, что я сделал, но он в настоящее время выводит мусор. Может ли кто-нибудь указать на некоторые ошибки Возможно, я сделал? Например, разрешено ли мне проходить std::cout?

template <typename data_T> matrix { 
    ... 

    template <typename out_T> int printTo(out_T &out, ...) { 
     data_T *start = ..., *end = ...; 
     ... 
     thrust::copy(start, end, std::ostream_iterator<data_T>(out, " ")); 
     ... 
    } 

    int cout(...) { 
     ... 
     printTo(std::cout, ...); 
     ... 
    } 

    int write(char* path, ...) { 
     ... 
     std::ofstream file; 
     file.open(path); 
     printTo(file, ...); 
     ... 
    } 
} 

Edit:

  • Изменение к int printTo(std::ostream &out, ...) {...} не решает проблему.
  • Подробнее: Я прочитал данные в матрицу из thrust::device_vector<T>, скажем dvec, и преобразовать его в data_T указатель pvec с помощью thrust::raw_pointer_cast(&dvec[0]) (как библиотека CUBLAS использует сырые указатели). Затем я работаю на pvec, а затем хочу распечатать его.
  • Я пытался печатать из указателя исходного thrust::device_vector непосредственно (т.е. *dvec) и делает работы: thrust::copy((*dvec).begin(), (*dvec).begin() + n ...). Итак, почему я могу копировать только с помощью итераторов *dvec, а не с помощью литографического указателя pvec?
+0

Вам не нужно, чтобы сделать 'printTo' шаблонную функцию. Просто первым аргументом будет ссылка 'std :: ostream'. –

+0

@JoachimPileborg, спасибо - я изменил его на 'int printTo (std :: ostream & out, ...) {...}', как было предложено, но он все равно выводит мусор. Любые другие идеи? – mchen

+0

Как вы храните "данные"? Как вы фактически инициализируете 'start' и' end'? –

ответ

6

Не используйте raw_pointer_cast здесь. Это заставит Thrust думать, что у вас есть указатель на данные на хосте, поэтому ваш код не дает вам то, что вы ожидаете. Я бы ожидал, что ваш код просто потерпит крах.

Чтобы скопировать device_vector к ostream_iterator, просто использовать thrust::copy непосредственно:

thrust::device_vector<float> vec = ... 

thrust::copy(vec.begin(), vec.end(), std::ostream_iterator<float>(std::cout, " ")); 
+0

Большое спасибо @JaredHoberock - как я могу сохранить итератор vec.begin()?Я фактически перебираю фрагменты данных вектора тяги, так как подматрица более крупной матрицы не может храниться смежно в памяти. – mchen

+0

Вы можете использовать 'thrust :: device_vector :: iterator i = vec.begin();' или 'thrust :: device_ptr ptr = vec.data();'. –

+0

Спасибо @JaredHoberock, но что, если я хочу использовать итератор с моим собственным типом шаблона: 'thrust :: device_vector :: iterator i = ...'? Я получаю ошибку компиляции 'expected a ';" 'если я изменяюсь от' 'до' '. – mchen

Смежные вопросы