简体   繁体   中英

sized arrays as function parameter types in C++

I am using templates for my struct like:

#pragma pack(push, 1)
template <typename T>
struct S
{
   T t;

   inline void Set(const T& val) { t = val; }
}
#pragma pack(pop)

T can be an float, int, short or char[10], char[1] or char[2] (and preferably any length would be great).

While the above seems to work quite nicely for the integral types, I'm having difficulty implementing the char[n] portion in that:

  1. I need to use strncpy or memcpy instead of the assignment operator
  2. Using the above, the compiler complains about the signature (const char[2]& val) and my calling it via s.Set("T").
  3. The interface between S with integral and character types has to be same as it's generic code that is calling them (and it doesn't care what type they are).

You can define template specializations for T in the case of char[10] , etc. Do any issues remain when you do that? But as Mat has already noted, using a string is an approach worth considering.

#include <iostream>

#pragma pack(push, 1)
template <typename T>
struct S
{
   T t;

   inline void Set(const T& val) { std::cout << "general\n"; }
};

template <int len>
struct S<char[len]>
{
   char t[len];

   inline void Set(const std::string& val) { std::cout << "specialization\n"; }
};
#pragma pack(pop)

int main() {

    S<int> a;
    a.Set(10);

    S<char[20]> b;
    b.Set("turkey!");

    return 0;
}

http://codepad.org/X8YVuFja output:

general
specialization

Well, a partial specialization might do the trick:

template <typename T> struct S
{
  T x;
  void set(const T & y) { x = y; }
};

template <typename T, unsigned int N> struct S<T[N]>
{
  T x[N];
  void set(const T (&y)[N]) { std::copy(y, y + N, x); }
};

Usage:

S<char[10]> b;
char c[10] = "Hello";
b.set(c);

Works fine for me: http://codepad.org/03FSqZC6

#pragma pack(push, 1)
template <typename T>
struct S
{
   T t;

   inline void Set(const T& val) {}
};
#pragma pack(pop)

int main() {
    typedef char (carray)[10];  //do you have a line like this?
    S<carray> lhs;
    carray rhs = "HELLO";
    lhs.Set(rhs);
    return 0;
}

Most likely your problem is caused by using the incorrect array type. See my code for an example of a correct typedef.

EDIT:

I just realized this becomes a pain to call Set if you already have a std::string or dynamic array of any sort. Do the template specialization.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM