The Flat Earth Society

Other Discussion Boards => Technology, Science & Alt Science => Topic started by: Pezevenk on October 18, 2019, 10:02:34 AM

Title: Do any of you know C++?
Post by: Pezevenk on October 18, 2019, 10:02:34 AM
Because I'm having a hard time with this annoying language. I know Java and it is pretty similar but some things about C++ is pretty confusing. I just need it because I gotta solve some exercises in a textbook that require C++, so it's nothing complicated, I'm just very confused by pointers and references and what you can return using functions and all that stuff.
Title: Re: Do any of you know C++?
Post by: Yes on October 18, 2019, 10:23:31 AM
Because I'm having a hard time with this annoying language. I know Java and it is pretty similar but some things about C++ is pretty confusing. I just need it because I gotta solve some exercises in a textbook that require C++, so it's nothing complicated, I'm just very confused by pointers and references and what you can return using functions and all that stuff.
It's been years since I've used C++, but I may be able to provide a bit of help.
In my opinion, the most confusing thing about pointers and references is the dumb syntax you have to use to declare and dereference them.

When you say, what you can return using functions, the answer to that is pretty much the same as in Java.  The important difference is that in Java, passing objects is actually passing pointers to objects, pointers which you're unable (by design) to directly interact with.  In C/C++, if you want to pass back a big object, it's typically the case that it's been allocated on the heap and you pass back a pointer to that object.  Java does the same thing, just without the dumb syntax.  Unlike in Java, you can pass anything allocated on the stack, too.  But it's generally a bad idea to pass "complex" objects on the stack that way, since it involves copying the whole object and may also involve unexpected actions in a copy ctor.  In contrast, all objects in Java are (conceptually*) allocated on the heap. (*This is like 99% true.  Cool optimizers can use escape analysis to determine when stack allocation is safe.  Ignore this parenthetical if you don't know what it means.)

This is also why there are so many memory bugs in C/C++ programs, because often you have to manually keep track of when it's safe to free the memory allocated on the heap.  There are automatic and semi-automatic ways to do this, but it's probably a bit much to bring up at this point.  There are also cool pointer "helpers" like unique_ptr you can use to help keep track of this, but we can discuss that later if you want.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 18, 2019, 10:48:26 AM

When you say, what you can return using functions, the answer to that is pretty much the same as in Java.  The important difference is that in Java, passing objects is actually passing pointers to objects, pointers which you're unable (by design) to directly interact with.  In C/C++, if you want to pass back a big object, it's typically the case that it's been allocated on the heap and you pass back a pointer to that object.  Java does the same thing, just without the dumb syntax.  Unlike in Java, you can pass anything allocated on the stack, too.  But it's generally a bad idea to pass "complex" objects on the stack that way, since it involves copying the whole object and may also involve unexpected actions in a copy ctor.  In contrast, all objects in Java are (conceptually*) allocated on the heap. (*This is like 99% true.  Cool optimizers can use escape analysis to determine when stack allocation is safe.  Ignore this parenthetical if you don't know what it means.)

This is also why there are so many memory bugs in C/C++ programs, because often you have to manually keep track of when it's safe to free the memory allocated on the heap.  There are automatic and semi-automatic ways to do this, but it's probably a bit much to bring up at this point.  There are also cool pointer "helpers" like unique_ptr you can use to help keep track of this, but we can discuss that later if you want.
Yeah, that's what confuses me. In Java I could just return an array from a function. In C++ I gotta do weird pointer stuff. I can never figure out where I should put the asterisks and where I should put the &s. Even when I somehow manage to get it to work, I can't do stuff like, say, getting the length of an array/vector that a pointer is pointing to. And when I manage to fix things it looks pretty inefficient to me, and defeating the point of it being fast for the numerical stuff I need it for. I'll give you an example when I get home.
Title: Re: Do any of you know C++?
Post by: Yes on October 18, 2019, 11:01:02 AM
I completely agree about the asterisks and ampersands.  There is a logic to it all, but they sure didn't make it straightforward. Keep in mind that pointers and references are not the same thing though, even though they have a lot in common.

And yeah, when you have a variable to an array, what you just have is a pointer to a place in memory when you'd expect contiguous objects.  The length of that array is not kept in that memory.  Generally you have to keep track of that on your own, or better yet just use something like std::array or std::vector or similar.  If you must use an array, and you must determine the length of an unknown array, you can use something like
Code: [Select]
sizeof(array)/sizeof(array[0]), but that comes with a host of caveats, and imo it's better to just use std library data structure.

Lower-level languages (compared to modern languages) being fast for numerical stuff is often overstated (https://benchmarksgame-team.pages.debian.net/benchmarksgame/).
Title: Re: Do any of you know C++?
Post by: Username on October 18, 2019, 11:10:44 AM
Yeah pointers end up confusing a lot of folks since java implicitly handles that for you.

With pointers you can do some really cool stuff though. For example, when I worked on the Myth II and III engines and tools you could really see how they leveraged them for some really fast operations on a lot of data, as well as knowing exactly the size and area of the memory you are consuming.

In java, you are actually returning a pointer to the array, not the array itself. It just hides that under the hood. Well, technically it's an object identifier or something like that.  Learning how it works behind the curtain is important as you can make use of that knowledge to make wise choices when passing things around.

Title: Re: Do any of you know C++?
Post by: Pezevenk on October 18, 2019, 12:39:20 PM
I completely agree about the asterisks and ampersands.  There is a logic to it all, but they sure didn't make it straightforward. Keep in mind that pointers and references are not the same thing though, even though they have a lot in common.

And yeah, when you have a variable to an array, what you just have is a pointer to a place in memory when you'd expect contiguous objects.  The length of that array is not kept in that memory.  Generally you have to keep track of that on your own, or better yet just use something like std::array or std::vector or similar.  If you must use an array, and you must determine the length of an unknown array, you can use something like
Code: [Select]
sizeof(array)/sizeof(array[0]), but that comes with a host of caveats, and imo it's better to just use std library data structure.

Lower-level languages (compared to modern languages) being fast for numerical stuff is often overstated (https://benchmarksgame-team.pages.debian.net/benchmarksgame/).
Well the benchmark test shows it's quite a bit faster than Java so... It's good enough for me.

Still, it's super annoying to deal with. I guess I'll try the std thing. But I gotta figure out the pointers eventually.
Title: Re: Do any of you know C++?
Post by: NotSoSkeptical on October 18, 2019, 04:29:14 PM
Pez,

You do understand that C and Java are inherently different in use.  Trying to compare how they work, is like comparing apples to oranges.  Yes they are both fruit and you gain nourishment (programming languages and you can create apps/function), but they serve entirely different purposes.

I would recommend you getting a how to or guide in basic C++.  They are great references and not very expensive.

Title: Re: Do any of you know C++?
Post by: Pezevenk on October 19, 2019, 09:49:43 AM
Pez,

You do understand that C and Java are inherently different in use.
You don't say!

Quote
  Trying to compare how they work, is like comparing apples to oranges. 
Not really, they have many similarities. A lot of the syntax is identical, and OOP in both has a lot of similarities.
Title: Re: Do any of you know C++?
Post by: Username on October 19, 2019, 12:12:54 PM
Yeah. They are pretty similar in the wider scheme of things. C++ is just a bit lower level.
Title: Re: Do any of you know C++?
Post by: Crouton on October 19, 2019, 12:41:07 PM
Post what you have. I'll take a look.
Title: Re: Do any of you know C++?
Post by: Username on October 19, 2019, 04:29:25 PM
#define ADDRESS_OF &
#define POINTED_TO_BY *

Might help you sort it out in the short run.

some_var = POINTED_TO_BY foo;
some_address = ADDRESS_OF type;
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 20, 2019, 02:18:33 PM
I think I kinda got the hang of it by trial and error. My understanding is that when * comes before a pointer or whatever it gives you what that pointer is pointing to, while & gives you the address of that thing, and you have to use it to define the pointer of that thing. One issue I have though is getting the size of an array/vector that is being pointed to by a pointer, does anyone have any idea how to do this?

Also I'm still 100% sure when it is a good idea to use pointers and references and when it isn't. Is there any good resource on that?
Title: Re: Do any of you know C++?
Post by: Crouton on October 20, 2019, 03:04:42 PM
C has no built in support for managing the size of an array. You can use a an object like carray that handles these sorts of details.  But you're depending on an external library for it which may cause issues with portability.  You're better off learning how to manage memory allocations manually. At least at first. Sort of for the same reason that you should not use graphing calculators in a math class.

Title: Re: Do any of you know C++?
Post by: Crouton on October 20, 2019, 03:36:14 PM
https://stackoverflow.com/questions/4995899/difference-between-pointer-and-reference-in-c

This is a pretty good rundown on pointers vs references.

To be honest I rarely use references. I just find pointers more straightforward.
Title: Re: Do any of you know C++?
Post by: Username on October 20, 2019, 09:28:21 PM
int size = sizeof(arr)/sizeof(arr[0]);
int size = sizeof(arr)/sizeof(int);

The size of the array divided by the size of the first element  / type.

There are other ways, or you can just keep track of it when you initialize it or allocate the memory for it via malloc.
Title: Re: Do any of you know C++?
Post by: Yes on October 21, 2019, 05:25:59 AM
Also I'm still 100% sure when it is a good idea to use pointers and references and when it isn't.
Since you're coming from a Java mindset, it might be easiest for you to just always use pointers (or references) on objects, and not use them for what Java calls primitives.  More specifically, for objects you want to pass around, just always use new and pass around the resulting pointer.  The nuance of when it's fine to allocate on the stack vs not can come later.
Title: Re: Do any of you know C++?
Post by: Crouton on October 21, 2019, 06:27:02 AM
Terrible.  Never do this.

#define HEAP_ARRAY_SIZE 100

unsigned long g_heap_array[HEAP_ARRAY_SIZE];

void DoSomething()
{
   int counter=0;
   while(counter<HEAP_ARRAY_SIZE)
   {
       printf("%lu element %i \n",g_heap_array[counter],counter);
      counter++;
   }
}


A little less terrible.  Don't abuse the heap this way.

//on the heap
unsigned long g_array_size=0;
unsigned long* g_p_array=NULL;

void DoSomething()
{
   int counter=0;
   while(counter<g_array_size)
   {
       printf("%lu element %i \n",g_heap_array[counter],counter);
      counter++;
   }
}

void CreateArray()
{
   unsigned long arbitrary_array_size=10;
   g_array_size=arbitrary_array_size=10;;
   g_p_array=(unsigned long*)malloc(g_array_size*sizeof(unsigned long));
   int counter=0;
   while(counter<g_array_size)
   {
      g_p_array[counter]=counter;
      counter++;
   }

   DoSomething();
   free(g_p_array);
   g_p_array=NULL;
   g_array_size=0;
}


Getting warmer.  In C where you don't have the luxury of classes

typedef struct _some_array
{
   unsigned long array_size;
   unsigned long* p_array;
}some_array;

void CreateArray(unsigned long size,some_array* array)
{
   array=(some_array*)malloc(sizeof(some_array));
   some_array->array_size=size;
   some_array->p_array=(unsigned long*)malloc(sizeof(unsigned long)*size);
}

//functions that do something with the array

void DestroyArray(some_array* array)
{
   if(NULL!=array)
   {
      if(NULL!=array->p_array)
      {
         free(array->p_array);
         array->p_array=NULL;
      }
      free(array);
      array=NULL;
   }
}


Using classes to make it pretty

class CSomeArray
{
   public:
   CSomeArray(unsigned long size);//constructor
   ~CSomeArray();//destructor

   unsigned long GetSize();
   unsigned long GetElement(unsigned long index);
   void SetElement(unsigned long index,unsigned long element);

   private:
   unsigned long* m_p_array;
   mutex m_mutex;
   unsigned long m_size;
}

CSomeArray::CSomeArray(unsigned long size)
{
   ASSERT(size>0);
   m_p_array=(unsigned long*)malloc(sizeof(unsigned long)*size);
   m_size=size;
}

CSomeArray::~CSomeArray()
{
   if(NULL!=m_p_array)
   {
      free(m_p_array);
      m_p_array=NULL;
   }
}

unsigned long CSomeArray::GetSize()
{
   return m_size;
}

unsigned long CSomeArray::GetElement(unsigned long index)
{
   ASSERT(index<m_size);
   ASSERT(m_p_array);
   m_mutex.lock();
   unsigned long element=m_p_array[index];
   m_mutex.unlock();
   return element;
}

unsigned long CSomeArray::SetElement(unsigned long index,unsigned long element)
{
   ASSERT(index<m_size);
   ASSERT(m_p_array);
   m_mutex.lock();
   m_p_array[index]=element;
   m_mutex.unlock();
}
Title: Re: Do any of you know C++?
Post by: Yes on October 21, 2019, 06:57:50 AM
Crouton, you have mixed malloc and free.  I'm not sure but I think that's UB.
I don't want to start a flame war over programming on a flat earth forum, so I'll just say that I strongly advice you not to use malloc/delete in C++.  Just use new/free.

Edit: I am a fool.  See below.
Title: Re: Do any of you know C++?
Post by: Crouton on October 21, 2019, 07:03:50 AM
I think you might have that mixed up there.  free() is the counterpart to malloc().  And new is the counterpart to delete.

https://en.cppreference.com/w/c/memory/malloc

I'm aware that malloc is old school.  I just never got used to new.  Not even sure if there's a technical reason behind it.  Maybe a cleaner syntax.
Title: Re: Do any of you know C++?
Post by: Yes on October 21, 2019, 07:06:04 AM
Today, I am the fool.
Title: Re: Do any of you know C++?
Post by: Crouton on October 21, 2019, 07:11:47 AM
Today, I am the fool.

No worries.

https://www.includehelp.com/cpp-tutorial/difference-between-new-and-malloc.aspx

Ah.  new invokes the constructor and delete invokes the destructor.  I didn't know that until I looked it up.  That would be handy in dealing with pointers to a class.
Title: Re: Do any of you know C++?
Post by: Username on October 21, 2019, 08:12:13 AM
Malloc makes a lot more sense in some situations, like game development and dealing with operations on large datasets.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 21, 2019, 12:30:08 PM
int size = sizeof(arr)/sizeof(arr[0]);
int size = sizeof(arr)/sizeof(int);

The size of the array divided by the size of the first element  / type.

There are other ways, or you can just keep track of it when you initialize it or allocate the memory for it via malloc.
I know that method but it doesn't seem to work very well when the array is not actually there and you only have a pointer to an array...
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 21, 2019, 12:33:07 PM
Terrible.  Never do this.

#define HEAP_ARRAY_SIZE 100

unsigned long g_heap_array[HEAP_ARRAY_SIZE];

void DoSomething()
{
   int counter=0;
   while(counter<HEAP_ARRAY_SIZE)
   {
       printf("%lu element %i \n",g_heap_array[counter],counter);
      counter++;
   }
}


A little less terrible.  Don't abuse the heap this way.

//on the heap
unsigned long g_array_size=0;
unsigned long* g_p_array=NULL;

void DoSomething()
{
   int counter=0;
   while(counter<g_array_size)
   {
       printf("%lu element %i \n",g_heap_array[counter],counter);
      counter++;
   }
}

void CreateArray()
{
   unsigned long arbitrary_array_size=10;
   g_array_size=arbitrary_array_size=10;;
   g_p_array=(unsigned long*)malloc(g_array_size*sizeof(unsigned long));
   int counter=0;
   while(counter<g_array_size)
   {
      g_p_array[counter]=counter;
      counter++;
   }

   DoSomething();
   free(g_p_array);
   g_p_array=NULL;
   g_array_size=0;
}


Getting warmer.  In C where you don't have the luxury of classes

typedef struct _some_array
{
   unsigned long array_size;
   unsigned long* p_array;
}some_array;

void CreateArray(unsigned long size,some_array* array)
{
   array=(some_array*)malloc(sizeof(some_array));
   some_array->array_size=size;
   some_array->p_array=(unsigned long*)malloc(sizeof(unsigned long)*size);
}

//functions that do something with the array

void DestroyArray(some_array* array)
{
   if(NULL!=array)
   {
      if(NULL!=array->p_array)
      {
         free(array->p_array);
         array->p_array=NULL;
      }
      free(array);
      array=NULL;
   }
}


Using classes to make it pretty

class CSomeArray
{
   public:
   CSomeArray(unsigned long size);//constructor
   ~CSomeArray();//destructor

   unsigned long GetSize();
   unsigned long GetElement(unsigned long index);
   void SetElement(unsigned long index,unsigned long element);

   private:
   unsigned long* m_p_array;
   mutex m_mutex;
   unsigned long m_size;
}

CSomeArray::CSomeArray(unsigned long size)
{
   ASSERT(size>0);
   m_p_array=(unsigned long*)malloc(sizeof(unsigned long)*size);
   m_size=size;
}

CSomeArray::~CSomeArray()
{
   if(NULL!=m_p_array)
   {
      free(m_p_array);
      m_p_array=NULL;
   }
}

unsigned long CSomeArray::GetSize()
{
   return m_size;
}

unsigned long CSomeArray::GetElement(unsigned long index)
{
   ASSERT(index<m_size);
   ASSERT(m_p_array);
   m_mutex.lock();
   unsigned long element=m_p_array[index];
   m_mutex.unlock();
   return element;
}

unsigned long CSomeArray::SetElement(unsigned long index,unsigned long element)
{
   ASSERT(index<m_size);
   ASSERT(m_p_array);
   m_mutex.lock();
   m_p_array[index]=element;
   m_mutex.unlock();
}


I don't really know what all that means, I guess I have some more stuff to learn here...
Title: Re: Do any of you know C++?
Post by: Yes on October 21, 2019, 12:51:19 PM
What's the code that you're working on?  Or problem you're trying to solve?  Is it just a matter of creating an array in one method, returning it, and iterating through it elsewhere?
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 21, 2019, 01:16:44 PM
What's the code that you're working on?  Or problem you're trying to solve?  Is it just a matter of creating an array in one method, returning it, and iterating through it elsewhere?
Say I create an array in one method (or rather a pointer to the array, which I think is how you do it?), I return it, and I pass it to another method, or function, or whatever you call it. Then in that second method I want to use the number of its elements. How do?
Title: Re: Do any of you know C++?
Post by: Crouton on October 21, 2019, 01:30:54 PM
What's the code that you're working on?  Or problem you're trying to solve?  Is it just a matter of creating an array in one method, returning it, and iterating through it elsewhere?
Say I create an array in one method (or rather a pointer to the array, which I think is how you do it?), I return it, and I pass it to another method, or function, or whatever you call it. Then in that second method I want to use the number of its elements. How do?

You're going to have to pass the number of elements in the array along with a pointer to the array as well.

void DoSomething(unsigned long* array,unsigned long array_length)
{
  //very important computer stuff
}

void StartSomething()
{
  unsigned long this_array[10];
  DoSomething(this_array,10);
}
Title: Re: Do any of you know C++?
Post by: Yes on October 22, 2019, 06:31:42 AM
Here's a more complete example using std::array, which bundles the array length with it.  You can pop this into https://www.onlinegdb.com/online_c++_compiler to check it out immediately.  I should reiterate that haven't used C++ on a daily basis for many years (mostly C# and SQL these days), so hopefully I haven't made another goof up.

Code: [Select]
#include <iostream>
#include <array>

std::array<float, 3>* MakeMyArray() {
    // `auto` tells the compiler to infer the type.
    // Both `auto` and `auto*` mean the same thing in this case, but I've included to * for emphasis.
    // Create a float array of length 3 on the heap and initialize it with the following values.
    // `new` constructs the object and returns the pointer to it.
    auto* arrPtr = new std::array<float, 3> {1.1f, 2.00002128f, 0};
    // Dereference the array and reassign one of the values.
    arrPtr->at(2) = 3.333f;
    // This returns a pointer to the array, not the array itself.  The array is on the heap.
    return arrPtr;
}

// The `template<size_t N>` business makes a UseArray that handles arrays of arbitrary size.
// This is not the only approach, but a fine one for what we're talking about.
template<std::size_t N>
void UseArray(std::array<float, N>* arrPtr) {
    std::cout << "Array length: " << N << std::endl;
    // Dereference the array and use fancy container iteration.
    for (auto &f : *arrPtr) {
        std::cout << f << std::endl;
    }
}

int main()
{
    std::cout << "Begin." << std::endl;

    // Again, `auto*` just means `std::array<float, 3>*` but with less keyboard involvement.
    auto* arrPtr = MakeMyArray();
    UseArray(arrPtr);

    std::cout << "End." << std::endl;
   
    delete arrPtr; // Be kind, please rewind.
    return 0;
}

This uses std::array specifically, since that's what we've been talking about.  This approach demands the array size be known at compile time (but with templates it doesn't have to be hardcoded like above).  Depending on your use case, std::vector may be more appropriate. 
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 22, 2019, 01:00:12 PM
What's the code that you're working on?  Or problem you're trying to solve?  Is it just a matter of creating an array in one method, returning it, and iterating through it elsewhere?
Say I create an array in one method (or rather a pointer to the array, which I think is how you do it?), I return it, and I pass it to another method, or function, or whatever you call it. Then in that second method I want to use the number of its elements. How do?

You're going to have to pass the number of elements in the array along with a pointer to the array as well.

void DoSomething(unsigned long* array,unsigned long array_length)
{
  //very important computer stuff
}

void StartSomething()
{
  unsigned long this_array[10];
  DoSomething(this_array,10);
}

That's annoying, I'm supposed to somehow find a way to return two different things from the method just to get the size of the array? C++ is a fuck.

Guess I'll just use the std arrays, it's simpler.
Title: Re: Do any of you know C++?
Post by: Yes on October 22, 2019, 01:26:53 PM
I can related to the sentiment.  But bare in mind that (compared to modern languages) C++ is very low level and avoids introducing any overhead that isn't explicitly requested.  So an array means "memory allocated for contiguous objects of fixed size", it does not mean "a basic container of known size."  Same deal with strings.  C/C++ strings are just characters in a row, hopefully terminated by a null character.  Bringing extra things like length is up to you.

A String literal in Java is not at all like a string literal (character array) in C/C++, and same goes with the array, even though they all have the same names.

If you want the convenience of Java's objects, you have to use (or create) objects that explicitly provide them.  The language literals themselves do not.  But don't worry, the standard library will likely have what you need for the basics.
Title: Re: Do any of you know C++?
Post by: Crouton on October 22, 2019, 01:38:17 PM
Agreed.

C/C++ really aren't ideal languages for casual programmers.  Java and C# fill that niche quite well.  I'm not sure why your professor even required this in C.  I'm going to assume that he hates you.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 22, 2019, 01:55:52 PM
Agreed.

C/C++ really aren't ideal languages for casual programmers.  Java and C# fill that niche quite well.  I'm not sure why your professor even required this in C.  I'm going to assume that he hates you.
The professor didn't, it's a textbook I am using right now, and also it's super possible that I may be required to use C++ later on. It's not just a casual thing. For whatever reason the scientific computing language of choice for my uni is Fortran (I guess because that's what the old professors know how to use better lol) but it's not that well used any more. Java is not that widely used for scientific purposes either because it's both not that fast to run and not that fast to code, so that was another weird choice. The preferred languages for scientific computing seem to be C++, Python (because it's super convenient), Matlab and Wolfram. Fortran is used too for some more specialized stuff and for the legacy code. We're already learning Matlab, some Wolfram, and Fortran, so I'm trying to learn C++, Python and Haskell (because it's super interesting from a mathematical perspective and gives you a lot of tools for understanding some stuff in abstract math) on my own. Python is fairly easy so I decided I'll just learn C++ first and then look at Python (and Haskell which is super weird in many ways).
Title: Re: Do any of you know C++?
Post by: Crouton on October 22, 2019, 02:21:03 PM
Fortran I've heard of but I've never used.  Same for matlab. The people who live in the analog world love that one though. Haskell I've never seen before.

Memory management in c is tedious but it's also very precise. This precision becomes very important for dealing directly with hardware and also real time programming. So just be aware that there's a reason it is the way it is.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 22, 2019, 03:04:09 PM
Fortran I've heard of but I've never used.  Same for matlab. The people who live in the analog world love that one though. Haskell I've never seen before.

Memory management in c is tedious but it's also very precise. This precision becomes very important for dealing directly with hardware and also real time programming. So just be aware that there's a reason it is the way it is.

Yeah, I guess it really is useful... But it's annoying.

Fortran is fairly simple in general but also a bit archaic. Haven't had much of a chance to look at it since the courses haven't started yet. It's fast though and good to work with arrays and matrices so physicists and applied math people like it. Not terribly useful for anything else.

Matlab is amazing, it's not a language in the same sense as the rest though, it's an environment too. Think of Matlab as a glorified graphing calculator, that you can program to do any sort of complex sequence of operations that you want, plus a whole bunch of other crazy stuff. It's definitely not just people who live in the analogue world who like it. It's almost indispensable for engineers, physicists, etc. Great for doing math, but it has its limitations. Wolfram Mathematica is similar.

Haskell is a weird one. It doesn't really look like any other language which is why it kinda freaks some people out. It's a functional programming language that makes use of a lot of stuff from category theory. A lot of people think it has no practical application and it's just an academic language but it actually has a lot of uses and it is somewhat famously used by Facebook for spam filters etc, it's just that people are kinda freaked out by how unfamiliar it is. In fact it is even said that novice programmers understand it easier because they're not as used to the paradigm of "normal" languages. Others say learning it spoils other languages, but idk about that.
Title: Re: Do any of you know C++?
Post by: Username on October 23, 2019, 12:07:27 AM
Matlab / Maple / Mathematica are pretty slick. Used them for some analysis the other day for work junk.

I'm surprised you didn't list R.
Title: Re: Do any of you know C++?
Post by: Yes on October 23, 2019, 05:39:45 AM
Java is not that widely used for scientific purposes either because it's both not that fast to run and not that fast to code, so that was another weird choice.
Performance differences are vicious rumors until they're measured.

I don't have much experience in science-focused programming, but I can tell you that the quality of code I've seen written by professional engineers has been hilariously abysmal.  The magnitude of linear searches is enough to make a CPU fan whimper.  People whose life focus isn't programming don't output great programming, who knew?  Anyway, my point is that you probably don't need any of the performance optimizations that lower-level languages might possibly grant a highly skilled programmer.  Because you're not a highly skilled programmer.  (And that's okay.)  You'll spend more time banging your head against low-level constructs than you will save by using them.  So you're better off using an easy language/environment or whatever you're familiar with.  Even using Excel to smoke some numbers for ten minutes is overall faster than opening your IDE and writing, compiling, debugging, testing, and inevitably drinking.

Although I don't want to sound discouraging.  Pursuing new skills is always worthwhile, even if it's just for the mental exercise.  Just keep the perspective in mind that you don't need C or C++ to make a program that is perfectly adequate for your needs.
Title: Re: Do any of you know C++?
Post by: Username on October 23, 2019, 10:03:03 AM
More than that, scientists look down at programming as if its "choose your own adventure." They don't understand the complexities of large systems and codebases.


Speaking to using c for science, if you want to deal with large sets of data efficiently it might make sense to use a language designed for this instead.
Title: Re: Do any of you know C++?
Post by: Crouton on October 23, 2019, 11:06:51 AM
Don't let them discourage you Pez.  It's just computer science.  It's not brain surgery.

I've been writing C for over 20 years and I believe that Beyonce and Mariah Carey are the same person!
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 11:16:34 AM
Matlab / Maple / Mathematica are pretty slick. Used them for some analysis the other day for work junk.

I'm surprised you didn't list R.
Afaik there isn't that much of a point to learn R for that sort stuff of you know the others. I might be wrong!
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 11:29:24 AM
Performance differences are vicious rumors until they're measured.
It's not just rumours. For example I wanted to make a simple program that generates a few million prime numbers, sorts them by what their last digit is, displays the percentage of primes that belong to each category (the result is that the percentages of 1, 3, 7 and 9 tend to 25%, which is connected to Dirichlet's theorem, but also I wanted to see if at any point 1 or 9 go above 25%, which they don't seem to, which is interesting though I think the reason why that is isn't as interesting as it first seems), but also counts how much time it took to evaluate for various ranges of primes, so that I can plot a graph of the time this takes. So it has to run this already more intensive than it sounds program quite a few times over and over. Java took a noticeably longer time to complete this stuff once I sorted out most of the pointer shit in C++ and made it not suck. I know that if I made it even a bit more complicated I'd be staring at a blank command window for minutes just to get a wrong result and have to go looking for the place where I fucked up.
Title: Re: Do any of you know C++?
Post by: Username on October 23, 2019, 11:41:57 AM
Matlab / Maple / Mathematica are pretty slick. Used them for some analysis the other day for work junk.

I'm surprised you didn't list R.
Afaik there isn't that much of a point to learn R for that sort stuff of you know the others. I might be wrong!
Ah, I just knew it was a big one in data science and have had it come up in various online classes I take to keep relevant - but I don't have a lot of experience with it. I'll have to look into that. Thanks
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 11:58:27 AM
Matlab / Maple / Mathematica are pretty slick. Used them for some analysis the other day for work junk.

I'm surprised you didn't list R.
Afaik there isn't that much of a point to learn R for that sort stuff of you know the others. I might be wrong!
Ah, I just knew it was a big one in data science and have had it come up in various online classes I take to keep relevant - but I don't have a lot of experience with it. I'll have to look into that. Thanks
Yeah I've heard some stuff about R but I don't really know that much about its pros and cons. Apparently it's good for statisticians? Might be worth looking at it but I can only learn so much stuff and what I listed is more than enough for me.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 12:06:50 PM
There's also Julia which is becoming more popular in scientific computing but it's a fairly recent language and not that widely used.
Title: Re: Do any of you know C++?
Post by: Yes on October 23, 2019, 12:49:39 PM
Java took a noticeably longer time to complete this stuff once I sorted out most of the pointer shit in C++ and made it not suck.
Something is very amiss here.  If it takes more than a second or two to generate a million prime numbers, then the first place you should start looking is your algorithm, not the programming language.

If you want, I can show you a sample program that outputs the last digit percentages from the 5,761,455 prime numbers found in the first 100,000,000 integers.  I wrote one just to make sure my expectations wasn't the something that was amiss.  On onlinegdb.com it takes about 2 to 6 seconds (quite a variation, but that's what happens with someone else's server).

By the way, did you get this idea from a recent 3Blue1Brown video?  I love that guy.



Actually, since I'll be gone for the day pretty soon, here's the code in case you want to take a look.  if you don't then please ignore.
Code: [Select]
import java.util.BitSet;

public class Main
{
public static void main(String[] args) {
    long startTime = System.currentTimeMillis();
   
BitSet primes = loadPrimes(100_000_000);
long loadedTime = System.currentTimeMillis();

        int[] lastDigits = new int[10];
        int total = 0;
        for (int i = 2; i != -1; i++) {
            i = primes.nextSetBit(i);
            if (i == -1) break;
            int digit = i % 10;
            lastDigits[digit]++;
            total++;
        }
       
        for (int digit = 0; digit < lastDigits.length; digit++) {
            float fraction = ((float)lastDigits[digit])/((float)total);
            System.out.printf("%d: %f%%\t(%d)%n", digit, fraction*100, lastDigits[digit]);
        }
       
        assert total == primes.cardinality();
       
        System.out.printf("%nPrime count: %d%n", total);
        System.out.printf("Primes took %d milliseconds.%n", loadedTime - startTime);
        System.out.printf("Everything took %d milliseconds.%n", System.currentTimeMillis() - startTime);
}

private static BitSet loadPrimes(int size) {
    // Sieve of Eratosthenes, or so Google tells me.
   
    // We'll use a BitSet to keep track of which numbers are primes.
    // It's an efficient way to store lots of indexable booleans.
    BitSet primes = new BitSet(size+1);
    primes.set(1, size, true); // Initialize to true.  Next we'll knock them out.
   
        for (int factor = 2; factor*factor <= size; factor++) {
            if (primes.get(factor)) {
                for (int j = factor; factor*j <= size; j++) {
                    primes.clear(factor*j); // All multiples are not prime
                }
            }
        }
        return primes;
}
}

Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 12:59:46 PM
Something is very amiss here.  If it takes more than a second or two to generate a million prime numbers, then the first place you should start looking is your algorithm, not the programming language.
It only takes a fraction of a second to generate one million primes. The issue is that that's not what it does. It generates 1 million, then it generates again 6 million, then 11, and all the way up to 101, and also does the other stuff I mentioned. C++ only takes about 6 seconds to do all that stuff I mentioned for 100 million primes in my program, so it's probably alright.

 
Quote
By the way, did you get this idea from a recent 3Blue1Brown video?  I love that guy.

Yeah that is where I got the idea from! I thought it would be a simple enough program to start learning some C++ so that I can use it for more complex exercises. I noticed in his vid that the ones ending in 3 and 5 were always more and I wanted to see if it's something that persists.
Title: Re: Do any of you know C++?
Post by: Username on October 23, 2019, 01:29:30 PM
I find it hard to believe that given the same algorithm java will out perform c. You have a virtual machine that has to run in between your compiled code and the metal. This isn't backed up with recent data, but theoretically java should almost always out perform given ideal implementation on both java and c. Whether this is notable I imagine depends on scale.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 23, 2019, 01:38:56 PM
I find it hard to believe that given the same algorithm java will out perform c. You have a virtual machine that has to run in between your compiled code and the metal. This isn't backed up with recent data, but theoretically java should almost always out perform given ideal implementation on both java and c. Whether this is notable I imagine depends on scale.
I am a bit confused, are you saying Java outperforms C or the opposite? Because I said C was faster for me.
Title: Re: Do any of you know C++?
Post by: Username on October 24, 2019, 11:13:12 AM
I find it hard to believe that given the same algorithm java will out perform c. You have a virtual machine that has to run in between your compiled code and the metal. This isn't backed up with recent data, but theoretically java should almost always out perform given ideal implementation on both java and c. Whether this is notable I imagine depends on scale.
I am a bit confused, are you saying Java outperforms C or the opposite? Because I said C was faster for me.
Ah sorry, I mistyped; c should out perform. I was responding to Yes.
Title: Re: Do any of you know C++?
Post by: Yes on October 24, 2019, 11:36:18 AM
C has significantly less overhead, so a properly-written C program should always beat a properly-written equivalent program in Java, no argument about that.  However, when you expand the performance metrics from just computation time to developer time plus computation time, one might get a different conclusion.  That's what I meant went I said it may be better to just have Excel smoke numbers for 10 minutes that to take the time to construct a properly-written program.  It depends on what the goals are.

Unrelated assertion: there are strange ways in which an improperly-written Java program can beat an equivalently improperly-written C program.  A smart JVM has the benefit of optimization based on runtime analysis.  However, in practice, that runtime optimization is more useful to help reduce the performance gap rather than to exceed it.
Title: Re: Do any of you know C++?
Post by: Pezevenk on October 24, 2019, 12:17:12 PM
However, when you expand the performance metrics from just computation time to developer time plus computation time, one might get a different conclusion.
Well that comes with experience though. Plus if you run the same thing many times, even if the development time was much larger it's gonna beat the slower language in the long run.
Title: Re: Do any of you know C++?
Post by: Pezevenk on December 31, 2019, 11:36:32 AM
Well I figured it out by now lol
Title: Re: Do any of you know C++?
Post by: Bullwinkle on December 31, 2019, 04:48:52 PM
Pretty sure I just got brain cancer from reading this thread. 
Title: Re: Do any of you know C++?
Post by: FlatAssembler on January 01, 2020, 12:04:23 PM
I've done some measurements about how fast code compilers for various languages produce, and, as crazy as it sounds, ADA, not C, seems to give the best performance for an equivalent code:
(https://github.com/FlatAssembler/ArithmeticExpressionCompiler/raw/master/MergeSort/TestResults/output_of_tester1_as_a_diagram.png)
AEC is the programming language I've designed and made a compiler (https://github.com/FlatAssembler/ArithmeticExpressionCompiler) for, and, unsurprisingly, it produces the worst code for an equivalent program. And the difference is so profound that the C and ADA implementations of QuickSort run faster in the worst case (when the array is completely sorted or inverse-sorted) than AEC implementation of MergeSort runs in that case (and MergeSort should theoretically run equally fast on all permutations of the array):
(https://github.com/FlatAssembler/ArithmeticExpressionCompiler/raw/master/MergeSort/TestResults/output_of_tester2_as_a_diagram.png)
This really makes you wonder how much algorithms can be blamed for programs being slow? Compilers the programmer uses seem to play a much greater role than the algorithms that the programmer chooses to use. And it's not really languages that the programmer uses, it's the compilers: AEC is lower level than C or ADA are, I've also even done some stuff in Assembly rather than AEC itself, yet its compiler can and does produce inferior code. So, how should the programmers be educated if we want them to produce programs that run fast? Teaching them algorithms helps very little, and so does teaching them to try to write performance-sensitive code in Assembly, it might even do more harm than good.
If the program is slow, it's usually because of either over-engineering (that's why Word is so slow, it does so many stuff nobody needs), or because of a usage of a wrong framework or a compiler, or incorrect usage of some framework or a compiler. Algorithms play little role, and an attempt to write in a very low-level language (or, worse yet, a programming language you designed to be low-level, and therefore supposedly fast) is usually shooting yourself in the foot.
Title: Re: Do any of you know C++?
Post by: Crouton on January 01, 2020, 12:40:18 PM
I've got to say those results look a bit odd.

The gnu c compiler has an option to bang out an lst file during compilation. I'd check it to see if the compiler is making some weird mistake.
Title: Re: Do any of you know C++?
Post by: Pezevenk on January 01, 2020, 04:39:23 PM
I got an Intel compiler for free (because of my uni) and I was wondering if it produced better results. I haven't tried it much yet but in a couple of examples I tried to measure the execution time it seemed like Visual C++ did an equal or marginally better job. Supposedly the Intel one should be somewhat better though, or at least that's what some people were saying. Who knows...

In other news, C++ doesn't drive me crazy any more, I kinda figured out how to do the things I could do in Java and I kinda like the way it is written. Arrays still give me a hard time sometimes, which is why I mostly use the standard library vector instead.
Title: Re: Do any of you know C++?
Post by: Crouton on January 01, 2020, 05:14:44 PM
The Intel compiler has support for a lot of the hardware features of their processors.  Other than that it isn't necessarily more sophisticated than any other compiler though it is built with performance in mind.

Microsoft's compiler I've never had a problem with but all things being equal I'd stick with gnu whenever possible just because it's ubiquitous.
Title: Re: Do any of you know C++?
Post by: rabinoz on January 01, 2020, 07:04:47 PM
Pretty sure I just got brain cancer from reading this thread.
Now you C Y I never got past C. I'm too much of a scatter-brain to come to grips with Object-oriented programming languages.
Title: Re: Do any of you know C++?
Post by: FlatAssembler on January 02, 2020, 07:39:42 AM
I've got to say those results look a bit odd.

The gnu c compiler has an option to bang out an lst file during compilation. I'd check it to see if the compiler is making some weird mistake.
I was using CLANG 9.0 (the latest stable release). Here (https://github.com/FlatAssembler/ArithmeticExpressionCompiler/blob/master/MergeSort/msort.s) is the assembly CLANG 9.0 generates for MergeSort in C, and here (https://github.com/FlatAssembler/ArithmeticExpressionCompiler/blob/master/QuickSort/qsort.s) is the assembly it generates for QuickSort.
Title: Re: Do any of you know C++?
Post by: Username on January 06, 2020, 08:11:25 AM
It's not really fair to reduce it down simply to the algorithm. One can make interesting implementation choices with any given algorithm in any given language that will affect the speed quite a bit depending on language, hardware, etc.

I do agree when a program is slow its often due to poor engineering, but given this is not the case, language choice can matter as can specific implementation details within a language and algorithm.

Also language choice makes a huge difference in some circumstances, and sometimes will force things that would otherwise be well engineered in other languages to be poorly engineered. The byte-swapping code comes to mind in Myth 1, 2 and 3 as well presumably before it Marathon. In c, its extremely efficient and the code itself is maintainable and well engineered. I'd have a hard time imagining the same could be achieved in Java. In fact, I would assume it impossible to gain this speed benefit in Java due to the JVM.
Title: Re: Do any of you know C++?
Post by: Pezevenk on January 06, 2020, 02:12:54 PM
It's not really fair to reduce it down simply to the algorithm. One can make interesting implementation choices with any given algorithm in any given language that will affect the speed quite a bit depending on language, hardware, etc.

I do agree when a program is slow its often due to poor engineering, but given this is not the case, language choice can matter as can specific implementation details within a language and algorithm.

Also language choice makes a huge difference in some circumstances, and sometimes will force things that would otherwise be well engineered in other languages to be poorly engineered. The byte-swapping code comes to mind in Myth 1, 2 and 3 as well presumably before it Marathon. In c, its extremely efficient and the code itself is maintainable and well engineered. I'd have a hard time imagining the same could be achieved in Java. In fact, I would assume it impossible to gain this speed benefit in Java due to the JVM.

Also a lot of the programs used for scientific computing are performance intensive but very bare bones, they're kinda hard to over-engineer. Anyways, I think the number one thing in these cases is finding a way to do things that will help you do things faster before you ever try to implement it. I remember a problem I was trying to solve (I don't remember exactly what it was), and I'm like, OK, I can implement an algorithm for that. It seemed like a very computationally intensive task, but I tried to do it the obvious way, with some optimizations I came up with. So anyways, I'm done, and I'm thinking "OK, these optimizations were super smart, this will definitely run very fast!" and so I try it for some 15 digit number or whatever and it worked pretty good indeed, it only took like 5 seconds or what seemed to be a very complex problem. And then I noticed that the problem wanted me to solve it for a 150 digit number, which was practically impossible given my algorithm. Turns out you had to follow a completely different method to solving the problem, and if you did that the program wouldn't even take a second to execute.
Title: Re: Do any of you know C++?
Post by: Yes on January 07, 2020, 03:09:56 AM
Anyways, I think the number one thing in these cases is finding a way to do things that will help you do things faster before you ever try to implement it.
Your insight is wisdom.
Title: Re: Do any of you know C++?
Post by: FlatAssembler on May 25, 2020, 09:54:36 AM
Just made my first useful program in C++: a program (https://github.com/FlatAssembler/Notes-To-WAV-converter) that converts musical notes stored in a text file to WAV. It's written entirely in C++11 and doesn't use any external library.
Title: Re: Do any of you know C++?
Post by: Username on May 26, 2020, 09:27:32 AM
What is one practical use for that?

Also looks like trash:

https://codereview.stackexchange.com/questions/241705/converting-musical-notes-to-wav

It's hard to believe anyone that wrote this code wrote any sort of language at all.
Title: Re: Do any of you know C++?
Post by: Username on May 26, 2020, 11:28:28 AM
Yeah okay, I was being a dick (though you did call me a liar for stating my profession of which I have 20+ years of experience). You are obviously still learning. If you'd like constructive criticism post what you have so far and I'd be happy to review it.

Title: Re: Do any of you know C++?
Post by: FlatAssembler on May 28, 2020, 05:13:51 AM
What is one practical use for that?

Also looks like trash:

https://codereview.stackexchange.com/questions/241705/converting-musical-notes-to-wav

It's hard to believe anyone that wrote this code wrote any sort of language at all.
Well, I don't know if you consider that practical, but it can be used for music composition. I am not really an expert in C++, I've written the compiler for my programming language in JavaScript. I don't know about you, but my perception is that C++ sucks as a language. It's enough high-level to make it inconvenient for kernel development, but getting basic things done in it, such as opening a graphic window, or string manipulation, is a nightmare. It got slightly better in C++11 (native support for regular expressions, the "stof" command...), but it's still very bad. Only writing binary files is slightly better done than in JavaScript, everything else is worse. Anyway, here is the code I've written thus far:
Code: [Select]
#include <iostream>
#include <fstream>
#include <string>
#include <cmath>
#include <map>

std::map<std::string, float> notes;
int sampleRate = 8192; //I don't think it's at all my fault that some players claim to support WAV format, but fail to play a WAV file that has lower sample rate than "standard".

int main(int argc, char **argv) {
notes["a"] = 220;
notes["as"] = 233;
notes["b"] = 247;
notes["C"] = 262;
notes["Cs"] = 277;
notes["D"] = 293;
notes["Ds"] = 311;
notes["E"] = 329;
notes["F"] = 349;
notes["Fs"] = 370;
notes["G"] = 391;
notes["Gs"] = 415;
notes["A"] = 440;
notes["As"] = 466;
notes["H"] = 493;
notes["C5"] = 523;
notes["Cs5"] = 554;
notes["D5"] = 587;
notes["Ds5"] = 622;
notes["E5"] = 659;
if (argc < 2) {
std::cerr << "Please supply the text file with notes as an argument."
<< std::endl;
return 1;
}
std::ifstream input(argv[1]);
if (argc > 2)
sampleRate = atoi(argv[2]);
if (!input) {
std::cerr << "Can't open \"" << argv[1] << "\" for reading!"
<< std::endl;
return 1;
}
FILE *wav = std::fopen("output.wav", "wb");
if (!wav) {
std::cerr << "Can't open \"output.wav\" for output!" << std::endl;
return 1;
}
bool isLittleEndian;
int testNumber = 0x10;
std::fwrite(&testNumber, sizeof(int), 1, wav);
std::fclose(wav);
wav = std::fopen("output.wav", "rb");
char testCharacter = 0;
std::fread(&testCharacter, 1, 1, wav);
std::fclose(wav);
if (testCharacter == 0x10) //The logic is: if the C library uses big endian for writing binary files, now "testCharacter" will still contain 0.
isLittleEndian = true;
else
isLittleEndian = false;
wav = std::fopen("output.wav", "wb");
if (isLittleEndian)
std::fprintf(wav, "RIFF"); //ASCII for 0x52494646, the magic number that WAV files start with.
else
std::fprintf(wav, "RIFX"); //Big endian WAV file starts with magic number 0x52494658, or, in ASCII, "RIFX".
int32_t ChunkSize = 36 + 8 * sampleRate * 2;
std::fwrite(&ChunkSize, 4, 1, wav);
std::fprintf(wav, "WAVEfmt "); //The beginning of the header.
int32_t Subchunk1Size = 16; //PCM header is always 16 bytes.
std::fwrite(&Subchunk1Size, 4, 1, wav);
int16_t AudioFormat = 1; //PCM format.
std::fwrite(&AudioFormat, 2, 1, wav);
int16_t NumChannels = 1; //MONO audio.
std::fwrite(&NumChannels, 2, 1, wav);
int32_t SampleRate = sampleRate;
std::fwrite(&SampleRate, 4, 1, wav);
int32_t ByteRate = 2 * sampleRate; //Since we are using 16 bits per sample, and "sampleRate" samples per second.
std::fwrite(&ByteRate, 4, 1, wav);
int16_t BlockAlign = 2; //Each block is two bytes.
std::fwrite(&BlockAlign, 2, 1, wav);
int16_t BitsPerSample = 16;
std::fwrite(&BitsPerSample, 2, 1, wav);
std::fprintf(wav, "data");
while (!input.eof()) {
std::string currentNote;
input >> currentNote;
if (currentNote.substr(0, 1) == "#") //Comment
{
while (!input.eof() && input.get() != '\n')
continue;
continue;
}
if (currentNote.length() == 0)
break;
std::string durationString = "";
int i = 0;
while ((currentNote[i] >= '0' && currentNote[i] <= '9')
|| currentNote[i] == '.') {
durationString += currentNote.substr(i, 1);
i++;
}
std::cerr << "Read note name \"" << currentNote
<< "\", the duration string is: " << durationString
<< std::endl;
int noteDuration = 3 * sampleRate / std::stof(durationString);
std::string fullNoteName = currentNote.substr(i);
if (std::stof(durationString) == 0
|| std::isnan(std::stof(durationString))
|| (notes[fullNoteName] == 0 && fullNoteName != "P"
&& fullNoteName.substr(0, 3) != "Hz(")) {
std::cerr << "Can't interpret the note name \"" << currentNote
<< "\" or the duration number " << durationString
<< ", aborting!" << std::endl;
std::fclose(wav);
input.close();
return 1;
}
std::cerr << "Playing note \"" << fullNoteName << "\" for "
<< noteDuration << " samples." << std::endl;
float currentFrequency = notes[fullNoteName];
if (fullNoteName.substr(0, 3) == "Hz(")
currentFrequency = std::stof(fullNoteName.substr(3));
std::cerr << "Frequency is " << currentFrequency << "Hz." << std::endl;
for (int i = 0; i < noteDuration; i++) {
float baseFrequency = std::sin(
2 * M_PI * currentFrequency * i / sampleRate)
* std::pow(2, 14);
float secondHarmony = std::sin(
2 * M_PI * 2 * currentFrequency * i / sampleRate + M_PI / 4)
* std::pow(2, 12);
float thirdHarmony = std::sin(
2 * M_PI * 3 * currentFrequency * i / sampleRate + M_PI / 2)
* std::pow(2, 10);
float fourthHarmony = std::sin(
2 * M_PI * 4 * currentFrequency * i / sampleRate - M_PI / 4)
* std::pow(2, 9);
float currentAmplitude = (baseFrequency + secondHarmony
+ thirdHarmony + fourthHarmony)
* std::exp(-(float) (2 * i) / (sampleRate)); //Attenuation.
int16_t numberToBeWritten =
(fullNoteName == "P") ? (0) : (currentAmplitude);
numberToBeWritten += std::rand() % (1 << 8) - (1 << 7); //A bit of noise makes it sound better.
std::fwrite(&numberToBeWritten, 2, 1, wav);
}
}
input.close();
std::fclose(wav);
}