🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: comp.std.c++
Article #1968

Do we need a standard isPointer() function?

#1968
From: Pablo Halpern
Date: Thu, 14 Sep 1995 16:49
86 lines
3551 bytes
I am trying to optimize a template for use with built-in types and
pointers. I have a function that moves objects within or between arrays.
The first cut is simply:

  template <class type>
  void List<type>::move_elems(type *dest, const type *src, int numelems)
  {
    // Copy elements one at a time using type's assignment operator
    while (numelems-- > 0)
      *dest++ = *src++;
  }

This will work for any type with a canonical operator=(). However, this
is not efficient for built-in types and pointers, which are better
copied with the following expression:

  memmove(dest, src, sizeof(type) * numelems);

I was able to specialize the template easily enough for the built-in
types e.g.:

  void List<int>::move_elems(int *dest, const int *src, int numelems)
  {
    memmove(dest, src, sizeof(int) * numelems);
  }

However, this is tedious (I counted 11 built-in types, not counting
const- and volatile-qualified versions) and doesn't work for pointers,
which should also be copied with memmove. What I would like is some
operation which tells me whether a type is a built-in type and/or a
pointer type. An extention to the type_info class something like the
following would help:

  class type_info
  {
    // ...
    int isBuiltin() const;
    int isPointer() const;
  };

So I would write:

  void List<type>::move_elems(type *dest, const type *src, int numelems)
  {
    if (typeid(type).isBuiltin() || typeid(type).isPointer())
      // Copy elements in bulk
      memmove(dest, src, sizeof(type) * numelems);
    else
      // Copy elements one at a time using type's assignment operator
      while (numelems-- > 0)
        *dest++ = *src++;
  }

My first attempt at solving this problem without language extentions was
the following macro:

#define IS_POINTER(T) \
  (typeid(T).name()[strlen(typeid(T).name()) - 1] == '*')

This actually works on the Borland 4.02 compiler for most pointer types
or pointer objects. A set of template functions with a macro could
provide a IS_BUILTIN(T) utility. However, my IS_PTR_TYPE(T) macro does
not work for const of volatile pointers:

  int * const p;
  if (IS_PTR_TYPE(p))
    // This code will not execute

Of course I could extend my macro to call functions that strip off
trailing type qualifiers, whitespace, etc. but:

  1) Is the format of the returned value of type_info::name() standard
     enough for me to depend on it for this purpose?
  2) If so, are macros like IS_POINTER(T) and IS_BUILTIN(T) usefull 
     enough to be added to a standard library file?
  3) Regardless of whether it can be finessed with the preprocessor, 
     do people think the extentions to type_info I propose make sense?
  4) Is there another way to skin this cat?

Thanks.
-------------------------------------------------------------
Pablo Halpern                   phalpern@truffle.ultranet.com
---
[ comp.std.c++ is moderated.  Submission address: std-c++@ncar.ucar.edu.
  Contact address: std-c++-request@ncar.ucar.edu.  The moderation policy
  is summarized in http://dogbert.lbl.gov/~matt/std-c++/policy.html. ]
Technical Details
Message-ID: <439kkn$n81@caesar.ultra.net>
Path: arc1-ca.pugleaf.net!in1.uu.net!bounce-back

Show Full Headers
Complete Article Headers
Path: arc1-ca.pugleaf.net!in1.uu.net!bounce-back
Date: 14 Sep 95 16:49:54 GMT
Approved: fjh@cs.mu.oz.au
From: phalpern@truffle.ultranet.com (Pablo Halpern)
Newsgroups: comp.std.c++
Subject: Do we need a standard isPointer() function?
X-Original-Date: Thu, 14 Sep 1995 16:17:48 GMT
Organization: UltraNet Communications, Inc.
Message-ID: <439kkn$n81@caesar.ultra.net>
X-Newsreader: Forte Free Agent v0.46