• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            posts - 9, comments - 0, trackbacks - 0, articles - 0
              C++博客 :: 首頁(yè) :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

            2013年5月17日

            • Make sure operator= is well-behaved when an object is assigned to itself. Techniques include comparing addresses of source and target objects, careful statement ordering, and copy-and-swap.

            • Make sure that any function operating on more than one object behaves correctly if two or more of the objects are the same.

            posted @ 2013-05-17 15:00 魏尚堂 閱讀(149) | 評(píng)論 (0)編輯 收藏

            This is only a convention; code that doesn't follow it will compile. However, the convention is followed by all the built-in types as well as by all the types in  the standard library (e.g., string, vector, complex, tr1::shared_ptr, etc.). Unless you have a good reason for doing things differently, don't.

            posted @ 2013-05-17 12:06 魏尚堂 閱讀(147) | 評(píng)論 (0)編輯 收藏

            base class constructors execute before derived class constructors, derived class data members have not been initialized when base class constructors run. If virtual functions called during base class construction went down to derived classes, the derived class functions would almost certainly refer to local data members, but those data members would not yet have been initialized.Calling down to parts of an object that have not yet been initialized is inherently dangerous, so C++ gives you no way to do it.

            #include <iostream>
            #include <string>
            #include <cstdlib>
            void print(std::string str){std::cout << str<< std::endl;}
            class Transaction {
                public:
                    Transaction()
                    {
                        print("Transaction Constructor");
                        logTransaction();
                    }
                    virtual void logTransaction() const // =0;
                    {
                        print("Transaction Log");
                    }
            };
            class BuyTransaction: public Transaction
            {
                public:
                    BuyTransaction(){   print("BuyTransaction Constructor");}
                    virtual void logTransaction() const
                    {
                        print("BuyTransaction Log");
                    }
            };
            int main()
            {
                BuyTransaction dbc;
                //dbc.logTransaction();
            }
            pure virtual functions cannot link.
            [shangtang@BTSOM-1 study]$ g++ TestT.cpp
            TestT.cpp: In constructor 'Transaction::Transaction()':
            TestT.cpp:14: warning: abstract virtual 'virtual void Transaction::logTransaction() const' called from constructor
            /tmp/ccXFzaHv.o: In function `Transaction::Transaction()':
            TestT.cpp:(.text._ZN11TransactionC2Ev[Transaction::Transaction()]+0x7f): undefined reference to `Transaction::logTransaction() const'
            collect2: ld returned 1 exit status
            virtual function can compile, run, but with surprise result
            [shangtang@BTSOM-1 study]$ ./a.out
            Transaction Constructor
            Transaction Log
            BuyTransaction Constructor

            The only way to avoid this problem is to make sure that none of your constructors or destructors call virtual functions on the object being created or destroyed and that all the functions they call obey the same constraint.

            posted @ 2013-05-17 11:27 魏尚堂 閱讀(212) | 評(píng)論 (0)編輯 收藏

            Depending on the precise conditions under which such pairs of simultaneously active exceptions arise, program execution either terminates or yields undefined behavior. In this example, it yields undefined behavior.
            C++ does not like destructors that emit exceptions!
            #include <iostream>
            #include <vector>
            struct Exception
            {
                Exception(){std::cout << "Exception Constructor" << std::endl;}
                ~Exception(){std::cout << "Exception Destructor" << std::endl;}
            };
            class Widget {
            public:
              ~Widget() {std::cout << "Widget Destructor" << std::endl; throw Exception();
              }        //this might emit an exception
              void print(){std::cout << "print" << std::endl;}
            };
                            
            void doSomething();
            int main()
            {
                doSomething();
            }
            void doSomething()
            {
              std::vector<Widget> v;
              v.push_back(Widget());
              v.push_back(Widget());
              v.push_back(Widget());
              v.push_back(Widget());
              std::vector<Widget>::iterator it = v.begin();
              while(it != v.end())
              {
                std::cout << "end" << std::endl;
                (*it).print();
                it++;
              }
            }
            complie with g++
            [shangtang@BTSOM-1 study]$ ./a.out
            Widget Destructor
            Exception Constructor
            terminate called after throwing an instance of 'Exception'
            Aborted (core dumped)
            There are two primary ways to avoid the trouble.

               1, Terminate the program if catch a exception, typically by calling std::abort (cstdlib)
              2, 
            Swallow the exception if catch a exception, print a log

            posted @ 2013-05-17 10:56 魏尚堂 閱讀(152) | 評(píng)論 (0)編輯 收藏

            2013年5月13日

            1, Declare destructors virtual in polymorphic base classes
            why ? because C++ specifies that when a derived class object is deleted through a pointer to a base class with a non-virtual destructor, results are undefined.What typically happens at runtime is that the derived part of the object is never destroyed

            2, if a class is not intended to be a base class, making the destructor virtual is usually a bad idea. 
            why?  if a class have virtual functions, it has extra overhead(vptr).

            3, In fact, many people summarize the situation this way: declare a virtual destructor in a class if and only if that class contains at least one virtual function

            4,Sometimes, however, you have a class that you'd like to be abstract, but you don't have any pure virtual functions.
            solution: declare pure virtual destructor.
            There is one twist, however you must provide a definition for the pure virtual destructor, or linker will complain.

            5, Not all base classes are designed to be used polymorphically. Neither the standard string type, for example, nor the STL container typesare designed to be base classes at all, much less polymorphic ones.


             
             

            posted @ 2013-05-13 14:45 魏尚堂 閱讀(218) | 評(píng)論 (0)編輯 收藏

            2013年1月24日

            thinking in c++ 有下面的例子,不太理解為什么這個(gè)宏中的條件表達(dá)式在編譯時(shí)就執(zhí)行了,在此作個(gè)記號(hào)

            // A simple, compile-time assertion facility
            #define STATIC_ASSERT(x) \
               do { typedef int a[(x) ? 1 : -1]; } while(0)

            int main()
            {
               STATIC_ASSERT(sizeof(int) <= sizeof(long));  // Passes
               STATIC_ASSERT(sizeof(double) <= sizeof(int)); // Fails 
               return 0;
            }

            posted @ 2013-01-24 10:26 魏尚堂 閱讀(673) | 評(píng)論 (0)編輯 收藏

            2013年1月21日

            template <typename T> class dataList
            {
               public:
                  friend ostream& operator<<(ostream& outStream, const dataList <T> &outList);
            }
            template <typename T> ostream& operator<<(ostream& outStream, const dataList <T> &outList)
            {
               //....
               return outStream;
            }
            int main(int argc, char* argv[])
            {
               dataList <int> testList;
               cout << testList;
            }
            這個(gè)程序員是鏈接不過,
            錯(cuò)誤信息:
             warning: friend declaration âstd::ostream& operator<<(std::ostream&, const dataList<T>&)â declares a non-template function
             note: (if this is not what you intended, make sure the function template has already been declared and add <> after the function name here)
            /tmp/cc9DSuka.o: In function `main':
            undefined reference to `operator<<(std::basic_ostream<char, std::char_traits<char> >&, dataList<int> const&)'
            collect2: ld returned 1 exit status
            錯(cuò)誤原因解釋

            The problem is that the compiler is not trying to use the templated operator<< you provided, but rather a non-templated version.

            When you declare a friend inside a class you are injecting the declaration of that function in the enclosing scope. The following code has the effect of declaring (and not defining) a free function that takes a non_template_test argument by constant reference:

            class non_template_test { friend void f( non_template_test const & ); }; // declares here: // void f( non_template_test const & );

            The same happens with template classes, even if in this case it is a little less intuitive. When you declare (and not define) a friend function within the template class body, you are declaring a free function with that exact arguments. Note that you are declaring a function, not a template function:

            template<typename T> class template_test { friend void f( template_test<T> const & t ); }; // for each instantiating type T (int, double...) declares: // void f( template_test<int> const & ); // void f( template_test<double> const & );  int main() {     template_test<int> t1;     template_test<double> t2; }

            Those free functions are declared but not defined. The tricky part here is that those free functions are not a template, but regular free functions being declared. When you add the template function into the mix you get:

            template<typename T> class template_test { friend void f( template_test<T> const & ); }; // when instantiated with int, implicitly declares: // void f( template_test<int> const & );  template <typename T> void f( template_test<T> const & x ) {} // 1  int main() {    template_test<int> t1;    f( t1 ); }

            When the compiler hits the main function it instantiates the template template_test with type intand that declares the free function void f( template_test<int> const & ) that is not templated. When it finds the call f( t1 ) there are two f symbols that match: the non-template f( template_test<int> const & ) declared (and not defined) when template_test was instantiated and the templated version that is both declared and defined at 1. The non-templated version takes precedence and the compiler matches it.

            When the linker tries to resolve the non-templated version of f it cannot find the symbol and it thus fails.

            What can we do? There are two different solutions. In the first case we make the compiler provide non-templated functions for each instantiating type. In the second case we declare the templated version as a friend. They are subtly different, but in most cases equivalent.

            Having the compiler generate the non-templated functions for us:

            template <typename T> class test  { friend void f( test<T> const & ) {} }; // implicitly

            This has the effect of creating as many non-templated free functions as needed. When the compiler finds the friend declaration within the template test it not only finds the declaration but also the implementation and adds both to the enclosing scope.

            Making the templated version a friend

            To make the template a friend we must have it already declared and tell the compiler that the friend we want is actually a template and not a non-templated free function:

            template <typename T> class test; // forward declare the template class template <typename T> void f( test<T> const& ); // forward declare the template template <typename T> class test { friend void f<>( test<T> const& ); // declare f<T>( test<T> const &) a friend }; template <typename T> void f( test<T> const & ) {}

            In this case, prior to declaring f as a template we must forward declare the template. To declare the ftemplate we must first forward declare the test template. The friend declaration is modified to include the angle brackets that identify that the element we are making a friend is actually a template and not a free function.
            引用自 http://stackoverflow.com/questions/1810753/overloading-operator-for-a-templated-class
            從上面我可以學(xué)到一點(diǎn):
            1, 編譯器匹配方法時(shí)非模板函數(shù)優(yōu)先模板函數(shù)
            2, 友元函數(shù)模板必須提前聲明

            posted @ 2013-01-21 10:48 魏尚堂 閱讀(592) | 評(píng)論 (0)編輯 收藏

            2013年1月17日

            Linux Shell的通配符與正則表達(dá)式 http://blog.csdn.net/chen_dx/article/details/2463495

            posted @ 2013-01-17 14:01 魏尚堂 閱讀(149) | 評(píng)論 (0)編輯 收藏

            2012年11月27日

            Perform every resource allocation (e.g., new) in its own code statement which immediately gives the new resource to a manager object (e.g., auto_ptr).

            This guideline is easy to understand and remember, it neatly avoids all of the exception safety problems in the original problem, and by mandating the use of manager objects it helps to avoid many other exception safety problems as well. This guideline is a good candidate for inclusion in your team's coding standards

            link http://www.gotw.ca/gotw/056.htm

            file I/O http://www.zwqxin.com/archives/cpp/use-sstream.html

            posted @ 2012-11-27 10:03 魏尚堂 閱讀(142) | 評(píng)論 (0)編輯 收藏

            国产精品久久久久无码av| 欧美日韩精品久久久免费观看| 人妻精品久久久久中文字幕69| 久久久老熟女一区二区三区| 国产L精品国产亚洲区久久 | 亚洲AV成人无码久久精品老人| 久久久久久午夜成人影院| 久久99国产精品成人欧美| 日韩久久久久久中文人妻| 精品视频久久久久| 色偷偷久久一区二区三区| 青草久久久国产线免观| 国产产无码乱码精品久久鸭| 伊人久久大香线蕉无码麻豆| 青青青国产成人久久111网站| 中文成人无码精品久久久不卡| av午夜福利一片免费看久久| 亚洲日韩欧美一区久久久久我| 秋霞久久国产精品电影院| 无码国内精品久久人妻蜜桃| 久久人人爽人爽人人爽av| 久久精品国产精品国产精品污| 久久精品免费全国观看国产| 精品久久久久久无码中文野结衣| 亚洲精品乱码久久久久66| 理论片午午伦夜理片久久 | 国产午夜精品久久久久九九| 久久久久亚洲精品天堂| 久久天天躁狠狠躁夜夜96流白浆 | 热综合一本伊人久久精品| 久久久国产精品网站| 精品无码久久久久久尤物| 亚洲伊人久久精品影院| 久久人人爽人人人人爽AV| 区亚洲欧美一级久久精品亚洲精品成人网久久久久 | 久久久久久av无码免费看大片| 久久精品国产影库免费看| 9久久9久久精品| 久久青青草原综合伊人| 91亚洲国产成人久久精品| 99久久免费只有精品国产|