HDTenEightyP/NetNews huggingface dataset:
From: bs@alice.att.com (Bjarne Stroustrup)
Newsgroups: comp.lang.c++
Subject: Re: Protected Derived classes.
Date: 3 Sep 92 01:45:12 GMT
Article-I.D.: alice.23623
Organization: AT&T Bell Laboratories, Murray Hill NJ



 > >class D : protected B { /* ...*/ };
 > 
 > This feature was added to the language after the ARM was published.
 > It is discussed in these two books:
 > Bjarne Stroustrup, "The C++ Programming Language", 2nd Edition
 > Stan Lippman, "C++ Primer", 2nd Edition

Actually, it was added while writing the ARM. It is in the ARM grammer
but not discussed further because I (wrongly) assumed people could
deduce the semantics from the rules from protected members.
From: rmartin@thor.Rational.COM (Bob Martin)
Newsgroups: comp.lang.c++
Subject: Re: GOTO, was: Tiny proposal for na
Date: 1 Sep 92 13:31:55 GMT

mat@mole-end.matawan.nj.us writes:

|Bob, I haven't used a goto in at least eight years, except perhaps in
|a toy program to prove that the compiler takes it.  I believe that once
|in that time have toyed with the idea of using one in real code, but
|found a good way without it.

|Goto's may be like titles such as `Empress of India.'  There may
|somewhere be a monarch who still is styled by that title, but nobody rules
|India as an empire.  But I'll be fight for my goto, if need be, with my
|fingernails against the omnidijkstratite juggernaut, and if someone wants
|to call himself Emperor of the North Pole, he's got my permission.

|Goto's are like the write-in vote.  I don't expect ever to want to vote
|for Elmer Plumpudding, but I want that slot on the voting machine.  (I
|realize that the courts in Hawaii have ruled otherwise, but since when
|are the courts a democratic institution?)

Mark:

I completely agree with you.  You have defended the right to use a
goto.  That right should remain inviolate.  (As I said before, I don't
want any software cops.)  But, just becuase we have the right, doesn't
mean that it is wise, or that we should ignore the lessons of the
past.  We also have the right to believe that the earth is flat.

What you have not defended, is the notion that gotos are a legitimate
tool for the experienced programmer.  Or that there are some things
that you just can't do without gotos.  Or that gotos are ok as long as
they are well commented. 

In fact, you haven't used a goto in at least eight years.  Is there
any other major language feature that your have left unused for that
long?  (bitfields perhaps?)  Eight years of non-use is a powerful
indictment.  So I assume that you, too, feel that the use of gotos is
generally unwise, and that the more experienced you are, the less use
you make of them.




--
Robert Martin                        Training courses offered in:
R. C. M. Consulting                       Object Oriented Analysis
2080 Cranbrook Rd.                        Object Oriented Design
Green Oaks, Il 60048 (708) 918-1004       C++
From: cory@enigami.mv.com (Cory Kempf)
Newsgroups: comp.lang.c++
Subject: Re: named loops
Date: 26 Aug 92 15:33:10 GMT
Reply-To: cory@enigami.mv.com
Organization: EnigamI, Inc., Nashua, NH
X-Mailer: uAccess - Macintosh Release: 1.6v1


In article <BEVAN.92Aug23144650@tiger.cs.man.ac.uk> (comp.lang.c++), bevan@cs.man.ac.uk (Stephen J Bevan) writes:
>In article <1992Aug22.171535.29638@taumet.com> steve@taumet.com (Steve Clamage) writes:
>   The main reason, as I see it, is that it adds no functionality and no
>   notational convenience to the language.  Compare:
>
>	   while loop1 (...) { ... break loop1;   ... }
>	   while       (...) { ... goto endloop1; ... } endloop1:

Howabout:

		do { ... } while( ... );
		doLoop: { ... } if(...) goto doLoop;

		while ( ... ) { ... }
		whileLoop: if( ... ) { ... goto whileLoop; }
		anotherWhileLoop: if ( ... ) { ... } 
						else goto endAnotherWhileLoop;
		goto anotherWhileLoop;
		endAnotherWhileLoop:

etc.

When it comes right down to it, almost EVERY language construct can
be implimented via gotos and if statements.  For that matter, data
structures can be implimented via one dimensional arrays.

The reason for NOT doing everything as a if/goto or as an array, is
that the code becomes more self documenting.

There are very few rules for what can be done with a goto.  You can
change the point of execution to almost anywhere.

With a while loop, there are very strict rules: it is a loop that
will cycle as long as the condition holds true.  

These rules are necessary to good programming.  *YOU* may find them
to be a pain, and arbitrary, but when you look at someone else's code,
they can be the only thing that stands between being able to understand
the code and losing your mind.

In general, if there is a specific purpose to a goto, rules that define
it's usage (such as exception handling in a pre-3.0 world), it is
best to hide the goto inside of a structure that provides a rigid
set of rules for it use.  It make the code much easier to understand.

+C



-------------------------------------------------------------
Cory Kempf                    EnigamI, Inc.
cory@enigami.mv.com           ...!decvax!enigami!cory
Annon:	wi.5036@wizvax.methuen.ma.us

"F' cryin' out loud, it's *your* life; shouldn't you at least examine 
your lifestyle values to see if they are really what *you* want."
										--Keith Lim
Newsgroups: comp.lang.c++
From: mat@mole-end.matawan.nj.us
Subject: Re: destruction of temporaries
Summary: Has anyone considered
Organization: :
Date: Mon, 31 Aug 1992 17:27:43 GMT

In article <23585@alice.att.com>, ark@alice.att.com (Andrew Koenig) writes:
> In article <1992Aug28.221841.149034@Cookie.secapl.com> frank@Cookie.secapl.com (Frank Adams) writes:
> 
> > I don't claim to have a complete solution to the problem.  However, for the
> > specific case   c ? a+b : a   where a+b creates a temporary, I would be
> > tempted (as a compiler writer) to always return a temporary: ...
 
> I'm afraid it doesn't solve the problem.  For example, suppose `a' is of type
> const char*, `b' is of type String, and String has one of those problematic
> conversions to const char*.  Now, let's modify your example a tiny bit and
> look at c?(const char*)(a+b):a.
 
> This expression always returns a value of type const char*, but that's not
> where the problem likes: the problem is in the temporary of type String
> yielded by the subexpression a+b.  The value of (const char*)(a+b) is valid
> only so long as that temporary stays around, so any games you play with
> the const char* values themselves won't affect that.

Andy, have we considered the following?

	A temporary that is created has a lifetime equivalent to
	the thing to which it is bound by initialization.  (This
	includes the initialization of function parameters-by-reference
	and the intialization of a  this  pointer.)

	A temporary that is _converted_ (in the C++ sense of the
	word) is considered to be bound to whatever the converted
	value initializes.

	Return values of other sort (from member functions) do not
	affect the lifetime.

I'm sure we have ... but it seems to me this answers most of the
problems.
-- 
 (This man's opinions are his own.)
 From mole-end				Mark Terribile

 mat@mole-end.matawan.nj.us, Somewhere in Matawan, NJ
Newsgroups: comp.lang.c++
From: pat@frumious.uucp (Patrick Smith)
Subject: Re: Destruction of temporaries
Date: Wed, 2 Sep 1992 04:20:30 GMT
Reply-To: uunet.ca!frumious!pat
Organization: None

rmartin@thor.Rational.COM (Bob Martin) writes:
|Some compilers may wish to deal with the deluge of warnings by
|implementing #pragmas which specifically inhibit warnings about the
|creation of aliases as arguments to specific functions.  For example:
|
| #pragma Supress_Alias_Warning String::operator+(const String&, const String&)
|
|This could prevent the compiler from warning about aliases created
|when forming the arguments to functions which are known to be benign.
|The above #pragma would eliminate all the warnings from your example,
|but would still pass warnings about other aliases.
|
|This exposes the alias problem, and puts responsibility for it square
|on the programmer.  It also allows the compiler to destroy temporaries
|at the earliest possible moment.

In my code, and I suspect in most people's, the vast majority of
reference parameters to functions fall into one of two categories.
Either it's a reference to non-const, and can't be called with a
temporary for an argument, or it's a reference to const and it's
perfectly safe to call it with a temporary argument.

So I think it would be a better idea for the programmer to identify
those functions which can't be called with temporaries as arguments,
instead of those which can.  As, for example, in Eric Smith's
proposal upon which I commented in another posting.

One might argue that it is safer to treat functions as 'dangerous
to call with temporary arguments unless otherwise indicated', rather
than 'safe ... unless otherwise indicated'.  But I think this argument
ignores human nature.  If you ask people to flag 19 out of every 20
functions (numbers made up out of thin air) as safe, many of them
will get tired of that and just start ignoring the warning messages.

-- 
Patrick Smith
uunet.ca!frumious!pat
pat%frumious.uucp@uunet.ca
From: tmb@arolla.idiap.ch (Thomas M. Breuel)
Newsgroups: comp.lang.c++
Subject: Re: Garbage Collection for C++
Date: 29 Aug 92 00:13:39 GMT
	<DAVEG.92Aug28004331@synaptx.synaptics.com>
Reply-To: tmb@idiap.ch
Organization: IDIAP (Institut Dalle Molle d'Intelligence Artificielle
	Perceptive)
In-reply-to: daveg@synaptics.com's message of 28 Aug 92 07:43:31 GMT

In article <DAVEG.92Aug28004331@synaptx.synaptics.com> daveg@synaptics.com (Dave Gillespie) writes:

   A C++ garbage collector could make itself destructor-safe using
   the same strategy.  When the GC finds an object is garbage and the
   object has a destructor, it simply calls the destructor and then
   somehow sets a flag showing that the object has effectively been
   converted to raw bits.  The next GC will finally collect the
   object's memory.  I doubt such a flag would be difficult to add;
   allocated objects would need a place to record enough RTTI to find
   the proper destructor anyway.

I'm sorry to be so repetitive, but _please_ understand that there is
no a priori relationship between destructors and finalization.
Destructors are a C++ language concept specifically linked to blocks
and the explicit use of "operator delete". This should not change in
any way. In particular, the GC should not finalize objects by calling
the destructor, since destructors have not written with that use in
mind.

If the user wants the finalization code to call the destructor, he can
do this explicitly.

   But wait---don't most classes have destructors?  Yes, at present,
   but I claim that GC would render most destructors obsolete.
   Destructors tend to be used for cleaning up auxiliary memory, a
   task which would be automated by GC.  Destructors in a C++ with
   GC would be just as rare as finalizations are in Lisp.

Exactly. And for existing classes in which the destructor only
deallocates, there is no need to call it during a GC. On the other
hand, for existing classes in which the destructor, say, destroys a
file descriptor or a window, generally the right thing is to insist
that the programmer continue to call "delete" manually.

					Thomas.
Newsgroups: comp.lang.c++
From: steve@taumet.com (Steve Clamage)
Subject: Re: Protected Derived classes.
Organization: TauMetric Corporation
Date: Wed, 2 Sep 1992 16:20:11 GMT

nandraj@unisql.UUCP (Nandraj Arni) writes:


>     I wanted to know why protected derived classes are not disscussed
>in ARM and not implemented in our GNU C++ compiler. What I am talking 
>about is:

>class B { /*...*/ };

>class D : protected B { /* ...*/ };

This feature was added to the language after the ARM was published.
It is discussed in these two books:
Bjarne Stroustrup, "The C++ Programming Language", 2nd Edition
Stan Lippman, "C++ Primer", 2nd Edition

I don't know which compilers implement the feature.  Scott Meyers, in
"Effective C++", mentions the feature, but says he doesn't know of
a good use for it.  I don't either, although some programmers have
evidently found it helpful.

-- 

Steve Clamage, TauMetric Corp, steve@taumet.com
Vice Chair, ANSI C++ Committee, X3J16
Newsgroups: comp.lang.c++
From: brister@decwrl.dec.com (James Brister)
Subject: Templates and T::*
Organization: DEC Western Software Lab
Date: 26 Aug 92 12:09:27

I'm trying to create a template class that will have a member that is a
pointer to a member function in the class it is parameterizing. I can get
this to work in a non template environment just fine, but under templates
it's causing me grief. Am I doing something wrong? Or is it compiler bug?

Code follows.

Thanks

James

This one works fine. ----------------------------------------------------------

class A {
  public:
    int a ;
    int operator< (const A &rightOper) { return a < rightOper.a ; }
};

class Foo 
{
  private:
    int (A::* compare) (const A &) ;
    
  public:
    Foo (int a, int (A::* func) (const A &) = 0) ;
};

Foo::Foo (int a, int (A::* func) (const A &)) {
    if ( func == 0)
      compare = &A::operator< ;
    else
      compare = func ;
}

main (int argc, char **argv) 
{
    Foo foo (10,&A::operator<) ;
}


This one fails -----------------------------------------------------------------

class A {
  public:
    int a ;
    int operator< (const A & rightOper) { return a < rightOper.a ; }
};


template<class T>
class Foo 
{
  private:
    int (T::* compare) (const T &) ; // error is: Missing ")".
    
  public:
    Foo (int a, int (T::* func) (const T &) = 0) ;// error: Invalid declarator
};

template<class T>
Foo::Foo (int a, int (T::* func) (const T &)) { // error: Parameter has no type or storage class.
    if ( func == 0)
      compare = &T::operator< ; // error: missing ";"
    else                     // error: invalid statement
      compare = func ;
}

main (int argc, char **argv) 
{
    Foo<A> foo (10,&A::operator<) ;
}

------------------------------------------------------------------------------

--
James Brister                                           brister@wsl.pa.dec.com
DEC Western Software Lab., Palo Alto, CA                        decwrl!brister
From: greg@cssc-woll.tansu.com.au (Pengelly Greg)
Newsgroups: comp.lang.c++
Subject: BC 3.1 TV Running slow ?
Date: 19 Aug 92 23:22:24 GMT
Organization: Customised Software Solutions Centre, Wollongong, Australia



Problems with Turbo Vision V3.1

We have a reasonably large TV application developed under BC V3.0
Compiled under BC V3.1 it runs like a dog. 
The application now runs noticably slower. 
Compiler switches and source code have not been changed.

Has anyone else had this problem. Better still can anyone provide the 
solution.  Help from Borland Australia has sofar been nonexistant.

 

_____________________________________________________________________________

Greg Pengelly                    ph (+61 42) 211124    
University of Wollongong  --->   g7909014@uow.edu.au   
Telecom Australia         --->   greg@cssc-woll.tansu.com.au
_____________________________________________________________________________
Newsgroups: comp.lang.c++
From: srinivas@lgc.com (Manapragada Srinivas)
Subject: Ellipsis in template constructors
Followup-To: gnu.g++.bug
Organization: Landmark Graphics Corporation
Date: Thu, 27 Aug 1992 04:17:23 GMT


Hi,

	I am trying to use ellipsis in my template constructors. The problem
	is that g++2.2.2 gives a syntax error for the followin piece of code


		template<class T>
		Vector<T>::Vector( int size ... )
		{
			// Other stuff
		}

	I have also tried 

		template<class T>
		Vector<T>::Vector( int size, ... )
		{
			// Other stuff
		}

	g++ gives the following error

		Vector.icc: In method `Vector<float>::Vector (int, ...)':
		Vector.icc:48: parse error before `)'


	Is this a bug in g++2.2.2 or ellipsis not allowed in constructors?


	I would appreciate any help in this matter.

Thanks in advance,

Srinivas
--
Yonder, beyond the event horizon!
Newsgroups: comp.lang.c++
From: boehm@parc.xerox.com (Hans Boehm)
Subject: Re: Garbage Collection for C++
Organization: Xerox PARC
Date: 28 Aug 92 16:31:55 GMT

daniel.edelson@goudurix.inria.fr (Daniel Edelson) writes:

>In article <DAVEG.92Aug27002517@synaptx.synaptics.com>, daveg@synaptics.com (Dave Gillespie) writes:

>|> Simple, conservative non-moving GC can be added with
>|> minimal effect to the rest of the language, and minimal danger of
>|> toppling it.
>|> 
>|> Dave Gillespie

>While it is an excellent technique, its worst case behavior is 
>unacceptable, e.g., one false pointer into a very large strongly
>connected data structure.... It's valuable and worth using, and 
>significantly better than anything else that's currently available,
>but does not appear to be a panacea. Its presence does not mean
>that we should stop looking for other solutions.

This touches on another serious issue with garbage collection in C++
that I haven't seen discussed - namely that of programming style.
I don't have any experience with large C++ programs.  But I have
seen techniques being advocated that simply don't get along well with
garbage collection of any form.  And they're particularly inappropriate
with conservative collection.  I have no idea whether these are
considered crucial or not.

My standard example is a list implementation that consists of a
"linkable elements" class from which one can inherit (possibly multiple
times) to get a link field added to one's data structure.  This
avoids allocating extra cons-cells for lists.  It also leads to a
situation in which objects contain many link fields for many list
structures simultaneously.  This gives great flexibility in traversing
the structure, most of which is usually never used.  But the garbage
collector can't determine that.  In fact, if you draw some pictures, you
can convince yourself that if you do enough of this, you are likely to
eventually connect everything to everything.

I claim this is a problem no matter what form of garbage collector you
use.  In the nonconservative case, all it takes is some client who
inadvertently hangs on to a tiny component of your data structure, and
the whole thing gets pinned.  Or the compiler allocates a temporary
that it doesn't destroy soon enough.  In the conservative case, you
also have a problem with a false reference to anywhere in the structure.

I don't think this is an insurmountable problem, since the overhead of
using cons-cells is probably pretty minimal in reality (and may be
negative, since you probably didn't really need all those link fields at
once).  But there is a problem with some existing code and programming
styles here.  Interestingly, this seems to be more of a problem with
C++ code than with C code.

Hans-J. Boehm
(boehm@parc.xerox.com)

Newsgroups: comp.lang.c++
From: jss@lucid.com (Jerry Schwarz)
Subject: Re: istrstream
Reply-To: jss@lucid.com (Jerry Schwarz)
Organization: Lucid, Inc.
Date: Wed, 2 Sep 92 18:11:03 GMT

In article <1992Sep1.225259.1533@Warren.MENTORG.COM>, adk@Warren.MENTORG.COM (Ajay Kamdar) writes:
|> Why do istrstream constructors take a char* instead of a const char* ?
|> This either stops me from reading a formatted input string (which I get
|> as a const char*) as an istrstream, or compels me to cast away the const
|> on the string when constructing the istrstream.
|> 

Because strstreambuf only has a char* constructor.  The next question
is obviously why strstreambuf has this limitation, and the answer
is that the interface was designed before you could overload on
"const".  It was an oversight that I never updated the interface.
This oversight has been corrected in the x3j16 proposal.

  -- Jerry Schwarz

Newsgroups: comp.lang.c++
From: rr@world.std.com (Robert I Ransbottom)
Subject: Initialization of external vars
Followup-To: comp.lang.c++
Summary: ???
Organization: The World Public Access UNIX, Brookline, MA
Distribution: usa
Date: Wed, 2 Sep 1992 02:47:54 GMT

// Seems that this should run true. [ C++3.0 ref man 3.4, 3.5, 6.7]
// What am I missing?
//
// code & sample run follows,
// rr@world.std.com

#include <stream.h>

class boolean {
 public:
        int boo;
 public:
  boolean(int a):
         boo((cerr << "initializing boo: " << boo << "\n", !!a)) {
                cerr << "assigning boo: " << boo << "\n";
                boo = !!a;
        }
        operator int () const {
                cerr << "convert boolean to int\n";
                return boo;
        }
};

boolean TRUE = 1;
main()
{
        if (TRUE) {
                cout << "boolean TRUE -- True.\n";
        } else {
                cout << "boolean TRUE -- False.\n";
        }
        if (TRUE.boo) {
                cout << "boolean TRUE.boo-- True.\n";
        } else {
                cout << "boolean TRUE.boo-- False.\n";
        }
}
// $ boolean
// convers. boolean to int
// boolean TRUE -- False.
// boolean TRUE.boo-- False.
From: checker@acf5.NYU.EDU (checker)
Newsgroups: comp.lang.c++
Subject: Re: Callbacks - C++ needs an extension?
Keywords: callback
Date: 2 Sep 92 04:58:58 GMT
Organization: New York University

svan@isy.liu.se (Jonas Svanberg) writes:
>Every class that want to receive direct callbacks must declare an
>own callback class which inherits from some sort of systemclass
>CallBack or whatever. In this derived class one defines a new
>constructor and overloads one memberfunction. These new member-
>functions contain typinginformation about the receiver of the 
>callback, so this will work and it is safe. 
>This can be nicely done with templates I suppose, but it still
>seems like hard work to me.

When the original template classes are done correctly, there is very
little work (either real or conceptual) to be done:

// assume the correct templates are written

class button
{
public:
	button( callback3<int,int,int> &CB );
};

This means button takes a callback that takes three ints.  To call it, I
do this:

specific_callback3<my_class,int,int,int> cb(*this,&my_class::Func);

button B(cb);

All of the derivation and crud is already done in the template classes. 
The two lines above are the only things you ever need to write once the
original templates are debugged (and they're pretty simple, too).  I
should stop to give credit where credit is due, a friend of mine (Rich
Hickey) came up with the template extension to this scheme; the original
used nested classes.

>Is it safe to make the call (obj->*membfun)() when both the obj* (of class
>A) and the membfun* have been casted from respectively:
>1. a pointer to a class derived from A and (the obj*)
>2. a pointer to a member of a class derived from A (the memfun*)
>?

I'd have to see the full declarations, but most of these casting schemes
break badly under multiple inheritance.  There are ways to do it without
casting so they should be used.

Chris
Newsgroups: comp.lang.c++
From: mat@mole-end.matawan.nj.us
Subject: Re: Destruction of temporaries
Organization: :
Date: Tue, 1 Sep 1992 09:22:10 GMT

In article <23598@alice.att.com>, ark@alice.att.com (Andrew Koenig) writes:
> In article <rmartin.715267769@thor> rmartin@thor.Rational.COM (Bob Martin) writes:
 
> > Ideed.  But I think the warning is still useful.
 
> The unfortunate reality is that I have seen a number of development
> projects that have an inflexible rule -- no warnings allowed!  That is,
> they will not allow their people to ship any code that generates warnings.
 
> Thus, giving a compiler warning for a construct is equivalent to
> banning it for those projects.
 
> Warnings had better be right almost all the time.

In general, I applaud such a policy.  It does assume one thing: that for
any code that generates a warning, there is equivalent code that is safe
and maintainable that does not generate the warning and does not require
large-scale structural changes in the program.

From the viewpoint, a warning is the compiler saying `I think you mean
this, but please make your intentions clearer.'
-- 
 (This man's opinions are his own.)
 From mole-end				Mark Terribile

 mat@mole-end.matawan.nj.us, Somewhere in Matawan, NJ