comp.lang.c++@googlegroups.com | Google Groups | ![]() |
Unsure why you received this message? You previously subscribed to digests from this group, but we haven't been sending them for a while. We fixed that, but if you don't want to get these messages, send an email to comp.lang.c+++unsubscribe@googlegroups.com. |
- What is your preferred Linux "distro" for C++ development? - 1 Update
- Arrays and C++ - 4 Updates
- First to learn C if learning C++? - 13 Updates
- Announcement of new C++11 library to handle measures - 3 Updates
- Correct vesion (Re: Clone an object with an abstract base class) - 4 Updates
Robert Hutchings <rm.hutchings@gmail.com>: Oct 12 01:13PM -0500 Some people strongly prefer Slackware.... |
arnuld <sunrise@invalid.address>: Oct 12 05:26PM AIM: To understand why "arrays of int/float" and "arrays of char" behave differently in C++ #include <iostream> int main() { int arr1[] = {10,11,12}; char arr2[] = {'a','b','c'}; double arr3[] = {0,10, 0.11, 0.12}; const char* str = "comp.lang.c++"; const wchar_t* alpha = L"first line" "Second Line"; std::cout << "arr1 = " << arr1 << std::endl; std::cout << "arr2 = " << arr2 << std::endl; std::cout << "arr3 = " << arr3 << std::endl; std::cout << "str = " << str << std::endl; std::wcout << "alpha = " << alpha << std::endl; return 0; } ========================= OUTPUT ================================ [arnuld@arch64 c++]$ g++ -ansi -pedantic -Wall -Wextra arrays.cpp [arnuld@arch64 c++]$ ./a.out arr1 = 0x7fffffffe960 arr2 = abc arr3 = 0x7fffffffe930 str = comp.lang.c++ alpha = first lineSecond Line [arnuld@arch64 c++]$ An array name is converted to pointer to its first element. arr1 and arr3 (1st and 3rd wariable) are arrays of int and float respectively and they behave accordingly to this rule but arr2 and str (2nd and 4th variables) do not. Why ? alpha (5th variable) has its initialization spread across 2 lines. I need to give L only on first line and not on 2nd line. Is this assumption correct ? -- arnuld http://lispmachine.wordpress.com/ |
Victor Bazarov <v.bazarov@comcast.invalid>: Oct 12 01:37PM -0400 On 10/12/2014 1:26 PM, arnuld wrote: > (1st and 3rd wariable) are arrays of int and float respectively and they > behave accordingly to this rule but arr2 and str (2nd and 4th variables) > do not. Why ? When you ask "why", you presume that your conclusion is correct. It isn't. All arrays behave according to the rule. > alpha (5th variable) has its initialization spread across 2 lines. I > need to give L only on first line and not on 2nd line. Is this assumption > correct ? Yes. Concatenation of the adjacent string literals is done prior to the syntactic analysis of the code. V -- I do not respond to top-posted replies, please don't ask |
Barry Schwarz <schwarzb@dqel.com>: Oct 12 10:45AM -0700 >(1st and 3rd wariable) are arrays of int and float respectively and they >behave accordingly to this rule but arr2 and str (2nd and 4th variables) >do not. Why ? Actually they do. The difference is how the compiler generates code for the overloaded operator <<. When the right operand has type pointer to char, the generated code treats the address as the start of a C style string (similar to using %s in printf). When the operand has type pointer to "object that cannot be a string," the generated code treats it the same as using %p in printf. >alpha (5th variable) has its initialization spread across 2 lines. I >need to give L only on first line and not on 2nd line. Is this assumption >correct ? Yes. It only looks like the initialization is spread across two lines. Two string literals separated only by white space are merged into a single string literal in one of the early compilation phases. Since '\n' and ' ' are both white space characters, your initialization of alpha is processed as L"first lineSecond Line" -- Remove del for email |
Wouter van Ooijen <wouter@voti.nl>: Oct 12 08:11PM +0200 arnuld schreef op 12-Oct-14 7:26 PM: > "Second Line"; > std::cout << "arr1 = " << arr1 << std::endl; > std::cout << "arr2 = " << arr2 << std::endl; Note that you are doing something dangerous here: you ask a string (const char pointer) to be printed that is not 0-terminated. Wouter |
Bo Persson <bop@gmb.dk>: Oct 12 11:34AM +0200 On 2014-10-12 00:48, JiiPee wrote: > str.size(); > so they have to understand that str is an object and it can call its > member functions, but yes its not too much OO there. There is no OO going on here, just some "C with classes". No new or delete, no inheritance, no virtual functions. It just works. Telling a new student that std::string holds a string, and that you can get its size by calling str.size(), will surprise nobody. Compare that to the "easy to understand" C string functions, and try to explain the incantation char* b = malloc(strlen(a) + 1); Bo Persson |
Emanuel Berg <embe8573@student.uu.se>: Oct 12 04:41PM +0200 > Why? You can easily learn italian without knowing > latin first. It's the same way with programming > languages. In general: yes, but in the case of C++ and C it is impossible from a practical perspective to learn C++ without learning C as well as C is a huge subset of C++. (At least formally so, in reality it is probably more correct to say that C++ is an extention of C.) -- underground experts united |
Robert Hutchings <rm.hutchings@gmail.com>: Oct 12 09:46AM -0500 On 10/12/2014 9:41 AM, Emanuel Berg wrote: > without learning C as well as C is a huge subset of > C++. (At least formally so, in reality it is probably > more correct to say that C++ is an extention of C.) I am following this discussion with keen interest. So, if one reads "Accelerated C++" by Koenig and Moo, they are learning C++ right from the start. Are we saying that this is the *wrong* way to learn C++? |
Emanuel Berg <embe8573@student.uu.se>: Oct 12 04:47PM +0200 > classes, and different I/O. > That's totally different from the way you write C > code. Yes, I mean: if the C program was good you don't need the C++ stuff to begin with. But if you want to you can compile it with g++ instead of gcc and you got a C++ program that does the same thing, probably just as good. (But again, why do that?) You often C the combination C/C++ in literature, ads, and so on. Well, there *is* a "C/C++" and that is C++. Other than that C and C++ are two different languages with different syntax, tools, and (as you mention) libraries. Tho the biggest difference by far is the C++ focus on OO. -- underground experts united |
Emanuel Berg <embe8573@student.uu.se>: Oct 12 04:56PM +0200 > yes. On videos the top C++ people they always say > the code should be as short as possible and simple. > Using C++ and classes does that. OO and programming with classes does not make the code "shorter". OO makes programs "simpler" only when the purpose of the program lend itself naturally to modelling: like simulation, games, certain abstract situations with clear building blocks (e.g., a hierarchical scheduler), and so on. OO is not "always better". Also: Short code is not always an advantage. Most often it is because it is fast to read and write. But sometimes short code gets really cryptical and difficult to maintain. Short code doesn't imply execution speed. It can actually be the other way around as there isn't any optimization of obscure hacks. > For example for-loop becomes very short some > times... with C you cannot do such things. Yes you can: for-loop is the same in C and C++ and several other languages as well. -- underground experts united |
Bo Persson <bop@gmb.dk>: Oct 12 05:31PM +0200 On 2014-10-12 16:56, Emanuel Berg wrote: > execution speed. It can actually be the other way > around as there isn't any optimization of obscure > hacks. So lets's compare. :-) std::string a = "Sample string"; std::string b = a; or char a[] = "Sample string"; char* b = malloc(strlen(a) + 1); strcpy(b, a); /* and sometimes later: */ free(b); >> times... with C you cannot do such things. > Yes you can: for-loop is the same in C and C++ and > several other languages as well. Newer C++ has better for loops as well, like: for (auto x : v) std::cout << x; will output all elements in the sequence v, like a vector, or a string or an array, or ... Bo Persson |
Jorgen Grahn <grahn+nntp@snipabacken.se>: Oct 12 04:06PM On Sun, 2014-10-12, Emanuel Berg wrote: > impossible from a practical perspective to learn C++ > without learning C as well as C is a huge subset of > C++. It is, but a lot of that subset is of no use in normal C++ programming. (Perhaps more the idioms than the concrete language constructs: you will use most C language constructs in your C++ programs over the years, but not in the way a C programmer would.) So, a lot like latin and italian. /Jorgen -- // Jorgen Grahn <grahn@ Oo o. . . \X/ snipabacken.se> O o . |
JiiPee <no@notvalid.com>: Oct 12 05:22PM +0100 On 12/10/2014 15:56, Emanuel Berg wrote: > execution speed. It can actually be the other way > around as there isn't any optimization of obscure > hacks. many times there is no difference in assembly code though. For example c-loop: int i; for(i=0; i<size; ++i) can be done in C++: for(auto i : vec) clearly c++ version is shorter and more elegant here. Its also easier to see what happens in the looop. So its better readable. plus the assembly code is the same in both, so they are equally fast Or would you say the C code here is better? In what way? >> times... with C you cannot do such things. > Yes you can: for-loop is the same in C and C++ and > several other languages as well. you can do: for(auto i : vec) in C (and lets imagine that the vector item type is very long, thus auto makes the type short)? |
Jorgen Grahn <grahn+nntp@snipabacken.se>: Oct 12 04:27PM On Sat, 2014-10-11, Emanuel Berg wrote: >> learn C before learning C++". Stroustrup said >> definite "no". > Maybe he said that as a way of promoting C++ and OO? The context is that someone wants to learn C++ -- surely no promotion is needed? I think the real background to that response is too many people have come to C++ over the years with a C background and written terrible code, making C++ (not C) look bad. > No harm can come from knowing C, on the contrary. > Only if you want to specifically do C++ and OO, of > course you shouldn't do C. That's the second time in three paragraphs you mention object orientation -- why? It was popular in the 1990s, but today noone forces you to do it, not in C++ at least. Personally I live happily without it[1]. [snip practical tips which I agree with] > have to be that "careful". A good C program is often a > good C++ program with minimal or zero modifications > (tho why do that if it is already good?). Strongly disagree. Good C++ programs use RAII, type safety, exceptions and the standard library: good C programs have to make do with arrays or home-grown linked lists, and manual memory management. /Jorgen [1] I find abstract datatypes useful in every program, but rarely see a need for run-time polymorphism, abstract interfaces, design patterns and so on. YMMV. -- // Jorgen Grahn <grahn@ Oo o. . . \X/ snipabacken.se> O o . |
JiiPee <no@notvalid.com>: Oct 12 05:30PM +0100 On 12/10/2014 16:31, Bo Persson wrote: > strcpy(b, a); > /* and sometimes later: */ > free(b); yes, this would be pain for me... "lazy" programmer as I am. I really don't like to remember doing free() at the end. I want it to be automatic. Although maybe C-people can show how to aumatizice this?? I guess C programmers use some helper function to do these? Doing like that would be pain for me at least... I do not like to write code if not necessary. > std::cout << x; > will output all elements in the sequence v, like a vector, or a string > or an array, or ... Yeps. This is a really good feature imo after learning to use it. It takes some time to get used to this new syntax, but after familiar with it, its very good and natural and no going back. |
Paavo Helde <myfirstname@osa.pri.ee>: Oct 12 11:41AM -0500 Emanuel Berg <embe8573@student.uu.se> wrote in > impossible from a practical perspective to learn C++ > without learning C as well as C is a huge subset of > C++. But it is not a proper subset, and neither is it "huge". There are lots of things in C which cannot be used or are not needed in C++ (from the top of my head: calling undeclared functions (default types!), _Bool, restrict, C-style casts, longjmp(), strcat() et al, malloc() et al, qsort (), printf() et al, tables of function pointers, naming conventions (like encoding library name or parameter types in the function name), static free functions, most of preprocessor, most of pointer arithmetics and sizeof, array syntax (esp tricky when passing to/from functions), error reporting by error codes, etc., tedious cleanup in error paths, etc.). The 'const' behavior is slightly different so some relearning is needed if the C const is learned too well. The idiomatic use of for() loops in C++ has variable declarations inside for(), which is not valid C syntax, and if()/while() also support similar syntax in C++, so one would need to learn the usage of basic looping constructs twice, first with unneeded restrictions. Placement of variable declarations inside function also has unnessecary and harmful restrictions in C, so learning the C way first is actually harmful when learning C++. To be honest, what's left in common is quite a small subset, basically built-in datatypes and conversions plus general syntax of declaring and defining functions. Yes, you will need these basics to learn C++, but they do not constitute a large part of either C or C++. Cheers Paavo |
Richard Damon <Richard@Damon-Family.org>: Oct 12 12:46PM -0400 On 10/12/14, 10:41 AM, Emanuel Berg wrote: > without learning C as well as C is a huge subset of > C++. (At least formally so, in reality it is probably > more correct to say that C++ is an extention of C.) In learning C++, you will learn much of the syntax of C (at least C90), but you might not know which parts of the syntax you learned are C and which parts are C++ only. What you are less apt to learn is the library. While basically all of the C library is available in C++, these well might not be covered in a basic course. |
Emanuel Berg <embe8573@student.uu.se>: Oct 12 07:48PM +0200 > functions, pure virtual functions, overriding > functions, stuff I forgot, and stuff I don't even > know about, A lot of the stuff you mention (e.g, inheritance, overloading) I include when I say OO. C also has a library: the standard C library :) > You need another 800 page book to tell you how to > use the STL library. GUI and the web is extra. > K&R's book on C has only has 272 pages *total*. I don't think counting the pages of books as a method has any value to examine complexity but there is no doubt in my mind that C++ is more difficult to master - it has many more concepts than C and those are not always implemented the way you would first think. > marginal value. C++ is "right up there" in terms of > difficult programming languages. Think of learning > Spanish vs. Mandarin. Natural languages and not a good metaphor for programming languages. If you sucked at Spanish at school you might still be a great programmer. C++ is not as straightforward as C but it is very possible to do with time and effort, besides you don't need to use all that fancy OO stuff if you don't want to. Inheritance is a good example that is a big part of OO (at least if you read books about it) but i real programs usually it just makes things complicated and difficult to overview. C++ isn't as simple and clean as C but that doesn't matter you can't use C++, can't use OO in a clean and simple way. -- underground experts united |
Wouter van Ooijen <wouter@voti.nl>: Oct 12 09:42AM +0200 Richard Damon schreef op 11-Oct-14 11:40 PM: > specific things to specific signals under specific signals, and don't > have many cases of writing a program to toggle an arbitrary signal under > some condition. Indeed. If you never need to do something with 'abstract' pins the C approach is sufficient. I want for instance be able to write a bit-banged I2C master, that uses an abstract pin. In actual use that pin can be a regular input-output pin, or an open-collector pin. The regular input-output pin needs to be handled a bit different (low => output and low, high => input). The I2C code does not concern itself with such details, but the resulting machine code is as efficient as if it fully knew. Or maybe I was in a funny mood, and the I2C pins were pins on an MCP23017 I/0 extender chip. But I do agree, if you can write your code directly for the I/O pins that you use there is no advantage in the abstraction I describe. Wouter |
Richard Damon <Richard@Damon-Family.org>: Oct 12 08:40AM -0400 On 10/12/14, 3:42 AM, Wouter van Ooijen wrote: > But I do agree, if you can write your code directly for the I/O pins > that you use there is no advantage in the abstraction I describe. > Wouter Actually, I find the insufficient as the piece of code to manipulate the pin then needs to change based on the pin type. With my method, there is a single line of code, in a header that is visible to the code that automatically reconfigures the code that is providing the "higher level" driver. In my method, the I2C Master interface that you describe would get its pin definitions from an configuration include file, as opposed to having some setup call build a pointer for them. This does say I need to duplicate the code if I want to build two bit banged I2C ports in a given application, or accept the added inefficiency of the virtual calls (but for bit banged I2C, is it really significant?) |
Wouter van Ooijen <wouter@voti.nl>: Oct 12 04:52PM +0200 Richard Damon schreef op 12-Oct-14 2:40 PM: >> Wouter > Actually, I find the insufficient as the piece of code to manipulate the > pin then needs to change based on the pin type. Yes and no: The i2c lib must of course state that it wants an open-collector pin. But the actual 'conversions' of input-output and open-collector to open-collector are written once, and are also used by other protocols that need an open-collector pin, for instance the dallas 1-wire interface. All in the name of 'write it once' or 'don't repeat yourself. The relevant part of the i2c interface: template< class arg_scl, class arg_sda class i2c_bus_master_bb_scl_sda { // use the pins in an appropriate way // (and assert that they can be used as such) typedef pin_oc_from< arg_scl > scl; typedef pin_oc_from< arg_sda > sda; ... }; All code in the class template uses the scl and sda, not the arg_scl and arg_sda. The pin_oc_from class template is specialized for the 3 cases: input-output pin, open-collector pin, and the default that generates an appropriate compiler error message. The actual code: // fallback: compile-time error template< class unsupported, class dummy = void > struct pin_oc_from { static_assert( sizeof( unsupported ) == 0, "pin_oc_from<> requires " "a pin_oc, or pin_in_out" ); }; // from itself: delegate template< class pin > struct pin_oc_from < pin, typename pin::has_pin_oc > : public pin_oc_archetype { static void init(){ pin::init(); } static bool get(){ return pin::get(); } static void set( bool x ){ pin::set( x ); } }; // from a pin_in_out template< class pin > struct pin_oc_from < pin, typename pin::has_pin_in_out > : public pin_oc_archetype { static void init(){ pin::init(); } static void set( bool x ){ // to make a pin_in_out behave like a pin_oc if( x ){ // make it float when it is set high pin::direction_set_input(); } else { // make it output and low when it is set low pin::direction_set_output(); pin::set( 0 ); } } static bool get(){ return pin::get(); } }; > duplicate the code if I want to build two bit banged I2C ports in a > given application, or accept the added inefficiency of the virtual calls > (but for bit banged I2C, is it really significant?) Maybe not for I2C, but you give up that possibility for IMO no gain. And for (for instance) dallas 1-wire or SPI I can very well imagine more than one bus of a certain type per system. What you essentially do is compile-time polymorphism by modifying the source file to include the right 'input' source file. One thing that I certainly don't like about that is that it requires you to copy the library file (bb i2c interface) to your project and modify it. (Or some other scheme, where #include something that is essentially a source file, not a header). There are other points, for instance that the interface between the points and the i2c part is essentially by global functions. Note that my scheme is not limited to GPIO's. There are many other abstractions that can be encapsulated similarly in static class templates. Wouter |
Paavo Helde <myfirstname@osa.pri.ee>: Oct 12 01:44AM -0500 > Was thinking if there are any reasons. There is one reason: Was it > Sutter who said that class should have as less funtions as possible. So > doing this globally would reduce the number of functions in classes. I agree that class public interface should be as minimal as possible - but not smaller! This example of unscalable mess with typeid checking is exactly the reason why virtual functions were invented in the first place. Cheers Paavo |
Paavo Helde <myfirstname@osa.pri.ee>: Oct 12 02:57AM -0500 Urs Thuermann <urs@isnogud.escape.de> wrote in > B *b1 = new auto(*b); > } > Is this the correct and preferred way in C++11? To work as expected, one needs to have dynamic type lookup at runtime here, but 'auto' is a compile-time concept, so I don't think it helps here. Moreover, it should know all possible run-time types of B-derived classes at compile time, but this is in principle impossible (as one can add new dynamic libraries with new classes at runtime). > and then call b->clone() instead of the new operator. > Is there a way to do this in C++98 without the need to add a new > function like clone() in each derived class? Yes, that's the way to do it. 1 extra line per class is not so much. Cheers Paavo |
JiiPee <no@notvalid.com>: Oct 12 10:04AM +0100 On 12/10/2014 07:44, Paavo Helde wrote: > exactly the reason why virtual functions were invented in the first place. > Cheers > Paavo but if for example std::string public interface had a function called: B* clone(); which nobody really uses other than some code internally, then isn't it bad from the users point of view seeing this kind of clone function which they never need? But surely there is a way to hide the clone, like being protected, then this would not be a problem. |
JiiPee <no@notvalid.com>: Oct 12 10:06AM +0100 On 12/10/2014 07:44, Paavo Helde wrote: > exactly the reason why virtual functions were invented in the first place. > Cheers > Paavo I would not like to see B* clone() being a public member of a std::string class. But if its a private member then it would be ok. The functions calling it can be friends so they can get access to private clone(). |
You received this digest because you're subscribed to updates for this group. You can change your settings on the group membership page. To unsubscribe from this group and stop receiving emails from it send an email to comp.lang.c+++unsubscribe@googlegroups.com. |
No comments:
Post a Comment