Remember that C and C++ are actually completely different languages. They share some common syntax, but C is a procedural language and C++ is object oriented, so they are different programming paradigms.

gcc should work just fine as a C compiler. I believe MinGW uses it. It also has flags you can specify to make sure it's using the right version of C (e.g. C99).

If you want to stick with C then you simply won't be able to use new (it's not part of the C language) but there shouldn't be any problems with moving to C++ for a shared library, just so long as you put your Object Oriented hat on when you do.

I'd suggest you just stick with the language you are more comfortable with. The fact that you're using new suggests that will be C++, but it's up to you.

Answer from Cameron Skinner on Stack Overflow
Top answer
1 of 7
9

Remember that C and C++ are actually completely different languages. They share some common syntax, but C is a procedural language and C++ is object oriented, so they are different programming paradigms.

gcc should work just fine as a C compiler. I believe MinGW uses it. It also has flags you can specify to make sure it's using the right version of C (e.g. C99).

If you want to stick with C then you simply won't be able to use new (it's not part of the C language) but there shouldn't be any problems with moving to C++ for a shared library, just so long as you put your Object Oriented hat on when you do.

I'd suggest you just stick with the language you are more comfortable with. The fact that you're using new suggests that will be C++, but it's up to you.

2 of 7
4
  1. You can use e.g. GCC as a C compiler. To ensure it's compiling as C, use the -x c option. You can also specify a particular version of the C standard, e.g. -std=c99. To ensure you're not using any GCC-specific extensions, you can use the -pedantic flag. I'm sure other compilers have similar options.

  2. malloc and calloc are indeed how you allocate memory in C.

  3. That's up to you.* You say that you want to be cross-platform, but C++ is essentially just as "cross-platform" as C. However, if you're working on embedded platforms (e.g. microcontrollers or DSPs), you may not find C++ compilers for them.

  4. No, new and delete are not supported in C.


* In my opinion, though, you should strongly consider switching to C++ for any application of non-trivial complexity. C++ has far more powerful high-level constructs than C (e.g. smart pointers, containers, templates) that simplify a lot of the tedious work in C. It takes a while to learn how to use them effectively, but in the long run, they will be worth it.
Top answer
1 of 12
386

Method 1 (using new)

  • Allocates memory for the object on the free store (This is frequently the same thing as the heap)
  • Requires you to explicitly delete your object later. (If you don't delete it, you could create a memory leak)
  • Memory stays allocated until you delete it. (i.e. you could return an object that you created using new)
  • The example in the question will leak memory unless the pointer is deleted; and it should always be deleted, regardless of which control path is taken, or if exceptions are thrown.

Method 2 (not using new)

  • Allocates memory for the object on the stack (where all local variables go) There is generally less memory available for the stack; if you allocate too many objects, you risk stack overflow.
  • You won't need to delete it later.
  • Memory is no longer allocated when it goes out of scope. (i.e. you shouldn't return a pointer to an object on the stack)

As far as which one to use; you choose the method that works best for you, given the above constraints.

Some easy cases:

  • If you don't want to worry about calling delete, (and the potential to cause memory leaks) you shouldn't use new.
  • If you'd like to return a pointer to your object from a function, you must use new
2 of 12
135

There is an important difference between the two.

Everything not allocated with new behaves much like value types in C# (and people often say that those objects are allocated on the stack, which is probably the most common/obvious case, but not always true). More precisely, objects allocated without using new have automatic storage duration Everything allocated with new is allocated on the heap, and a pointer to it is returned, exactly like reference types in C#.

Anything allocated on the stack has to have a constant size, determined at compile-time (the compiler has to set the stack pointer correctly, or if the object is a member of another class, it has to adjust the size of that other class). That's why arrays in C# are reference types. They have to be, because with reference types, we can decide at runtime how much memory to ask for. And the same applies here. Only arrays with constant size (a size that can be determined at compile-time) can be allocated with automatic storage duration (on the stack). Dynamically sized arrays have to be allocated on the heap, by calling new.

(And that's where any similarity to C# stops)

Now, anything allocated on the stack has "automatic" storage duration (you can actually declare a variable as auto, but this is the default if no other storage type is specified so the keyword isn't really used in practice, but this is where it comes from)

Automatic storage duration means exactly what it sounds like, the duration of the variable is handled automatically. By contrast, anything allocated on the heap has to be manually deleted by you. Here's an example:

void foo() {
  bar b;
  bar* b2 = new bar();
}

This function creates three values worth considering:

On line 1, it declares a variable b of type bar on the stack (automatic duration).

On line 2, it declares a bar pointer b2 on the stack (automatic duration), and calls new, allocating a bar object on the heap. (dynamic duration)

When the function returns, the following will happen: First, b2 goes out of scope (order of destruction is always opposite of order of construction). But b2 is just a pointer, so nothing happens, the memory it occupies is simply freed. And importantly, the memory it points to (the bar instance on the heap) is NOT touched. Only the pointer is freed, because only the pointer had automatic duration. Second, b goes out of scope, so since it has automatic duration, its destructor is called, and the memory is freed.

And the barinstance on the heap? It's probably still there. No one bothered to delete it, so we've leaked memory.

From this example, we can see that anything with automatic duration is guaranteed to have its destructor called when it goes out of scope. That's useful. But anything allocated on the heap lasts as long as we need it to, and can be dynamically sized, as in the case of arrays. That is also useful. We can use that to manage our memory allocations. What if the Foo class allocated some memory on the heap in its constructor, and deleted that memory in its destructor. Then we could get the best of both worlds, safe memory allocations that are guaranteed to be freed again, but without the limitations of forcing everything to be on the stack.

And that is pretty much exactly how most C++ code works. Look at the standard library's std::vector for example. That is typically allocated on the stack, but can be dynamically sized and resized. And it does this by internally allocating memory on the heap as necessary. The user of the class never sees this, so there's no chance of leaking memory, or forgetting to clean up what you allocated.

This principle is called RAII (Resource Acquisition is Initialization), and it can be extended to any resource that must be acquired and released. (network sockets, files, database connections, synchronization locks). All of them can be acquired in the constructor, and released in the destructor, so you're guaranteed that all resources you acquire will get freed again.

As a general rule, never use new/delete directly from your high level code. Always wrap it in a class that can manage the memory for you, and which will ensure it gets freed again. (Yes, there may be exceptions to this rule. In particular, smart pointers require you to call new directly, and pass the pointer to its constructor, which then takes over and ensures delete is called correctly. But this is still a very important rule of thumb)

🌐
Cprogramming
cboard.cprogramming.com › cplusplus-programming › 62449-new-keyword.html
'new' keyword - C Board
MyClass var1 = MyClass(constructorarg); Now what the new keyword does is dynamicly allocate memory for an object on the heap, and then return the ADDRESS to that location. Now what you need to do if you want to do this, is use a pointer (something you didn't deal with dirrectly in Java) here is an example
🌐
Reddit
reddit.com › r/learnprogramming › what does the "new" keyword do in programming?
r/learnprogramming on Reddit: What does the "new" keyword do in programming?
March 6, 2016 -

Sometimes people choose to write "new" before declaring an array or calling a function. But there are some who say it is bad and people should do without it.

But... If you can do without "new", why do people use it in the first place? Everyone talks about pros vs cons but no one talks about what is this "new" and what purpose does it serve.

Top answer
1 of 5
4
new is used to allocate an object with dynamic storage duration, while declaring an object without new uses automatic storage duration. Given an example: Obj foo(); Obj* bar = new Obj(); foo is allocated using automatic storage duration. foo will exist only within the scope of the brackets containing the declaration. When the block ends, the foo will be destructed. bar is allocated using dynamic storage duration. It will persist even when you go out of scope. That means if you exit the block bar is currently in, e.g. you finish your function and return elsewhere, bar will still continue to exist. You have to manually destruct it yourself using the delete or delete[] where appropriate. The rule of thumb is for every new and new[] in your code, there should exist an equal number of delete and delete[]. This is one of the most common beginner bugs, as new users allocate memory dynamically but forget to call delete after they are done, assuming their object will be destructed automatically. This is not the case, and can lead to memory leaks.
2 of 5
3
The behavior of new is not the same across languages so you'll need to let us know which language you're interested in. Briefly: In C++ new allocates memory. There are several different new operators in this language each with a different purpose but in general it's possible to avoid their use by using containers from the standard library or - when necessary - one of the smart pointer classes. The reason to avoid new is that it must be paired with a corresponding delete. Forgetting to do so leaks memory. In Java and C# new allocates a new object. This is similar to C++ but objects in these languages are garbage collected. There is no corresponding delete operator because the object is automatically cleaned up after there are no longer any references to the object. It is perfectly fine - and necessary - to use new in these languages. In JavaScript new allocates a new object and sets up that object's prototype chain in a particular way. As in Java and C# these objects are garbage collected. The new operator is different in behavior from Java or C# because its behavior can be implemented using other language constructs; that is, new is syntactic sugar which saves you from writing some code. In particular, you can already allocate an object by simply declaring it.
🌐
Bitesizedengineering
bitesizedengineering.com › p › what-happens-when-you-type-the-new
What happens when you type the "new" keyword?
February 9, 2023 - This is useful in cases where you suspect someone might have overloaded it. new(storage) CandyBar(“Snickers”) is the placement new syntax. What it does is probably self-explanatory - it constructs the CandyBar object at the storage address. Why is all of this relevant, one might ask. And to ...
🌐
Javiercasas
javiercasas.com › articles › the-tyranny-of-the-new-keyword-1
The Tyranny of the new keyword (I)
The way to call constructors in objects is by using the new keyword so indirectly the constructor is called. Therefore, I need special effort to initialize an object, as I need to somehow call new on it. So initialization of an object is something that can be done only as the result of new.
🌐
Cppreference
en.cppreference.com › w › cpp › keyword › new.html
C++ keyword: new - cppreference.com
Log in · Page · Discussion · View · Edit · History · From cppreference.com · < cpp‎ | keyword · C++ [edit] C++ language · [edit] Keywords · [edit] new expression · allocation functions as the name of operator-like functions · Retrieved from "https://en.cppreference.com/mwiki/...
Find elsewhere
🌐
Reddit
reddit.com › r/cpp_questions › what does actually using the new keyword, or instantiating something in c++ really mean?
r/cpp_questions on Reddit: What does actually using the new keyword, or instantiating something in C++ really mean?
August 28, 2020 -

So I don't consider myself a CS noob by any means and have wrangled my fair share of systems, but also find myself forgetting my CS classes a bit and was surprised when I pondered this I didn't have a clear answer. So, in C/C++ (assuming a non-optimizing compiler) I know when we have a declaration like int stackVar = 5; that will probably get placed either in a register or on in-memory stack. However, when you call new, you always get a pointer back, because from what I understand, new will mean it always goes to heap. Why is it this way? It seems to me that instantiating makes sense for larger objects because having a pointer to them is less expensive than loading the object itself. But when then do we put things on stack, or is that only primitive data types? What does "instantiating" actually mean in the context of saying Request* r = new Request() for some web API versus the above int r = 5 example? How are the two different?

Top answer
1 of 9
18
So, it seems like your question sort of boils down to two things: What is heap allocation used for, and what does new do on top of allocation? Heap allocation is mainly used if you’ve got some sort of array or object that the size isn’t known at compile time, or if you’ve got a huge data structure. On top of those two reasons, the heap is also used to extend the lifetime of arrays, objects etc. Generally, you’re going to be putting things on the stack. Variables, normal arrays, things that don’t need extended lifetimes should live on the stack because you don’t have to deal with allocating memory, and it’ll help your code run faster. Using the new keyword with an object not only allocates memory, but it also calls the class constructor with it, which is pretty neat! But, you don’t need to put objects on the heap, and usually you won’t have to. You can simply declare and initialize objects just like you would with any primitive types. Hope this cleared it up! Feel free to ask more questions, my writing isn’t 100% clear lol
2 of 9
5
When you write int x{ 5 }; or int* y = new int{ 5 }; two things happen: allocation and initialization. When you create an object "normally" (like x above), it is placed on the stack, which means that space is allocated for it on the stack and the stack pointer is moved forwards to point to the next free slot. When you place something on the heap, the actual value is placed on the heap, and the pointer y is placed on the stack. Allocating space for something on the heap is very expensive compared to stack allocations, since stack allocations are essentially just pointer arithmetic, whereas heap allocation means that your program asks the operating system to give it some free space. Initialization is the same for stack and heap allocations; the constructor of whatever type is being constructed is run on that freshly allocated chunk of memory. As to why you would allocate something on the heap instead of on the stack; you generally only do it when you don't know the size of whatever object you're trying to allocate space for, or if the object's size exceeds the size of the stack, which is pre-determined. For example, a std::vector might contain 8 integers or it might contain 5 million. Since we don't know, the vector allocates space for its contents on the heap. Polymorphism is another valid use-case.
🌐
GeeksforGeeks
geeksforgeeks.org › c++ › new-vs-operator-new-in-cpp
new vs operator new in C++ - GeeksforGeeks
February 21, 2023 - When you create an object of class using new keyword(normal new). The memory for the object is allocated using operator new from heap. The constructor of the class is invoked to properly initialize this memory.
🌐
Quora
quora.com › What-are-some-alternatives-to-using-the-new-keyword-in-C
What are some alternatives to using the 'new' keyword in C++? - Quora
Answer: In C++ you can call a function that creates objects and returns them. The compiler is an optimizing compiler, and will arrange the code to not need to return a copy in most cases. [code]#include #include #include #include using st_vec = st...
🌐
Cppreference
en.cppreference.com › w › cpp › language › new.html
new expression - cppreference.com
If placement-args are provided, they are passed to the allocation function as additional arguments. Such allocation functions are known as "placement new", after the standard allocation function void* operator new(std::size_t, void*), which simply returns its second argument unchanged. This is used to construct objects in allocated storage:
🌐
Quora
quora.com › What-is-the-purpose-of-the-new-operator-in-C
What is the purpose of the 'new' operator in C++? - Quora
Answer: In C++, [code ]new[/code] ... the most common use of new, especially among beginners is something like: [code ]Foo *bar = new Foo;[/code] Many experienced C++ programmer......
🌐
TutorialsPoint
tutorialspoint.com › cprogramming › c_keywords.htm
C - Keywords
The new keywords introduced from C99 onwards start with an underscore character. The compiler checks the source code for the correctness of the syntax of all the keywords and then translates it into the machine code. In the following program, we are using a keyword as an identifier i.e., as ...
🌐
Quora
quora.com › What-exactly-does-the-keyword-new-do-in-C++-During-an-interview-I-said-it-instantiates-a-class-and-calls-the-constructor-Why-is-that-wrong
What exactly does the keyword new do in C++? During an interview, I said it instantiates a class and calls the constructor. Why is that wrong? - Quora
Answer (1 of 13): In summary [code ]new[/code] allocates memory for the specified object from the free-store and then initializes the object (if primitive) or calls the relevant constructor (if a class object). In C++ classes aren’t themselves objects (like Java say) and while any static members...
🌐
Cplusplus
cplusplus.com › forum › beginner › 144787
How useful can the "new" keyword be in h - C++ Forum
The rule of thumb is that there's mostly likely no need to call new if you're going to be deleting the allocated memory in the same scope that you're new'ing it. (Except for raw arrays, which you should be using std::vectors anyway) ... I did this recently ( a month or so ) to learn how I could create objects with unknown arguments at run time. The idea behind this is that the function returns a pointer of type object which is allocated on the heap via new. The delete function takes an obj address as an argument to free that obj's memory. Keep an eye on the addresses, you can use them to see how big your object is, and see how it is allocated contiguously.
Top answer
1 of 2
183

In C++11, the using keyword when used for type alias is identical to typedef.

7.1.3.2

A typedef-name can also be introduced by an alias-declaration. The identifier following the using keyword becomes a typedef-name and the optional attribute-specifier-seq following the identifier appertains to that typedef-name. It has the same semantics as if it were introduced by the typedef specifier. In particular, it does not define a new type and it shall not appear in the type-id.

Bjarne Stroustrup provides a practical example:

typedef void (*PFD)(double);    // C style typedef to make `PFD` a pointer to a function returning void and accepting double
using PF = void (*)(double);    // `using`-based equivalent of the typedef above
using P = [](double)->void; // not valid in C++11
using P = auto(double)->void // Fixed thanks to DyP

Pre-C++11, the using keyword can bring member functions into scope. In C++11, you can now do this for constructors (another Bjarne Stroustrup example):

class Derived : public Base { 
public: 
    using Base::f;    // lift Base's f into Derived's scope -- works in C++98
    void f(char);     // provide a new f 
    void f(int);      // prefer this f to Base::f(int) 

    using Base::Base; // lift Base constructors Derived's scope -- C++11 only
    Derived(char);    // provide a new constructor 
    Derived(int);     // prefer this constructor to Base::Base(int) 
    // ...
}; 

Ben Voight provides a pretty good reason behind the rationale of not introducing a new keyword or new syntax. The standard wants to avoid breaking old code as much as possible. This is why in proposal documents you will see sections like Impact on the Standard, Design decisions, and how they might affect older code. There are situations when a proposal seems like a really good idea but might not have traction because it would be too difficult to implement, too confusing, or would contradict old code.


Here is an old paper from 2003 n1449. The rationale seems to be related to templates. Warning: there may be typos due to copying over from PDF.

First let’s consider a toy example:

template <typename T>
class MyAlloc {/*...*/};

template <typename T, class A>
class MyVector {/*...*/};

template <typename T>

struct Vec {
typedef MyVector<T, MyAlloc<T> > type;
};
Vec<int>::type p; // sample usage

The fundamental problem with this idiom, and the main motivating fact for this proposal, is that the idiom causes the template parameters to appear in non-deducible context. That is, it will not be possible to call the function foo below without explicitly specifying template arguments.

template <typename T> void foo (Vec<T>::type&);

So, the syntax is somewhat ugly. We would rather avoid the nested ::type We’d prefer something like the following:

template <typename T>
using Vec = MyVector<T, MyAlloc<T> >; //defined in section 2 below
Vec<int> p; // sample usage

Note that we specifically avoid the term “typedef template” and introduce the new syntax involving the pair “using” and “=” to help avoid confusion: we are not defining any types here, we are introducing a synonym (i.e. alias) for an abstraction of a type-id (i.e. type expression) involving template parameters. If the template parameters are used in deducible contexts in the type expression then whenever the template alias is used to form a template-id, the values of the corresponding template parameters can be deduced – more on this will follow. In any case, it is now possible to write generic functions which operate on Vec<T> in deducible context, and the syntax is improved as well. For example we could rewrite foo as:

template <typename T> void foo (Vec<T>&);

We underscore here that one of the primary reasons for proposing template aliases was so that argument deduction and the call to foo(p) will succeed.


The follow-up paper n1489 explains why using instead of using typedef:

It has been suggested to (re)use the keyword typedef — as done in the paper [4] — to introduce template aliases:

template<class T> 
    typedef std::vector<T, MyAllocator<T> > Vec;

That notation has the advantage of using a keyword already known to introduce a type alias. However, it also displays several disavantages among which the confusion of using a keyword known to introduce an alias for a type-name in a context where the alias does not designate a type, but a template; Vec is not an alias for a type, and should not be taken for a typedef-name. The name Vec is a name for the family std::vector< [bullet] , MyAllocator< [bullet] > > – where the bullet is a placeholder for a type-name. Consequently we do not propose the “typedef” syntax. On the other hand the sentence

template<class T>
    using Vec = std::vector<T, MyAllocator<T> >;

can be read/interpreted as: from now on, I’ll be using Vec<T> as a synonym for std::vector<T, MyAllocator<T> >. With that reading, the new syntax for aliasing seems reasonably logical.

I think the important distinction is made here, aliases instead of types. Another quote from the same document:

An alias-declaration is a declaration, and not a definition. An alias- declaration introduces a name into a declarative region as an alias for the type designated by the right-hand-side of the declaration. The core of this proposal concerns itself with type name aliases, but the notation can obviously be generalized to provide alternate spellings of namespace-aliasing or naming set of overloaded functions (see ✁ 2.3 for further discussion). [My note: That section discusses what that syntax can look like and reasons why it isn't part of the proposal.] It may be noted that the grammar production alias-declaration is acceptable anywhere a typedef declaration or a namespace-alias-definition is acceptable.

Summary, for the role of using:

  • template aliases (or template typedefs, the former is preferred namewise)
  • namespace aliases (i.e., namespace PO = boost::program_options and using PO = ... equivalent)
  • the document says A typedef declaration can be viewed as a special case of non-template alias-declaration. It's an aesthetic change, and is considered identical in this case.
  • bringing something into scope (for example, namespace std into the global scope), member functions, inheriting constructors

It cannot be used for:

int i;
using r = i; // compile-error

Instead do:

using r = decltype(i);

Naming a set of overloads.

// bring cos into scope
using std::cos;

// invalid syntax
using std::cos(double);

// not allowed, instead use Bjarne Stroustrup function pointer alias example
using test = std::cos(double);
2 of 2
3

Another difference between typedef and using: you may do this:

    using vector3d_t = double[3];
    vector3d_t v = {1,2,3};
    v[1] = 4;

It is not possible with typedef:

    typedef double[3] vector3d_t; // Compilation error
🌐
TutorialsPoint
tutorialspoint.com › when-to-use-new-operator-in-cplusplus-and-when-it-should-not-be-used
When to use new operator in C++ and when it should not be used?
#include <iostream> using namespace ... 2 : 223.324 · Now let us understand the above program. The new operator is used to initialize the memory and return its address to the pointer variable ptr1 and ptr2....
🌐
cppreference.com
en.cppreference.com › w › c › keyword.html
C keywords - cppreference.com
These can be used wherever the keyword can. It is unspecified whether any of the spellings of these keywords, their alternate forms, or true and false is implemented as a predefined macro. Each name that begins with a double underscore __ or an underscore _ followed by an uppercase letter is reserved: see identifier for details. Note that digraphs <%, %>, <:, :>, %:, and %:%: provide an alternative way to represent standard tokens.