Author Topic: ARDUINO: MAP function question  (Read 1429 times)

0 Members and 1 Guest are viewing this topic.

Offline Excavatoree

  • Frequent Contributor
  • **
  • Posts: 841
  • Country: us
ARDUINO: MAP function question
« on: July 11, 2019, 07:20:00 pm »
In a project described on someone's web page, the designer had this line in his or her Arduino code:

newvariable = MAP(whatever, 0, 1023, 0, 1023);

My very meager understanding of the MAP function leads me to believe that this statement does nothing, and the MAP function is not necessary.  Am I missing something?  Why would someone do that?  Doesn't the statement, as written take a value from 0 to 1023, and map it to the same value?   
 

Offline blueskull

  • Supporter
  • ****
  • Posts: 13768
  • Country: cn
  • Power Electronics Guy
Re: ARDUINO: MAP function question
« Reply #1 on: July 11, 2019, 07:31:40 pm »
I don't know what MAP() does. I know what map() does, though. C/C++ is case sensitive.

If you meant map(), then you're right, it doesn't do anything, but it's there for future use (scaling), so the code is easily expandable by just modifying literals.
 
The following users thanked this post: Excavatoree

Offline Excavatoree

  • Frequent Contributor
  • **
  • Posts: 841
  • Country: us
Re: ARDUINO: MAP function question
« Reply #2 on: July 11, 2019, 07:34:31 pm »
Sorry, I typed from memory, and am used to situations where functions are capitalized.    I'm thankful the Arduino IDE will flag those errors for me as they occur.

As you can see, my experience is limited and I wanted to rule out some not obvious functionality.   I'm not a programmer, but I know there are some simple tricks that often are not intuitive to people who lack experience.
« Last Edit: July 11, 2019, 07:37:41 pm by Excavatoree »
 

Offline cv007

  • Frequent Contributor
  • **
  • Posts: 506
Re: ARDUINO: MAP function question
« Reply #3 on: July 11, 2019, 08:10:20 pm »
Just go to the source to find out what it does-

https://github.com/arduino/ArduinoCore-avr/blob/master/cores/arduino/WMath.cpp

the same thing will be somewhere in your Ardduino installation.
 

Offline Excavatoree

  • Frequent Contributor
  • **
  • Posts: 841
  • Country: us
Re: ARDUINO: MAP function question
« Reply #4 on: July 12, 2019, 12:42:30 am »
Just go to the source to find out what it does-

https://github.com/arduino/ArduinoCore-avr/blob/master/cores/arduino/WMath.cpp

the same thing will be somewhere in your Ardduino installation.

I did that, and determined that the statement did nothing.  I thought "surely that isn't correct.  The author must have added it for a reason.  I just don't see it."  So I re-read the material, and sought more.  After some study, I still came to the conclusion that the statement did nothing.  However, I'm inexperienced, and thought "certainly I'm missing something.  That's why I asked."   Generally, when one lacks experience, it's best to assume one is missing something.

I'm certainly smart enough to RTFM, and I did so.  I only asked a question to be sure my interpretation was correct.
 

Offline Rick Law

  • Super Contributor
  • ***
  • Posts: 2834
  • Country: us
Re: ARDUINO: MAP function question
« Reply #5 on: July 12, 2019, 06:26:55 pm »
(I think this exceeds the normal definition of a reply and drifted into the "rant" category)

I think "map" function is a misguided attempt to make programming "easier" for everybody.  It has been as successful and as deadly as "easy ways to do heart surgery for DIY'ers".

/* *** */

If you can answer this question, you don't need the map() function:

In a class of 1234 students, 6.7% passed; how many student passed?
That is to "map" 6.7% from 100 (definition of percent) into 1234 (actual sample).

If one can't answer that question, learning more math will help with understanding EE, politics, economy, history... it will even help in understanding cooking recipes.

/* *** */

I said deadly in the first paragraph, there is a reason...   It was just around the time when software became suspect for that LION air crash, just around that time I was at a tire-repair store waiting on some tire work.  The waiting room TV was showing a Microsoft elementary school project working with what appears to be 3rd/4th graders  "programming" by (using some Microsoft developed tools) dragging cartoon icons around to make a "working application".  The talking heads on the show was amazed at how programming was easy and that kids would in no time be making 6 figures automating everything...  No wonder programmers are getting no respect these days.

No doubt there are a few 10 year-olds who knows more math than most college grads can ever dream of, but to merely assume that math and other basics are irrelevant is...  well, as foolish as thinking: well, start as a janitor at the hospital, work hard, get promoted to "orderly", then in time, get promoted as nurse, then promoted doctor, then heart surgeon.  Heck, even a six year old can cut with a knife, who needs a decade of education just to do a heart bypass.  Anyone can do it.
 
The following users thanked this post: Excavatoree

Online Ian.M

  • Super Contributor
  • ***
  • Posts: 8640
Re: ARDUINO: MAP function question
« Reply #6 on: July 12, 2019, 07:27:41 pm »
https://en.wikipedia.org/wiki/Cargo_cult_programming

Unfortunately *far* too common in the Arduino community due to de-emphasis  of formal training in procedural programming.
 
The following users thanked this post: Excavatoree, Dave

Offline sokoloff

  • Super Contributor
  • ***
  • Posts: 1403
  • Country: us
Re: ARDUINO: MAP function question
« Reply #7 on: July 12, 2019, 07:59:24 pm »
I think a lot of the crap code we see in the Arduino ecosystem is more of a positive sign (that artists and other non-programmers are attempting programming and at least somewhat succeeding) than a negative sign (that we have unwashed mashes trying to do things that only trained priests should be doing).

Sure, there's crap code out there, but I can guarantee that I've seen just as dumb from CD-degree holding programmers working directly for me (at a prior company).
 

Online djacobow

  • Super Contributor
  • ***
  • Posts: 1066
  • Country: us
  • takin' it apart since the 70's
Re: ARDUINO: MAP function question
« Reply #8 on: July 12, 2019, 08:02:32 pm »
Wow, that WMath.h is barftastic.

First, yes, that map() function is something that probably doesn't warrant inclusion in a basic library.

Second, when I want to scale between ranges like that, I usually am dealing with different types, too, so this function probably isn't even what I want.

Third, the name is terrible, and will not meet the expectations of people who are familiar with other languages where map is either a key-value datastructure (c++ STL) or a function that applies a function to each element of an array and returns an array of the results.

Fourth (mostly personal peeve), I am tired of seeing "int" and "long". Nobody ever remembers exactly what they are on platform X. I wish everyone would just use stdint types. (int8_t, uint32_t, etc).

Finally, isn't:

Code: [Select]
long random(long howbig)
{
  if (howbig == 0) {
    return 0;
  }
  return random() % howbig;
}

subtly buggy? This will not return a uniform distribution of results in the specified range. The effect is most pronounced if howbig is close to the maximum value returned by random(). This effect might be small, but when people want "random" numbers, sometimes they really need them.

It's easier to see this effect if you shrink everything down. Let's pretend we have instead uint8_t rand8() and it returns [0,255], and you implement uint8_t rand8(uint8_t howbig) using simple modulo as above.

If we repeatedly call rand8(253) you'll see that this will generate more 2x as many 0's, 1's, and 2's than it does any other value 3-252.

 
 
The following users thanked this post: Ian.M, rhodges

Offline Nominal Animal

  • Super Contributor
  • ***
  • Posts: 1725
  • Country: fi
    • My home page and email address
Re: ARDUINO: MAP function question
« Reply #9 on: July 13, 2019, 03:08:02 am »
The integer/long version of Arduino map() function is broken/incorrect if the mapped range is inverted, and does not round results correctly.  I recently posted a suggested replacement (elsewhere, probably should have posted to Arduino forums/github):
Code: [Select]
template <class T, class A, class B, class C, class D>
long map(T _x, A _x_min, B _x_max, C _out_from, D _out_to, typename std::enable_if<std::is_integral<T>::value >::type* = 0)
{
long x = _x, x_min = _x_min, x_max = _x_max, out_from = _out_from, out_to = _out_to;
long x_range = x_max - x_min, out_range = out_to - out_from, r;

// (1 - abs(r/x_range)) is the smallest fraction rounded away from zero.
// The sign of r is the same as the sign of x_range*out_range.
if (x_range > 0) {
if (out_range > 0) {
r = (x_range - 1) / 2;
} else
if (out_range < 0) {
r = (1 - x_range) / 2;
} else {
r = 0;
}
} else
if (x_range < 0) {
if (out_range > 0) {
r = (x_range + 1) / 2;
} else
if (out_range < 0) {
r = (-1 - x_range) / 2;
} else {
r = 0;
}
} else {
r = 0;
}

return out_from + ((x - x_min) * out_range + r) / x_range;
}
In particular, this version produces the same answer (long)round(map((float)x, (float)xmin, (float)xmax, (float)ymin, (float)ymax)) does.  If the ranges are literals, GCC does optimize the if clauses away, effectively compiling just that final line with constants.

If it isn't obvious, r in the code is a constant that provides the correct rounding: halfway away from zero.
 
The following users thanked this post: Excavatoree, thm_w, rstofer

Offline Nominal Animal

  • Super Contributor
  • ***
  • Posts: 1725
  • Country: fi
    • My home page and email address
Re: ARDUINO: MAP function question
« Reply #10 on: July 13, 2019, 03:30:20 am »
I do love Xorshift* generators. For example,
Code: [Select]
uint64_t xorshift32_state = 1;  /* Any nonzero seed will work */

static inline uint32_t xorshift32(void)
{
    xorshift32_state ^= xorshift32_state >> 12;
    xorshift32_state ^= xorshift32_state << 25;
    xorshift32_state ^= xorshift32_state >> 27;
    return (xorshift32_state * UINT64_C(2685821657736338717)) >> 32;
}
passes all BigCrush tests, which makes it pretty darn good.  I'd use this on all 64-bit architectures, as well as on 32-bit microcontrollers with hardware multiplication, or when the randomness is important.  The period is 264-1, and any 64-bit state except zero works as a seed.  Other variants exist if this is too "slow".

It is definitely fast enough for the exclusion method.  Using a couple of helper structures and functions to define ranges:
Code: [Select]
struct u32range {
    uint32_t  mask;
    uint32_t  limit;
    uint32_t  offset;
};

struct i32range {
    uint32_t  mask;
    uint32_t  limit;
    int32_t  offset;
};

static inline struct u32range  set_u32range(uint32_t umin, uint32_t umax)
{
    struct u32range  result;

    if (umin > umax) {
        result.limit = umin - umax;
        result.offset = umax;
    } else {
        result.limit = umax - umin;
        result.offset = umin;
    }
    result.mask = limit;
    result.mask |= result.mask >> 1;
    result.mask |= result.mask >> 2;
    result.mask |= result.mask >> 4;
    result.mask |= result.mask >> 8;
    result.mask |= result.mask >> 16;

    return result;
}

static inline struct i32range  set_i32range(int32_t imin, int32_t imax)
{
    struct i32range  result;

    if (imin > imax) {
        result.limit = (uint32_t)(imin - imax);
        result.offset = imax;
    } else {
        result.limit = (uint32_t)(imax - imin);
        result.offset = imin;
    }
    result.mask = limit;
    result.mask |= result.mask >> 1;
    result.mask |= result.mask >> 2;
    result.mask |= result.mask >> 4;
    result.mask |= result.mask >> 8;
    result.mask |= result.mask >> 16;

    return result;
}
and uniform random integers within a specified range are generated by
Code: [Select]
uint32_t  within32u(const struct u32range range)
{
    uint32_t  x;
    do {
        x = xorshift32() & range.mask;
    } while (x > range.limit);
    return x + range.offset;
}

int32_t  within32i(const struct i32range range)
{
    uint32_t  x;
    do {
        x = xorshift32() & range.mask;
    } while (x > range.limit);
    return (int32_t)x + range.offset;
}
The above works on any generator with uniform 32-bit binary distribution.  On average, with any valid nonempty range, less than two pseudorandom numbers are generated per output.
Since the operations are just bit shifts, exclusive ors, ands, and one multiplication per pseudorandom number, it is also ridiculously fast in practice compared to other generators, even linear congruential generators.
« Last Edit: July 13, 2019, 03:35:46 am by Nominal Animal »
 
The following users thanked this post: Excavatoree, rhodges

Online rstofer

  • Super Contributor
  • ***
  • Posts: 7334
  • Country: us
Re: ARDUINO: MAP function question
« Reply #11 on: July 17, 2019, 02:29:34 pm »
The integer/long version of Arduino map() function is broken/incorrect if the mapped range is inverted, and does not round results correctly.  I recently posted a suggested replacement (elsewhere, probably should have posted to Arduino forums/github):
Code: [Select]
template <class T, class A, class B, class C, class D>
long map(T _x, A _x_min, B _x_max, C _out_from, D _out_to, typename std::enable_if<std::is_integral<T>::value >::type* = 0)
{
<snip>
In particular, this version produces the same answer (long)round(map((float)x, (float)xmin, (float)xmax, (float)ymin, (float)ymax)) does.  If the ranges are literals, GCC does optimize the if clauses away, effectively compiling just that final line with constants.

If it isn't obvious, r in the code is a constant that provides the correct rounding: halfway away from zero.

I really enjoy your code.  I should archive up the various examples...

Early in the thread, there were comments along the line of "why should map() even exist, any programmer can come up with the equivalent in a few lines of code."  And here we have it!  Something over 30 lines of carefully thought out code will get it done (properly).  Any programmer should just type that stuff in and be done with it.  No map() function required!  Of course it will work right out of the box!  Eureka!  (for those who know what the Eureka Syndrome is...)

There is no law in nature compelling people to use library functions and, on occasion, library code will be incorrect but over time with thousands of eyes looking, the errors are corrected.  There is better than even odds that the library code will be better than mine.

 

Offline frozenfrogz

  • Frequent Contributor
  • **
  • Posts: 924
  • Country: de
  • Having fun with Arduino and Raspberry Pi
Re: ARDUINO: MAP function question
« Reply #12 on: July 17, 2019, 03:48:01 pm »
If you can answer this question, you don't need the map() function:

I see what you are aiming for. However:
When I started dipping my toes into the shallow waters of Arduino and working with micro controllers, I was glad to find a lot of libraries and helper functions like map() etc. Now, the more I stare into the abyss that is "actual programming", I can improve on my coding skills - ’though I guess my programming "skills" will never make it into a real production environment.
I think, that is not a bad thing. I am not aiming to become a programmer, but am grateful for the opportunity to easily build my own hacky prototypes to illustrate an idea or build a temporary solution for an exhibition or other kind of presentation.
The more things I build with tools like Arduino or Processing, the more I learn about "eloquent" ways of getting things done. I doubt, that I would have been able to wrap my head around things like shifting registers, bit logic and the likes, without starting at the shallow end in the first place.
Of course I do agree with you, that a proper production environment will suffer big time if you rely on basic Arduino programming skills.

I would love your opinion on what would be your recommendation for good entry points to learning C/C++ by yourself if you were not taking the Arduino route.
He’s like a trained ape. Without the training.
 

Online rstofer

  • Super Contributor
  • ***
  • Posts: 7334
  • Country: us
Re: ARDUINO: MAP function question
« Reply #13 on: July 17, 2019, 04:18:41 pm »
I would love your opinion on what would be your recommendation for good entry points to learning C/C++ by yourself if you were not taking the Arduino route.

There are two aspects to the problem of "where to start":  Hardware and software (tools).

You can use the Arduino hardware without the libraries.  You can learn to write to the bare iron in terms of timers, ADC, IO, etc.  In effect, recreating what the libraries already do but without the bloat.  The AVR platform is really a decent place to start.  Grab the User Manual / Datasheet and start reading.

Years ago I was working with bare iron on an ATmega128 with the AVR toolchain (included with Arduino) and AVRdude (also included with Arduino I believe) and I found it a very pleasant chip to use (unlike mid-range 8 bit PICs).  It's easy to code in C and the GCC compiler is the same one included in Arduino.  Avrdude will use ICSP for programming the device.

Here is an example of a pure C program for blinking an LED.  Note that there is no separate setup() and main() functions.  Main() runs at startup.

https://balau82.wordpress.com/2011/03/29/programming-arduino-uno-in-pure-c/

Well, it's pure in that it isn't using the Arduino libraries but it IS using avrlib.  It's pretty hard to get away from ALL libraries unless you write in assembly code.  After all, there is a C library that is implied just by using the language.

There is nothing stopping you from writing C or C++ on the Arduiino with no library usage at all.

You will want to study the 'make' utility and learn to write Makefiles.  These, in turn, can be used with command line Linux or with some IDEs.  Microsoft Visual Studio works well and there is an Arduino plug-in although, given the use of AVRdude, I'm not sure it is necessary.  Eclipse also works well with Makefiles.

When I was playing with the 128, I was using Linux at the command line and gedit for the source editor.  There is something comforting about a somewhat graphic WYSIWYG editor and a simple command line.  Toss in a couple of aliases to reduce the typing effort and it's a nice place to play:

alias m='make program'

One keystroke 'm' to make the executable and program the device.  Talk about lazy!


« Last Edit: July 17, 2019, 04:28:54 pm by rstofer »
 

Offline Rick Law

  • Super Contributor
  • ***
  • Posts: 2834
  • Country: us
Re: ARDUINO: MAP function question
« Reply #14 on: July 25, 2019, 03:52:02 am »
If you can answer this question, you don't need the map() function:

I see what you are aiming for. However:
When I started dipping my toes into the shallow waters of Arduino and working with micro controllers, I was glad to find a lot of libraries and helper functions like map() etc. Now, the more I stare into the abyss that is "actual programming", I can improve on my coding skills - ’though I guess my programming "skills" will never make it into a real production environment.
...
...
I would love your opinion on what would be your recommendation for good entry points to learning C/C++ by yourself if you were not taking the Arduino route.
Sorry it took me a while to reply...  It took me a while to think about this...

It is hard to say "good entry points to learning C/C++ by yourself if you were not taking the Arduino route" because there is so much to learn and it depends on what you want to learn first and how far you want to go.

It is a difficult task to say what is good way for YOU from MY perspective.  My pair of prescription glasses allow me to see well enough to drive my car at speed.  But if I hand you my prescription glasses and say "this works for me, so it should help you," you can imagine...  So consider this pure opinion that may not work for you.

I think the best way to learn depends on where your skill level is currently.  If you are new to both, I think it is best to separate learning MCU programming as two individual tasks as (1) learning programming, and (2) learning the programming of MCU.

As to '"learn about 'eloquent' ways of getting things done", that is not necessary.  As experience expands, 'eloquence' will come by itself.

Assuming you are very much a beginner and money pinched...

Arduino IDE already have all the basic tools to learn programming, the version I use (1.6.1) doesn't have a debugger and I don't know if newer versions have a debugger.  Even without a debugger is still an adequate tool to learn and refine programming skills.  You need to get to the point where you can read all the Arduino BASIC examples and understood their program architecture, understood all the functions they calls, and understood all the commands they used.

Once you get pass the "Serial" examples in the Arduino, you have the basic "terminal connect to a computer" type system.  With this, you can do programming and see the results (from your serial connection) -- Use serial.print() as the output connection from the computer to your eye balls, and serial.read() as the input connection of the computer from your fingers.  That can be the tools to learn programing as far as you want.

Do some programs like figuring out the first 10 prime numbers and see if your terminal is printing out the first 10 prime numbers.  You can make your programs progressively more complex (such as entering two dates and let your program figure out how many days elapsed).  From first hard-coding the dates in the code, later to it being able to accept the dates from your terminal (the PC/laptop running your Arduino IDE).  Learning ways to parse the input date string yourself (and similar tasks) will greatly improve your programming skills.  Those type of programs are just raw programming.  You can improve your programming while not being impeded by lack of hardware (MCU) knowledge.

You can add-to or replace elapse dates programming with doing your own software multiply.  Say multiplying two numbers both are 4-digits BCD encoded integer. (4-bit per digit encoded BCD so two bytes per number).  Doing some BCD will make you to learn shifting, masking, and bit fields.  Dealing with bits is important when dealing with MCUs.

As said, you can improve programming as far as you want to take it.

Rather than randomly seeking "what to learn next", looking up the first two 100 level Computer-Science class syllabus is a good way to get a list of "to-learns" and you do not have to rigidly follow that list.  You can learn what those are first then you learn how to do it when you do need to do it yourself.

I think by the time you learned how to do a software BCD multiply and/or to input a date, and parse it yourself, you are way more than adequate a programmer to start digging into the hardware (MCU) side of things.

I am going to stop here for now to wait for your input.  I may be totally off target in my assumptions in your skill level and in understanding what you are looking for.  I can do a "part 2" if I am hitting the nail.
« Last Edit: July 25, 2019, 04:03:53 am by Rick Law »
 

Offline frozenfrogz

  • Frequent Contributor
  • **
  • Posts: 924
  • Country: de
  • Having fun with Arduino and Raspberry Pi
Re: ARDUINO: MAP function question
« Reply #15 on: July 25, 2019, 08:24:19 am »
Hello rstofer and Rick Law,
thanks for taking the time to reply.
The reason I am asking is: At university I managed to build up a small lab for our students to experiment with electronics over the past couple of years. These are all students with little to no experience in programming or basic electronics and time is always a limiting factor also.
In our faculty, you can study "product design" and "communications design". One of the usual tasks that come up on a regular basis is building some kind of human input device that connects to a computer. For example, imagine a screen with a map of a natural resource and when you step towards the screen, resources vanish the closer you get (as an illustration of the human impact on soil erosion) – this is a fictitious example, but I guess you get the gist of it.
This would be a small part of a project a student works on over a semester and in this instance I would introduce different kinds of distance sensors, how they work, what an mcu is and how communication between sensor and mcu is established, plus some basic programming principles with Arduino on the input device side and Processing on the screen side. The student would decide on what type of sensor to use, how to speak with it,...

Arduino and Processing are pretty nice in terms of whacking together a quick prototype that does the job and finishing in time to be able to present that prototype at exam time.

I am trying to give the students all the information they need to figure out the programming and what their prototype should do and look like themselves. That way, all the projects we did in the lab have been a success so far and most students grasped a basic understanding of what they were doing. Some would come back to similar projects and improve on what they learned on their own time, some would just take it as experience and move on to other subjects.
I would love to introduce bare metal C++ for the programming part but as far as my experience, this would be a way to hard task to swallow for almost anyone coming to the lab for the first time.
« Last Edit: July 25, 2019, 08:26:24 am by frozenfrogz »
He’s like a trained ape. Without the training.
 

Offline Nominal Animal

  • Super Contributor
  • ***
  • Posts: 1725
  • Country: fi
    • My home page and email address
Re: ARDUINO: MAP function question
« Reply #16 on: July 25, 2019, 11:09:16 am »
In my opinion, frozenfrogs, that is perfectly fine, and gets results.  Technically, what you've done, is to achieve a purpose by getting the students use existing modules to experiment and fulfill a certain task, with minimal programming required (since a buttload of examples of how to do those things already exist).

I personally don't really call it programming, but experimentation.  It is like engaging students interested in robotics and mechanisms by using Lego Mindstorms or Technic.
It gives a fundamentally intuitive grasp at the subject, without going into the art/science/knowledge of it.  For the purpose you use it, this is absolutely perfect in my opinion.

Thing is, it does not by itself help them learn programming at all, the underlying logic and approaches different programming languages have, or how the entire stack is constructed; only an intuitive grasp.  So, when discussing in a context where the assumption is that we talk about programming and not about initial experimentation by non-programmers, the answers and guidance you get will not match your expectations/experience/situation.  Context matters.

The main issue I've had, is that self-learners rarely need to understand those underlying structures and differences, until it is almost too late.  You get things like huge effort spent in micro-optimizing some functions that are rarely run, while the project itself uses very inefficient algorithms; and could be made an order of magnitude more efficient by rewriting it with a better model and algorithms.  It takes effort to un-learn such habits, and to learn the more important stuff, like writing maintainable code with useful and insightful comments (that do not describe what the code does, but what the programmer intent is).

(Note, however, that I have not taught programming per se as a job; only some specific workshop-type courses a long time ago.  I do help others learn at StackOverflow, though.)

I haven't encountered (but not looked for, either!) for really good programming guides one could follow, because I think a mixed approach works better.  You tickle their intuition enough to get them interested, and then introduce the related concepts, so they'll explore them just enough to know they're there.  Like foreshadowing, or Chekov's Gun.  At the point where they have the prerequisite skills or capability to understand (integrate into their existing knowledge base!), advanced concepts, structures, and algorithms are explored in detail; especially via deconstructing/constructing example code.

I did have a hobby project last year, for a web workshop type of course, using a microcontroller (with native USB support, under Arduino) and Python 3 and Qt or GTK to create an interactive graphical user interface to control something on that microcontroller.  It fell through (test subject bowed out, due to "lack of time"; I only have a rough skeleton, as I intended to flesh it out using that test subject), but the intent was to do exactly what I described above.  The Arduino part is experimentation with existing modules, using USB Serial to talk to the GUI application.  Different programming languages are used intentionally, although it is much steeper learning curve for the learner.  In Python, a separate thread is used to handle the serial communications, and one or more Queues to talk with the GUI.  This way the GUI won't stall, even when communication/computation takes a while.  This is on Linux, so additional sysadmin stuff like device/file/directory ownership, character devices, and udev rules need to be discussed to get things working.

When I myself first learned programming some thirty-odd years ago, on a C64, a friend and I had to painstakingly copy BASIC from a magazine by hand.  I remember how I discovered that using a screenful of ╱ and ╲ characters, one could create mazes.  Alas, no internet (no modem for BBS access either) meant I only discovered proper maze-creating algorithms a decade later...  Some will never take the leap from copying existing code or plans to creating their own, but IMO, that leap is the difference between experimentation or playing in the Arduino environment, and proper programming.
 

Online rstofer

  • Super Contributor
  • ***
  • Posts: 7334
  • Country: us
Re: ARDUINO: MAP function question
« Reply #17 on: July 25, 2019, 02:07:39 pm »
I like to mentally separate 'programming' from 'coding'.  To me, 'programming' works with data, structures and algorithms.  'Coding' is how you represent those things in some language.  We didn't have 'structs' in Fortran IV and character strings were usually handled in assembly language libraries.  Still today, if I'm going to crunch numbers, I would prefer to use Fortran over C even though there is no really good reason for that.  C can handle the task but somehow Fortran looks right.  It would, I've been using it since 1970.

To the point, the focus of the class doesn't seem to be programming but coding up examples, perhaps based on other's works.  That's fine, if the project sparks an interest, the students can take is as far as they wish.

I fully embrace the Arduino concept of providing a platform for non-CS majors to use for mechatronics.  The tools and libraries are adequate and there are alternate, and more capable, tools but they aren't necessary. 

Arduino provides a standard environment for everybody.  Still there are choices to make:  Code in C++ or just C?  Use the Arduino libraries or work at a lower level?  Scrap all the libraries and work at bare metal with avr-lib and avr-gcc?

I like mbed as the next step up simply because device programming is as simple as drag and drop of the binary executable.  From there you can go anywhere.  Bare metal of high performance ARM processors?  Use factory libraries?

Since the intent of the course is not mainline CS, Arduino is a terrific place to play.

Interesting side issue:  One of the best books ever written on CS is Niklaus Wirth's "Algorithm + Data Structures = Programs" which focuses on Pascal as a language for implementing algorithms that are wrapped around data structures.  Around 1980, UCSD Pascal was the hottest thing going for writing code for the Z80 style machines.  Here we are 40 years later and the first CS track course at the community college is Pascal programming.  I doubt that any commercial software is developed in Pascal but 'programming' (as I defined it above) is nicely taught using the language.

It is not realistic to think that a single course, or even a small collection of courses will provide all the electronics, programming and coding education it takes to make a living in that universe.  These days, the datasheet for a modest CPU will run nearly 1000 pages, certainly more than 500.  From that, a student might be able to use the peripherals in some bare metal way.  But that isn't mechatronics!  It takes another level to apply these peripherals to solving some real world problem.  About the only way to learn that kind of thing is to experiment.

Build something...

« Last Edit: July 25, 2019, 02:38:15 pm by rstofer »
 
The following users thanked this post: Nominal Animal

Offline Rick Law

  • Super Contributor
  • ***
  • Posts: 2834
  • Country: us
Re: ARDUINO: MAP function question
« Reply #18 on: July 25, 2019, 11:24:41 pm »
Looks like my last reply did miss the head of the nail - by a country mile.  Now that I understand what you are seeking...

While I may not agree with the finer details, in overview, I agree with Nominal Animal's point concerning the need to differentiate between "experimentation" vs "programming" and rstofer's point about the need to differentiate between "coding" vs "programming."

With the environment you described, you have a mix of students some with extreme interest and some with none.  Along with a semester being the "time limit", you have to entice them with something interest, grow that interest, and do it mach schnell.  You wont be able to get non-programmers to be a programmer in one semester, but you may be able to get them to do some tinkering - such as modifying how existing example programs may work based on some sensor input.  Those with some knowledge coming in may get to the point where they can make a sensor work by leveraging standard libraries out there.

I think it would be advantageous to do an "easy to conceptualize" thing right at the get-go to grab their attention.  Simple day-to-day use stuff that may have an MCU.  I just got this "clip on finger" Heart Rate (pulse) and Oxygen monitor sensor for people doing a workout.  It makes a good example - an OLED display that display both pulse rate and blood oxygen %.  A simple show and then question the student what may be the needed sensors for each function.  That specific item may not interest your student population.  I just happen to have purchased one and I just happen to finish reading the manual about how they determine "oxygen level."   You know your students better, you can decide what gadget may be interesting to your student population - may be a FitBit watch, may be a WII remote (with accelerometer) ...  Let the student come back with what they may need to sense and what the program would need to do - that conversation can lead to: "Well, we can't do that much in one semester.  How about if we just sense the coffee temperature and set a RED YELLOW GREEN light for "to hot to drink" vs "drink slow" vs "go".  Now we narrow to a sensor or two that is easily available out there.

There is a lot to gain with standard IDE, standard modules, and just let them tinker.  Show them how to use a standard "module" like an 2x16 LCD.  With the tons of different monitors for arduino on AliEpxress, you can choose a few and show - may be humidity monitor, may be a noise level monitor, may be a distance monitor, may be a temperature sensor...  Just let them use the standard modules and the standard Arduino IDE/Library so they can see how they can use the MCU to control the world.

As to by-passing, or rather, cutting the cord with Arduino IDE and Arduino Library, you can make that a follow up second semester kind of thing.  A beginner is unlikely to be ready to be that independent in just one semester.
 
The following users thanked this post: Nominal Animal


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf