Structuur van arduino programma
30 berichten
• Pagina 3 van 3 • 1, 2, 3
Re: Structuur van arduino programma
Je hoeft zelfs die return eigenlijk niet te doen.
Je hebt een globale variabele van het type struct Sensor_type.
Met de return geef je één integer-value terug.
Als je de functie alleen aanroept, en de return-waarde niet toekent aan val, dan kan je daarna alle 'velden' in de struct uitlezen, zoals ik in mijn laatste voorbeeldje liet zien. Je kan dan ook volstaan met een functie van het type void ipv int. Ik ken de dirty details van de gebruikte compiler en code-optimizer niet, maar het zou kunnen dat dat je in de machinecode één of een paar instructies scheelt. Als je de return-waarde gebruikt moet die bij het beëindigen van de functie op de stack (intern geheugen) worden gezet (gepushd) en daarna na het afronden van de functie-call moet de waarde van de stack in de variabele val worden gezet. Dat betekent: extra instructies (= clock-cycles die de processor niet aan wat anders kan besteden), extra geheugen (als je rechtstreeks met de velden van de struct werkt heb je de int val niet meer nodig, en extra werkgeheugen (er moet een variabele meer op de stack worden gezet. Bij kleine sketches niet belangrijk, maar als je tegen de grenzen van de grootte van je sketch aanloopt kan dat net het verschil maken. Ik probeer dan ook zo zuinig mogelijk te programmeren, als dat je tweede natuur wordt dan loop je gewoon later tegen grenzen aan, en wordt een sketch van meet af aan met optimale snelheid verwerkt. Ik vermoed verder dat de variabele 'val' bij iedere aanroep van loop() opnieuw wordt gecreëerd. Zo werkt het tenminste in een standaard 'c' programma. Ook dat betekent dus bij iedere aaroep van loop() een paar extra instructies. Als je de variabele aan het begin van je sketch declareert wordt er maar één keer een variabele aangemaakt, en wordt verder met een pointer naar die variabele gewerkt. Totdat ik van het tegendeel ben overtuigd declareer ik in sketches liever geen variabelen in de loop() functie of in andere functies die erg vaak worden aangeroepen. In 'normale' 'c'-programma's vermijd ik globale variabelen liever, ze hebben de hebbelijkheid een programma ondoorzichtig te maken. Maar in de microcontroller-wereld geef ik voorrang aan efficiency.
Je hebt een globale variabele van het type struct Sensor_type.
Met de return geef je één integer-value terug.
Als je de functie alleen aanroept, en de return-waarde niet toekent aan val, dan kan je daarna alle 'velden' in de struct uitlezen, zoals ik in mijn laatste voorbeeldje liet zien. Je kan dan ook volstaan met een functie van het type void ipv int. Ik ken de dirty details van de gebruikte compiler en code-optimizer niet, maar het zou kunnen dat dat je in de machinecode één of een paar instructies scheelt. Als je de return-waarde gebruikt moet die bij het beëindigen van de functie op de stack (intern geheugen) worden gezet (gepushd) en daarna na het afronden van de functie-call moet de waarde van de stack in de variabele val worden gezet. Dat betekent: extra instructies (= clock-cycles die de processor niet aan wat anders kan besteden), extra geheugen (als je rechtstreeks met de velden van de struct werkt heb je de int val niet meer nodig, en extra werkgeheugen (er moet een variabele meer op de stack worden gezet. Bij kleine sketches niet belangrijk, maar als je tegen de grenzen van de grootte van je sketch aanloopt kan dat net het verschil maken. Ik probeer dan ook zo zuinig mogelijk te programmeren, als dat je tweede natuur wordt dan loop je gewoon later tegen grenzen aan, en wordt een sketch van meet af aan met optimale snelheid verwerkt. Ik vermoed verder dat de variabele 'val' bij iedere aanroep van loop() opnieuw wordt gecreëerd. Zo werkt het tenminste in een standaard 'c' programma. Ook dat betekent dus bij iedere aaroep van loop() een paar extra instructies. Als je de variabele aan het begin van je sketch declareert wordt er maar één keer een variabele aangemaakt, en wordt verder met een pointer naar die variabele gewerkt. Totdat ik van het tegendeel ben overtuigd declareer ik in sketches liever geen variabelen in de loop() functie of in andere functies die erg vaak worden aangeroepen. In 'normale' 'c'-programma's vermijd ik globale variabelen liever, ze hebben de hebbelijkheid een programma ondoorzichtig te maken. Maar in de microcontroller-wereld geef ik voorrang aan efficiency.
If you think education is expensive, try ignorance! (Derek Bok)
Advertisement
Re: Structuur van arduino programma
Karel, het gaat een beetje hard voor mij. Ik begrijp het niet helemaal moet ik eerlijk bekennen vooral je opmerkingen over efficiency. Maar ik neem direct aan dat je gelijk hebt.
Maar ik heb de variabele val er uit gehaald , void Process_Potmeter() gemaakt ipv int Process_Potmeter(), de return verwijderd. En alles blijft werken en is in de code ook overzichtelijker.
Groet
René
Maar ik heb de variabele val er uit gehaald , void Process_Potmeter() gemaakt ipv int Process_Potmeter(), de return verwijderd. En alles blijft werken en is in de code ook overzichtelijker.
Groet
René
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Structuur van arduino programma
Wat karel aangaf is eigenlijk ook de bedoeling
In de loop roep je periodiek de Process_Achtergrondtaakje() aan , en dan kan je in je overige code gewoon de resultaten gebruiken.
De vlag "Potmeter.valid = true;" die aan het einde staat gebruik ik het meest tijdens het opstarten van het systeem als de analoge sensoren nog niet stabiel zijn, of diepe middeling hebben , dan kan het soms seconden duren voordat een sensor waarde echt 'goed' is, met die vlag kan je dan voorkomen dat je een 'slechte' waarde leest. Ook kan het process aan 'jou' doorgeven dat er iets niet lekker is.
Je kan het ook zo doen:
Alles selecteren
void loop() {
lcd.clear();
Process_Potmeter();
val = Potmeter.RawValue;
etc.
In de loop roep je periodiek de Process_Achtergrondtaakje() aan , en dan kan je in je overige code gewoon de resultaten gebruiken.
De vlag "Potmeter.valid = true;" die aan het einde staat gebruik ik het meest tijdens het opstarten van het systeem als de analoge sensoren nog niet stabiel zijn, of diepe middeling hebben , dan kan het soms seconden duren voordat een sensor waarde echt 'goed' is, met die vlag kan je dan voorkomen dat je een 'slechte' waarde leest. Ook kan het process aan 'jou' doorgeven dat er iets niet lekker is.
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
Re: Structuur van arduino programma
Inmiddels gebruik ik het Process_Potmeter op onderstaande wijze
Dit werkt prima.
Maar dan nu mijn Servo.
Die heb ik nu geimplementeerd met
In de void loop() gebruik ik die dan bijvoorbeeld op de volgende manier
- Code: Alles selecteren
void Process_Potmeter() {
Potmeter.RawValue = analogRead(A0); // read analog channel potmeter
Potmeter.RawValue=Potmeter.RawValue/10.23; // hiermee wordt de schaal van 0 tot 100
Potmeter.Target=Potmeter.RawValue*4.5+50; // hiermee wordt het automatische vliegbereik begrensd tussen 50 en 500m
if (Potmeter.OldValue > Potmeter.RawValue + 1 || Potmeter.OldValue < Potmeter.RawValue - 1) // kleine variaties(trillingen) in de potmeter worden genegeerd
{
Potmeter.changed = true;
Potmeter.OldValue = Potmeter.RawValue;
}
else
{
Potmeter.changed = false;
}
Potmeter.valid = true; // set flag signal is valid and updated (gebruik ik nog niet)
}//Process_Potmeter
- Code: Alles selecteren
void loop() {
button.tick(); // voor de werking van Onebutton.h
Process_Potmeter(); // om de potmeter te kunnen lezen
switch (RunMode) {
....
..
//verdere code waarbij ik de resultaten van het Potmeter_Process gebruik.
Dit werkt prima.
Maar dan nu mijn Servo.
Die heb ik nu geimplementeerd met
- Code: Alles selecteren
#include <Servo.h>
Servo myservo;
void setup() {
myservo.attach(9);
// en nog meer zaken
//
//
}
In de void loop() gebruik ik die dan bijvoorbeeld op de volgende manier
- Code: Alles selecteren
if (Potmeter.changed)
{
MT = EEPROM.read(address_MT); // leest uit EEPROM de parameter MT (maxpercentage gas)
lcd.setCursor(0,0);
lcd.print(" ");
lcd.setCursor(6,0);
lcd.print(Potmeter.RawValue * MT / 100);
lcd.print(" % gas ");
myservo.write(93 + Potmeter.RawValue * MT / 100);
delay(10);
}
Re: Structuur van arduino programma
Dat ging even mis met plaatsen want ik had mijn vraag nog niet gesteld.
Het bovenstaande werkt allemaal. Maar ik wil voor mijn Servo ook zo'n process definiëren als voor de Potmeter is gedaan.
astrofrostbyte gaf daarvoor een voorzetje.
Bij die opzet kan/moet ik niet #include <Servo.h> gebruiken denk ik want daarin heeft "Servo" al een betekenis.
Hoe moet dat dan wel? Want ik wel beschikken over CurrentPosition en TargetPosition om daar acties van te laten afhangen.
Het bovenstaande werkt allemaal. Maar ik wil voor mijn Servo ook zo'n process definiëren als voor de Potmeter is gedaan.
astrofrostbyte gaf daarvoor een voorzetje.
- Code: Alles selecteren
struct Servo_type {
unsigned int CurrentPosition;
unsigned int TargetPosition;
boolean busy;
};
Servo_type Servo;
Bij die opzet kan/moet ik niet #include <Servo.h> gebruiken denk ik want daarin heeft "Servo" al een betekenis.
Hoe moet dat dan wel? Want ik wel beschikken over CurrentPosition en TargetPosition om daar acties van te laten afhangen.
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Structuur van arduino programma
Blijf gewoon je servo library gebruiken , daar is niks mee , 'myservo.' is dan een object, goede kans dat je dus direct de resulaten uit dat object kan benaderen, zoiets als var = myservo.position; is dus mischien mogelijk. moet je toch ff de manual van die servo lib doorspitten. (gebruik je de standaard arduino servo lib ?)
Met process_servo() kan je daar nog wat extra functionaliteit aan toevoegen.
Je kan gewoon een ander naampje kiezen voor de structure bv: LeftFlap. , dit stoort helemaal niet met je servo lib.
Dit is vaak wel mooier in de code, je bestuurd geen servo, maarje bestuurd bv een Flap of rudder, het is erg mooi in je code als er staat: rudder = 5; //degree, al dat servo gedoe wil je eigenlijk niet weten.
Met process_servo() kan je daar nog wat extra functionaliteit aan toevoegen.
Je kan gewoon een ander naampje kiezen voor de structure bv: LeftFlap. , dit stoort helemaal niet met je servo lib.
- Code: Alles selecteren
struct Servo_type {
unsigned int CurrentPosition;
unsigned int TargetPosition;
int CurrentAngle;
boolean busy;
}; Servo_type LeftFlap;
Dit is vaak wel mooier in de code, je bestuurd geen servo, maarje bestuurd bv een Flap of rudder, het is erg mooi in je code als er staat: rudder = 5; //degree, al dat servo gedoe wil je eigenlijk niet weten.
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
Re: Structuur van arduino programma
Mooi ga ik zo proberen.
Ja ik gebruik standaard arduino servo lib.
Dank
René
Ja ik gebruik standaard arduino servo lib.
Dank
René
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Structuur van arduino programma
Zit net ff programeer technisch te denken, mischien dat een 'echte' programmeur dat weet, maar volgens mij kan je een servo object ook gewoon bij je structure hangen.
- Code: Alles selecteren
struct Servo_type {
unsigned int CurrentPosition;
Servo myservo; // <---- defineer een object
int CurrentAngle;
boolean busy;
};
Servo_type LeftFlap;
Servo_type Rudder;
setup()
{ LeftFlap.myservo.attach(9); // zou dit werken ??
Rudder.myservo.attach(8); // zou dit werken ??
LeftFlap.myservo.write(100); // zou dit werken ??
Rudder.myservo.write(5); // zou dit werken ??
}
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Structuur van arduino programma
nou, ging meer om het idee, maar reden kan zijn leesbaarheid van de code,
Ik denk dat het 'normaal beter' is om de structure data in de class te hangen ipv. object in je structure.
Het is mogenlijk om de servo class uit te breiden mbv Inheritance. http://playground.arduino.cc/Code/Hierarchy (moet ik ook nog eens mee gaan spelen)
toch een erg mooie compiler hoor die avr-gcc die door Arduino gebruikt word.
Ik denk dat het 'normaal beter' is om de structure data in de class te hangen ipv. object in je structure.
Het is mogenlijk om de servo class uit te breiden mbv Inheritance. http://playground.arduino.cc/Code/Hierarchy (moet ik ook nog eens mee gaan spelen)
toch een erg mooie compiler hoor die avr-gcc die door Arduino gebruikt word.
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
30 berichten
• Pagina 3 van 3 • 1, 2, 3
Wie is er online?
Gebruikers in dit forum: Geen geregistreerde gebruikers en 16 gasten