P
Phil Endecott
Dear All,
For some reason I had got it into my head that std::vector<T>::iterator
and std::basic_string<T>::iterator were certain to be T*. I now see
that this isn't true.
So here's why this matters to me. I have a function that is templated
on an iterator type:
template <typename Iter>
void func(Iter i) { ...... }
A common case is Iter = std::some-container<char>::iterator. For those
containers where the elements are certain to be stored contiguously in
memory (i.e. string and vector, right?), I want to provide an optimised
specialisation: if the elements have suitable alignment, I'll cast to
int* and process them 4 or 8 at a time, rather than one at a time.
(I've already established that this is worthwhile; it's similar to
specialising std::copy to invoke memcpy().)
So, in my mistaken belief that std::vector/basic_string<char>::iterator
was char*, I wrote this:
template <>
void func(char* i) <char*> { ...... }
which of course didn't work.
So presumably I could specifically detect basic_string and vector, and
invoke the char* specialisation on the address of the element:
template <>
void func(std::basic_string<char>::iterator i)
<std::basic_string<char>::iterator> {
func<char*>(&(*i));
}
template <>
void func(std::basic_string<char>::iterator i)
<std::basic_string<char>::iterator> {
func<char*>(&(*i));
}
Question: does that work?
But I'd really like to be able to detect any container, including
user-defined ones, where the elements are stored contiguously in memory.
Is there some way to enable the specialisation in these cases?
Many thanks for any suggestions.
Phil.
For some reason I had got it into my head that std::vector<T>::iterator
and std::basic_string<T>::iterator were certain to be T*. I now see
that this isn't true.
So here's why this matters to me. I have a function that is templated
on an iterator type:
template <typename Iter>
void func(Iter i) { ...... }
A common case is Iter = std::some-container<char>::iterator. For those
containers where the elements are certain to be stored contiguously in
memory (i.e. string and vector, right?), I want to provide an optimised
specialisation: if the elements have suitable alignment, I'll cast to
int* and process them 4 or 8 at a time, rather than one at a time.
(I've already established that this is worthwhile; it's similar to
specialising std::copy to invoke memcpy().)
So, in my mistaken belief that std::vector/basic_string<char>::iterator
was char*, I wrote this:
template <>
void func(char* i) <char*> { ...... }
which of course didn't work.
So presumably I could specifically detect basic_string and vector, and
invoke the char* specialisation on the address of the element:
template <>
void func(std::basic_string<char>::iterator i)
<std::basic_string<char>::iterator> {
func<char*>(&(*i));
}
template <>
void func(std::basic_string<char>::iterator i)
<std::basic_string<char>::iterator> {
func<char*>(&(*i));
}
Question: does that work?
But I'd really like to be able to detect any container, including
user-defined ones, where the elements are stored contiguously in memory.
Is there some way to enable the specialisation in these cases?
Many thanks for any suggestions.
Phil.