xpcom/string/public/nsTPromiseFlatString.h

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/xpcom/string/public/nsTPromiseFlatString.h	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,106 @@
     1.4 +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
     1.5 +/* vim:set ts=2 sw=2 sts=2 et cindent: */
     1.6 +/* This Source Code Form is subject to the terms of the Mozilla Public
     1.7 + * License, v. 2.0. If a copy of the MPL was not distributed with this
     1.8 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     1.9 +
    1.10 +
    1.11 +  /**
    1.12 +   * NOTE:
    1.13 +   *
    1.14 +   * Try to avoid flat strings.  |PromiseFlat[C]String| will help you as a last
    1.15 +   * resort, and this may be necessary when dealing with legacy or OS calls,
    1.16 +   * but in general, requiring a null-terminated array of characters kills many
    1.17 +   * of the performance wins the string classes offer.  Write your own code to
    1.18 +   * use |nsA[C]String&|s for parameters.  Write your string proccessing
    1.19 +   * algorithms to exploit iterators.  If you do this, you will benefit from
    1.20 +   * being able to chain operations without copying or allocating and your code
    1.21 +   * will be significantly more efficient.  Remember, a function that takes an
    1.22 +   * |const nsA[C]String&| can always be passed a raw character pointer by
    1.23 +   * wrapping it (for free) in a |nsDependent[C]String|.  But a function that
    1.24 +   * takes a character pointer always has the potential to force allocation and
    1.25 +   * copying.
    1.26 +   *
    1.27 +   *
    1.28 +   * How to use it:
    1.29 +   *
    1.30 +   * A |nsPromiseFlat[C]String| doesn't necessarily own the characters it
    1.31 +   * promises.  You must never use it to promise characters out of a string
    1.32 +   * with a shorter lifespan.  The typical use will be something like this:
    1.33 +   *
    1.34 +   *   SomeOSFunction( PromiseFlatCString(aCSubstring).get() ); // GOOD
    1.35 +   *
    1.36 +   * Here's a BAD use:
    1.37 +   *
    1.38 +   *  const char* buffer = PromiseFlatCString(aCSubstring).get();
    1.39 +   *  SomeOSFunction(buffer); // BAD!! |buffer| is a dangling pointer
    1.40 +   *
    1.41 +   * The only way to make one is with the function |PromiseFlat[C]String|,
    1.42 +   * which produce a |const| instance.  ``What if I need to keep a promise
    1.43 +   * around for a little while?'' you might ask.  In that case, you can keep a
    1.44 +   * reference, like so
    1.45 +   *
    1.46 +   *   const nsCString& flat = PromiseFlatString(aCSubstring);
    1.47 +   *     // this reference holds the anonymous temporary alive, but remember,
    1.48 +   *     // it must _still_ have a lifetime shorter than that of |aCSubstring|
    1.49 +   *
    1.50 +   *  SomeOSFunction(flat.get());
    1.51 +   *  SomeOtherOSFunction(flat.get());
    1.52 +   *
    1.53 +   *
    1.54 +   * How does it work?
    1.55 +   *
    1.56 +   * A |nsPromiseFlat[C]String| is just a wrapper for another string.  If you
    1.57 +   * apply it to a string that happens to be flat, your promise is just a
    1.58 +   * dependent reference to the string's data.  If you apply it to a non-flat
    1.59 +   * string, then a temporary flat string is created for you, by allocating and
    1.60 +   * copying.  In the event that you end up assigning the result into a sharing
    1.61 +   * string (e.g., |nsTString|), the right thing happens.
    1.62 +   */
    1.63 +
    1.64 +class nsTPromiseFlatString_CharT : public nsTString_CharT
    1.65 +  {
    1.66 +    public:
    1.67 +
    1.68 +      typedef nsTPromiseFlatString_CharT    self_type;
    1.69 +
    1.70 +    private:
    1.71 +
    1.72 +      void Init( const substring_type& );
    1.73 +
    1.74 +        // NOT TO BE IMPLEMENTED
    1.75 +      void operator=( const self_type& ) MOZ_DELETE;
    1.76 +
    1.77 +        // NOT TO BE IMPLEMENTED
    1.78 +      nsTPromiseFlatString_CharT() MOZ_DELETE;
    1.79 +
    1.80 +        // NOT TO BE IMPLEMENTED
    1.81 +      nsTPromiseFlatString_CharT( const string_type& str ) MOZ_DELETE;
    1.82 +
    1.83 +    public:
    1.84 +
    1.85 +      explicit
    1.86 +      nsTPromiseFlatString_CharT( const substring_type& str )
    1.87 +        : string_type()
    1.88 +        {
    1.89 +          Init(str);
    1.90 +        }
    1.91 +
    1.92 +      explicit
    1.93 +      nsTPromiseFlatString_CharT( const substring_tuple_type& tuple )
    1.94 +        : string_type()
    1.95 +        {
    1.96 +          // nothing else to do here except assign the value of the tuple
    1.97 +          // into ourselves.
    1.98 +          Assign(tuple);
    1.99 +        }
   1.100 +  };
   1.101 +
   1.102 +// We template this so that the constructor is chosen based on the type of the
   1.103 +// parameter. This allows us to reject attempts to promise a flat flat string.
   1.104 +template<class T>
   1.105 +const nsTPromiseFlatString_CharT
   1.106 +TPromiseFlatString_CharT( const T& string )
   1.107 +  {
   1.108 +    return nsTPromiseFlatString_CharT(string);
   1.109 +  }

mercurial