问:
Having issues in functions inside function in javascript (eventlistener)
Got those Event Listeners out of the functions. Works ok except when 2 sounds in a row are the same, the second sound isn't said, sometimes. No idea where this comes from. Other issue : if the game is reset when unfinished then I get double sounds. I don't know where to remove the EventListeners if they are the problem.  Isn't it troublesome to have the same event (click on cells) with 2 different targets ?

Here's the code :

//Pour placer les images dans le tableau (sinon enlever cette partie pour avoir les images en ligne avec fonction shuffle dans un flex)

let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);

//Pour mélanger les images dans le tableau.
function shuffle() {
  let cardVar = [card1, card2, card3, card4, card5, card6];

  for (let cardPosition = cardVar.length - 1; cardPosition >= 1; cardPosition--) {
    let numrandom = Math.floor(Math.random() * (cardPosition + 1));
    let sauve = cardVar[cardPosition];
    cardVar[cardPosition] = cardVar[numrandom];
    cardVar[numrandom] = sauve;
  }
  //Mélange aléatoire des cartes du tableau
  cell1.appendChild(cardVar[0]);
  cell2.appendChild(cardVar[1]);
  cell3.appendChild(cardVar[2]);
  cell4.appendChild(cardVar[3]);
  cell5.appendChild(cardVar[4]);
  cell6.appendChild(cardVar[5]);
}

//Pour jouerSon aléatoire  sans doublon ... à finir...

//Récupérer array des sons et nombre de sons :

function sonsAleatoires() {
  //Arrays of win and loose
  let reussitesArray = [];
  let echecsArray = [];

  let sounds = document.getElementsByTagName('audio');
  let nbreSounds = sounds.length;
  let soundsArray = [];

  for (let i = 0; i < nbreSounds; i++) {
    sons = sounds[i];
    let x = sons.getAttributeNode('id').value;
    soundsArray.push(x);
  }

  //Duplique deux fois la liste des sons pour en avoir une vingtaine
  let soundsArray2 = soundsArray.slice();
  let soundsArray3 = soundsArray2.slice();
  let soundsArray4 = soundsArray.concat(soundsArray2, soundsArray3);

  //Randomize sounds
  for (let soundPosition = soundsArray4.length - 1; soundPosition >= 1; soundPosition--) {
    let numrandom = Math.floor(Math.random() * (soundPosition + 1));
    let sauve = soundsArray4[soundPosition];
    soundsArray4[soundPosition] = soundsArray4[numrandom];
    soundsArray4[numrandom] = sauve;
  }

  console.log(soundsArray4);

  let p = -1;
  let numsnd;

  son();

  function son() {
    p++;
    if (p >= soundsArray4.length) {
      return;
    } else {
      let sonAjouer = document.getElementById(soundsArray4[p]);
      let snd = sonAjouer.getAttributeNode('id').value;
      numsnd = Number(snd.charAt(3));
      sonAjouer.play();
    } //fin du if
  } //fin de son

  let cells = document.getElementsByTagName('td');
  let nbreCells = cells.length;
  for (var y = 0; y < nbreCells; y++) {
    cells[y].addEventListener('click', donnerResultat);
  }

  function donnerResultat() {
    let idCell = "";
    let contenuCell = "";
    let numImage = 0;
    idCell = (this.id);
    contenuCell = document.getElementById(idCell).lastElementChild.getAttributeNode('id').value;
    numImage = Number(contenuCell.charAt(4));
    if (p >= soundsArray4.length) {
      return;
    }

    //Compares id soundn and id img cliqued
    if (numsnd === numImage) {
      reussitesArray.push(1);

      document.getElementById(idCell).style.backgroundColor = "#83f500";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = "";
      }, 1000);

    } else {
      echecsArray.push(contenuCell);
      document.getElementById(idCell).style.backgroundColor = "#f13022";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = ""
      }, 1000);
    } //fin du if

  } //end of function donnerResultat

  //next sound
  for (var c = 0; c < nbreCells; c++) {
    cells[c].addEventListener('click', son, false);
  }

} //end of sonsAleatoires```
<pre class="snippet-code-css lang-css prettyprint-override"><code>*,
*:before,
*:after {
  margin: 0px;
  box-sizing: border-box;
}

html,
body {
  height: 100%;
  width: 100%;
}

body {
  justify-content: center;
  align-items: center;
  background-color: #ffeb3b63
}

h1 {
  font-size: 5vw;
  color: #FF5722;
}

.main {
  background-color: orange;
  width: 100%;
  position: relative;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.card {
  position: relative;
  margin: auto;
}

.card img {
  max-height: 12vw;
  width: auto;
  position: relative;
  border-radius: 1em;
  margin: auto;
  border: 1px solid #9C27B0;
  cursor: pointer;
}

.buttons {
  width: 15%;
  position: absolute;
  top: 10vw;
}

.buttons ul {
  list-style: none;
}

#button1 {
  display: none;
}

#button,
#button1,
#button3,
#button4 {
  position: relative;
  max-height: 10vw;
  float: right;
}

table {
  margin: auto;
  width: 65%;
}

table,
td {
  border: 1px solid #9c27b0;
  //border-collapse: collapse;
  padding: 2px;
  text-align: center;
  font: 4vw bold;
  color: #FFC107;
  background-color: #d0e21b6e
}

td {
  width: 31%;
}

.cell {
  cursor: pointer;
  background-color: #795548a1
}

p {
  position: relative;
  color: blue;
  font-size: 4vw;
  left: 50px;
}</code>```

<!DOCTYPE html>

  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Listen and point to</title>
  <link rel="stylesheet" href="style.css" />

 Ecoute et clique

<input type="image" id="button3" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/bouton-son.png" alt="bouton" onclick="sonsAleatoires()" />

<input type="image" id="button4" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/repeat.PNG" alt="bouton" onclick="replay()" />

<input type="image" id="button1" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/read.png" alt="bouton" onclick="afficher()" />

  <audio id="son1">
      <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.ogg" type="audio/ogg">
      <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.mp3" type="audio/mpeg">
        </audio>
  <audio id="son2">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.ogg" type="audio/ogg">
  </audio>
  <audio id="son3">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.ogg" type="audio/ogg">
  </audio>
  <audio id="son4">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.ogg" type="audio/ogg">
  </audio>
  <audio id="son5">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.ogg" type="audio/ogg">
  </audio>
  <audio id="son6">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.ogg" type="audio/ogg">
          </audio>

  <p id="Moyenne"

```

答:
An event listener is being added to cells on every call to sonsAleatoires().

function sonsAleatoires() {

  /* ... */

  function son() {
    /* code snip */
  } //fin de son

  /* ... */

  // add click listener to each cell:

  //next sound
  for (var c = 0; c < nbreCells; c++) {
    cells[c].addEventListener('click', son, false);
  }

}
```

<p>This will result in multiple listeners on each cell. To prevent multiple listeners, ensure that the 'son' listeners are only added once.</p>

<p>Introduce a <code>sonListenersAdded</code> variable:</p>

<pre class="lang-js prettyprint-override"><code>let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);

// add this here:
let sonListenersAdded = false;
</code>```

Then replace this:

for (var c = 0; c < nbreCells; c++) {
  cells[c].addEventListener('click', son, false);
}
```

<p>with this:</p>

<pre class="lang-js prettyprint-override"><code>if (!sonListenersAdded) {
  for (let cell of cells) {
    cell.addEventListener('click', son, false);
  }
  sonListenersAdded = true;
}
</code>```

Working code:

//Pour placer les images dans le tableau (sinon enlever cette partie pour avoir les images en ligne avec fonction shuffle dans un flex)

let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);
let sonListenersAdded = false;

//Pour mélanger les images dans le tableau.
function shuffle() {
  let cardVar = [card1, card2, card3, card4, card5, card6];

  for (let cardPosition = cardVar.length - 1; cardPosition >= 1; cardPosition--) {
    let numrandom = Math.floor(Math.random() * (cardPosition + 1));
    let sauve = cardVar[cardPosition];
    cardVar[cardPosition] = cardVar[numrandom];
    cardVar[numrandom] = sauve;
  }
  //Mélange aléatoire des cartes du tableau
  cell1.appendChild(cardVar[0]);
  cell2.appendChild(cardVar[1]);
  cell3.appendChild(cardVar[2]);
  cell4.appendChild(cardVar[3]);
  cell5.appendChild(cardVar[4]);
  cell6.appendChild(cardVar[5]);
}

//Pour jouerSon aléatoire  sans doublon ... à finir...

//Récupérer array des sons et nombre de sons :

function sonsAleatoires() {
  //Arrays of win and loose
  let reussitesArray = [];
  let echecsArray = [];

  let sounds = document.getElementsByTagName('audio');
  let nbreSounds = sounds.length;
  let soundsArray = [];

  for (let i = 0; i < nbreSounds; i++) {
    sons = sounds[i];
    let x = sons.getAttributeNode('id').value;
    soundsArray.push(x);
  }

  //Duplique deux fois la liste des sons pour en avoir une vingtaine
  let soundsArray2 = soundsArray.slice();
  let soundsArray3 = soundsArray2.slice();
  let soundsArray4 = soundsArray.concat(soundsArray2, soundsArray3);

  //Randomize sounds
  for (let soundPosition = soundsArray4.length - 1; soundPosition >= 1; soundPosition--) {
    let numrandom = Math.floor(Math.random() * (soundPosition + 1));
    let sauve = soundsArray4[soundPosition];
    soundsArray4[soundPosition] = soundsArray4[numrandom];
    soundsArray4[numrandom] = sauve;
  }

  // console.log(soundsArray4);

  let p = -1;
  let numsnd;

  son();

  function son(evt) {

    // console.log('son evt;', evt);

    p++;
    if (p >= soundsArray4.length) {
      return;
    } else {
      let sonAjouer = document.getElementById(soundsArray4[p]);
      let snd = sonAjouer.getAttributeNode('id').value;
      numsnd = Number(snd.charAt(3));
      console.log('son playing sound snd:', snd);
      sonAjouer.play();
    } //fin du if
  } //fin de son

  let cells = document.getElementsByTagName('td');
  let nbreCells = cells.length;
  for (var y = 0; y < nbreCells; y++) {
    cells[y].addEventListener('click', donnerResultat);
  }

  function donnerResultat() {
    let idCell = "";
    let contenuCell = "";
    let numImage = 0;
    idCell = (this.id);
    contenuCell = document.getElementById(idCell).lastElementChild.getAttributeNode('id').value;
    numImage = Number(contenuCell.charAt(4));
    if (p >= soundsArray4.length) {
      return;
    }

    //Compares id soundn and id img cliqued
    if (numsnd === numImage) {
      reussitesArray.push(1);

      document.getElementById(idCell).style.backgroundColor = "#83f500";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = "";
      }, 1000);

    } else {
      echecsArray.push(contenuCell);
      document.getElementById(idCell).style.backgroundColor = "#f13022";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = ""
      }, 1000);
    } //fin du if

  } //end of function donnerResultat

  //next sound
  if (!sonListenersAdded) {
    // console.log('donnerResultat adding event listeners');
    for (let cell of cells) {
      cell.addEventListener('click', son, false);
    }
    sonListenersAdded = true;
  }

} //end of sonsAleatoires```
<pre class="snippet-code-css lang-css prettyprint-override"><code>*,
*:before,
*:after {
  margin: 0px;
  box-sizing: border-box;
}

html,
body {
  height: 100%;
  width: 100%;
}

body {
  justify-content: center;
  align-items: center;
  background-color: #ffeb3b63
}

h1 {
  font-size: 5vw;
  color: #FF5722;
}

.main {
  background-color: orange;
  width: 100%;
  position: relative;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.card {
  position: relative;
  margin: auto;
}

.card img {
  max-height: 12vw;
  width: auto;
  position: relative;
  border-radius: 1em;
  margin: auto;
  border: 1px solid #9C27B0;
  cursor: pointer;
}

.buttons {
  width: 15%;
  position: absolute;
  top: 10vw;
}

.buttons ul {
  list-style: none;
}

#button1 {
  display: none;
}

#button,
#button1,
#button3,
#button4 {
  position: relative;
  max-height: 10vw;
  float: right;
}

table {
  margin: auto;
  width: 65%;
}

table,
td {
  border: 1px solid #9c27b0;
  //border-collapse: collapse;
  padding: 2px;
  text-align: center;
  font: 4vw bold;
  color: #FFC107;
  background-color: #d0e21b6e
}

td {
  width: 31%;
}

.cell {
  cursor: pointer;
  background-color: #795548a1
}

p {
  position: relative;
  color: blue;
  font-size: 4vw;
  left: 50px;
}</code>```

 Ecoute et clique

<input type="image" id="button3" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/bouton-son.png" alt="bouton" onclick="sonsAleatoires()" />

<input type="image" id="button4" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/repeat.PNG" alt="bouton" onclick="replay()" />

<input type="image" id="button1" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/read.png" alt="bouton" onclick="afficher()" />

  <audio id="son1">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.ogg" type="audio/ogg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.mp3" type="audio/mpeg">
</audio>
  <audio id="son2">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.ogg" type="audio/ogg">
</audio>
  <audio id="son3">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.ogg" type="audio/ogg">
</audio>
  <audio id="son4">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.ogg" type="audio/ogg">
</audio>
  <audio id="son5">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.ogg" type="audio/ogg">
</audio>
  <audio id="son6">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.ogg" type="audio/ogg">
</audio>

Moyenne

```

Body:
Got those Event Listeners out of the functions. Works ok except when 2 sounds in a row are the same, the second sound isn't said, sometimes. No idea where this comes from. Other issue : if the game is reset when unfinished then I get double sounds. I don't know where to remove the EventListeners if they are the problem.  Isn't it troublesome to have the same event (click on cells) with 2 different targets ?

Here's the code :

//Pour placer les images dans le tableau (sinon enlever cette partie pour avoir les images en ligne avec fonction shuffle dans un flex)

let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);

//Pour mélanger les images dans le tableau.
function shuffle() {
  let cardVar = [card1, card2, card3, card4, card5, card6];

  for (let cardPosition = cardVar.length - 1; cardPosition >= 1; cardPosition--) {
    let numrandom = Math.floor(Math.random() * (cardPosition + 1));
    let sauve = cardVar[cardPosition];
    cardVar[cardPosition] = cardVar[numrandom];
    cardVar[numrandom] = sauve;
  }
  //Mélange aléatoire des cartes du tableau
  cell1.appendChild(cardVar[0]);
  cell2.appendChild(cardVar[1]);
  cell3.appendChild(cardVar[2]);
  cell4.appendChild(cardVar[3]);
  cell5.appendChild(cardVar[4]);
  cell6.appendChild(cardVar[5]);
}

//Pour jouerSon aléatoire  sans doublon ... à finir...

//Récupérer array des sons et nombre de sons :

function sonsAleatoires() {
  //Arrays of win and loose
  let reussitesArray = [];
  let echecsArray = [];

  let sounds = document.getElementsByTagName('audio');
  let nbreSounds = sounds.length;
  let soundsArray = [];

  for (let i = 0; i < nbreSounds; i++) {
    sons = sounds[i];
    let x = sons.getAttributeNode('id').value;
    soundsArray.push(x);
  }

  //Duplique deux fois la liste des sons pour en avoir une vingtaine
  let soundsArray2 = soundsArray.slice();
  let soundsArray3 = soundsArray2.slice();
  let soundsArray4 = soundsArray.concat(soundsArray2, soundsArray3);

  //Randomize sounds
  for (let soundPosition = soundsArray4.length - 1; soundPosition >= 1; soundPosition--) {
    let numrandom = Math.floor(Math.random() * (soundPosition + 1));
    let sauve = soundsArray4[soundPosition];
    soundsArray4[soundPosition] = soundsArray4[numrandom];
    soundsArray4[numrandom] = sauve;
  }

  console.log(soundsArray4);

  let p = -1;
  let numsnd;

  son();

  function son() {
    p++;
    if (p >= soundsArray4.length) {
      return;
    } else {
      let sonAjouer = document.getElementById(soundsArray4[p]);
      let snd = sonAjouer.getAttributeNode('id').value;
      numsnd = Number(snd.charAt(3));
      sonAjouer.play();
    } //fin du if
  } //fin de son

  let cells = document.getElementsByTagName('td');
  let nbreCells = cells.length;
  for (var y = 0; y < nbreCells; y++) {
    cells[y].addEventListener('click', donnerResultat);
  }

  function donnerResultat() {
    let idCell = "";
    let contenuCell = "";
    let numImage = 0;
    idCell = (this.id);
    contenuCell = document.getElementById(idCell).lastElementChild.getAttributeNode('id').value;
    numImage = Number(contenuCell.charAt(4));
    if (p >= soundsArray4.length) {
      return;
    }

    //Compares id soundn and id img cliqued
    if (numsnd === numImage) {
      reussitesArray.push(1);

      document.getElementById(idCell).style.backgroundColor = "#83f500";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = "";
      }, 1000);

    } else {
      echecsArray.push(contenuCell);
      document.getElementById(idCell).style.backgroundColor = "#f13022";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = ""
      }, 1000);
    } //fin du if

  } //end of function donnerResultat

  //next sound
  for (var c = 0; c < nbreCells; c++) {
    cells[c].addEventListener('click', son, false);
  }

} //end of sonsAleatoires

*,
*:before,
*:after {
  margin: 0px;
  box-sizing: border-box;
}

html,
body {
  height: 100%;
  width: 100%;
}

body {
  justify-content: center;
  align-items: center;
  background-color: #ffeb3b63
}

h1 {
  font-size: 5vw;
  color: #FF5722;
}

.main {
  background-color: orange;
  width: 100%;
  position: relative;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.card {
  position: relative;
  margin: auto;
}

.card img {
  max-height: 12vw;
  width: auto;
  position: relative;
  border-radius: 1em;
  margin: auto;
  border: 1px solid #9C27B0;
  cursor: pointer;
}

.buttons {
  width: 15%;
  position: absolute;
  top: 10vw;
}

.buttons ul {
  list-style: none;
}

#button1 {
  display: none;
}

#button,
#button1,
#button3,
#button4 {
  position: relative;
  max-height: 10vw;
  float: right;
}

table {
  margin: auto;
  width: 65%;
}

table,
td {
  border: 1px solid #9c27b0;
  //border-collapse: collapse;
  padding: 2px;
  text-align: center;
  font: 4vw bold;
  color: #FFC107;
  background-color: #d0e21b6e
}

td {
  width: 31%;
}

.cell {
  cursor: pointer;
  background-color: #795548a1
}

p {
  position: relative;
  color: blue;
  font-size: 4vw;
  left: 50px;
}

<!DOCTYPE html>

  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Listen and point to</title>
  <link rel="stylesheet" href="style.css" />

 Ecoute et clique

<input type="image" id="button3" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/bouton-son.png" alt="bouton" onclick="sonsAleatoires()" />

<input type="image" id="button4" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/repeat.PNG" alt="bouton" onclick="replay()" />

<input type="image" id="button1" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/read.png" alt="bouton" onclick="afficher()" />

  <audio id="son1">
      <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.ogg" type="audio/ogg">
      <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.mp3" type="audio/mpeg">
        </audio>
  <audio id="son2">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.ogg" type="audio/ogg">
  </audio>
  <audio id="son3">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.ogg" type="audio/ogg">
  </audio>
  <audio id="son4">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.ogg" type="audio/ogg">
  </audio>
  <audio id="son5">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.ogg" type="audio/ogg">
  </audio>
  <audio id="son6">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.mp3" type="audio/mpeg">
          <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.ogg" type="audio/ogg">
          </audio>

  <p id="Moyenne"

Body:
An event listener is being added to cells on every call to sonsAleatoires().

function sonsAleatoires() {

  /* ... */

  function son() {
    /* code snip */
  } //fin de son

  /* ... */

  // add click listener to each cell:

  //next sound
  for (var c = 0; c < nbreCells; c++) {
    cells[c].addEventListener('click', son, false);
  }

}

This will result in multiple listeners on each cell. To prevent multiple listeners, ensure that the 'son' listeners are only added once.

Introduce a sonListenersAdded variable:

let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);

// add this here:
let sonListenersAdded = false;

Then replace this:

for (var c = 0; c < nbreCells; c++) {
  cells[c].addEventListener('click', son, false);
}

with this:

if (!sonListenersAdded) {
  for (let cell of cells) {
    cell.addEventListener('click', son, false);
  }
  sonListenersAdded = true;
}

Working code:

//Pour placer les images dans le tableau (sinon enlever cette partie pour avoir les images en ligne avec fonction shuffle dans un flex)

let cards = document.getElementsByClassName('card');
let nbreCards = cards.length;
cell1.appendChild(card1);
cell2.appendChild(card2);
cell3.appendChild(card3);
cell4.appendChild(card4);
cell5.appendChild(card5);
cell6.appendChild(card6);
let sonListenersAdded = false;

//Pour mélanger les images dans le tableau.
function shuffle() {
  let cardVar = [card1, card2, card3, card4, card5, card6];

  for (let cardPosition = cardVar.length - 1; cardPosition >= 1; cardPosition--) {
    let numrandom = Math.floor(Math.random() * (cardPosition + 1));
    let sauve = cardVar[cardPosition];
    cardVar[cardPosition] = cardVar[numrandom];
    cardVar[numrandom] = sauve;
  }
  //Mélange aléatoire des cartes du tableau
  cell1.appendChild(cardVar[0]);
  cell2.appendChild(cardVar[1]);
  cell3.appendChild(cardVar[2]);
  cell4.appendChild(cardVar[3]);
  cell5.appendChild(cardVar[4]);
  cell6.appendChild(cardVar[5]);
}

//Pour jouerSon aléatoire  sans doublon ... à finir...

//Récupérer array des sons et nombre de sons :

function sonsAleatoires() {
  //Arrays of win and loose
  let reussitesArray = [];
  let echecsArray = [];

  let sounds = document.getElementsByTagName('audio');
  let nbreSounds = sounds.length;
  let soundsArray = [];

  for (let i = 0; i < nbreSounds; i++) {
    sons = sounds[i];
    let x = sons.getAttributeNode('id').value;
    soundsArray.push(x);
  }

  //Duplique deux fois la liste des sons pour en avoir une vingtaine
  let soundsArray2 = soundsArray.slice();
  let soundsArray3 = soundsArray2.slice();
  let soundsArray4 = soundsArray.concat(soundsArray2, soundsArray3);

  //Randomize sounds
  for (let soundPosition = soundsArray4.length - 1; soundPosition >= 1; soundPosition--) {
    let numrandom = Math.floor(Math.random() * (soundPosition + 1));
    let sauve = soundsArray4[soundPosition];
    soundsArray4[soundPosition] = soundsArray4[numrandom];
    soundsArray4[numrandom] = sauve;
  }

  // console.log(soundsArray4);

  let p = -1;
  let numsnd;

  son();

  function son(evt) {

    // console.log('son evt;', evt);

    p++;
    if (p >= soundsArray4.length) {
      return;
    } else {
      let sonAjouer = document.getElementById(soundsArray4[p]);
      let snd = sonAjouer.getAttributeNode('id').value;
      numsnd = Number(snd.charAt(3));
      console.log('son playing sound snd:', snd);
      sonAjouer.play();
    } //fin du if
  } //fin de son

  let cells = document.getElementsByTagName('td');
  let nbreCells = cells.length;
  for (var y = 0; y < nbreCells; y++) {
    cells[y].addEventListener('click', donnerResultat);
  }

  function donnerResultat() {
    let idCell = "";
    let contenuCell = "";
    let numImage = 0;
    idCell = (this.id);
    contenuCell = document.getElementById(idCell).lastElementChild.getAttributeNode('id').value;
    numImage = Number(contenuCell.charAt(4));
    if (p >= soundsArray4.length) {
      return;
    }

    //Compares id soundn and id img cliqued
    if (numsnd === numImage) {
      reussitesArray.push(1);

      document.getElementById(idCell).style.backgroundColor = "#83f500";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = "";
      }, 1000);

    } else {
      echecsArray.push(contenuCell);
      document.getElementById(idCell).style.backgroundColor = "#f13022";
      setTimeout(function() {
        document.getElementById(idCell).style.backgroundColor = ""
      }, 1000);
    } //fin du if

  } //end of function donnerResultat

  //next sound
  if (!sonListenersAdded) {
    // console.log('donnerResultat adding event listeners');
    for (let cell of cells) {
      cell.addEventListener('click', son, false);
    }
    sonListenersAdded = true;
  }

} //end of sonsAleatoires

*,
*:before,
*:after {
  margin: 0px;
  box-sizing: border-box;
}

html,
body {
  height: 100%;
  width: 100%;
}

body {
  justify-content: center;
  align-items: center;
  background-color: #ffeb3b63
}

h1 {
  font-size: 5vw;
  color: #FF5722;
}

.main {
  background-color: orange;
  width: 100%;
  position: relative;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.card {
  position: relative;
  margin: auto;
}

.card img {
  max-height: 12vw;
  width: auto;
  position: relative;
  border-radius: 1em;
  margin: auto;
  border: 1px solid #9C27B0;
  cursor: pointer;
}

.buttons {
  width: 15%;
  position: absolute;
  top: 10vw;
}

.buttons ul {
  list-style: none;
}

#button1 {
  display: none;
}

#button,
#button1,
#button3,
#button4 {
  position: relative;
  max-height: 10vw;
  float: right;
}

table {
  margin: auto;
  width: 65%;
}

table,
td {
  border: 1px solid #9c27b0;
  //border-collapse: collapse;
  padding: 2px;
  text-align: center;
  font: 4vw bold;
  color: #FFC107;
  background-color: #d0e21b6e
}

td {
  width: 31%;
}

.cell {
  cursor: pointer;
  background-color: #795548a1
}

p {
  position: relative;
  color: blue;
  font-size: 4vw;
  left: 50px;
}

<body>
  <h1 class="header"> Ecoute et clique </h1>
  <div>
    <table class="table">
      <tr>
        <td id="cell1"></td>
        <td id="cell2"></td>
        <td id="cell3"></td>
      </tr>

      <tr>
        <td id="cell4"></td>
        <td id="cell5"></td>
        <td id="cell6"></td>
      </tr>

    </table>
  </div>
  <div class="main">
    <div class="card" id="card1"><img id="img1" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/frere_nb.png" alt="frere"></div>
    </td>
    <div class="card" id="card2"><img id="img2" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/soeur_nb.png" alt="soeur"></div>
    <div class="card" id="card3"><img id="img3" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/mere_nb.png" alt="mere"></div>
    <div class="card" id="card4"><img id="img4" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/pere_nb.png" alt="pere"></div>
    <div class="card" id="card5"><img id="img5" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/grandmere_nb.png" alt="gdmere"></div>
    <div class="card" id="card6"><img id="img6" src="http://lve64.free.fr/sequences/famille_2016/images_famille_reduites/grand_pere_nb.png" alt="gdpere"></div>
  </div>

  <div class="buttons">
    <ul>
      <li><input type="image" id="button3" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/bouton-son.png" alt="bouton" onclick="sonsAleatoires()" /></li>
      <li><input type="image" id="button4" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/repeat.PNG" alt="bouton" onclick="replay()" /></li>
      <li><input type="image" id="button1" src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/buttons/read.png" alt="bouton" onclick="afficher()" /></li>

    </ul>
  </div>
  <audio id="son1">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.ogg" type="audio/ogg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/broth.mp3" type="audio/mpeg">
</audio>
  <audio id="son2">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/sister.ogg" type="audio/ogg">
</audio>
  <audio id="son3">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/moth.ogg" type="audio/ogg">
</audio>
  <audio id="son4">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/fath.ogg" type="audio/ogg">
</audio>
  <audio id="son5">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdm.ogg" type="audio/ogg">
</audio>
  <audio id="son6">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.mp3" type="audio/mpeg">
  <source src="http://lve64.free.fr/projets_jeu_navigateur/projet_cartes_lve2/famille_mots/gdf.ogg" type="audio/ogg">
</audio>

  <p id="Moyenne">Moyenne</p>
</body>


来源: stackexchange

问:
Why is the main purpose of ResNet if the vanishing gradient problem is solved using RELU activation function?
I read that ResNet solves the problem of vanishing gradient problem by using skip functions. But are they not already solved using RELU? Is there some other important thing I'm missing about ResNet or does Vanishing gradient problem occur even after using RELU? </p>

答:
The ReLU activation solves the problem of vanishing gradient that is due to sigmoid-like non-linearities (the gradient vanishes because of the flat regions of the sigmoid).

The other kind of "vanishing" gradient seems to be related to the depth of the network (e.g. see this for example). Basically, when backpropagating gradient from layer N to N-k, the gradient vanishes as a function of depth (in vanilla architectures). The idea of resnets is to help with gradient backpropagation (see for example Identity mappings in deep residual networks, where they present resnet v2 and argue that identity skip connections are better at this).

A very interesting and relatively recent paper that sheds light on the working on resnets is resnets behaves as ensembles of relatively small networks. The tl;dr of this paper could be (very roughly) summarized as this: residual networks behave as an ensemble: removing a single layer (i.e. a single residual branch, not its skip connection) doesn't really affect performance, but performance decreases in an smooth manner as a function of the number of layers that are removed, which is the way in which ensembles behave. Most of the gradient during training comes from short paths. They show that training only this short paths doesn't affect performance in a statistically significant way compared to when all paths are trained. This means that the effect of residual networks doesn't really come from depth as the effect of long paths is almost non-existant.

ContentLicense: CC BY-SA 4.0


问:
Is there a better way to write this check to see if a value exists on a prop in react?
I have this prop coming into my component, errors, which is an empty object if my form has no errors.  If there are errors they will be added to the object.  My question is, im checking for a specific property on the object, right now I'm checking to see that is not undefined.  Is there a better way to perform a check like this? Here is a snippet of the code</p>

```<code>const SelectOverdrawnFunds = ({
  overdrawnFunds = [],
  options,
  setFieldValue,
  setErrors,
  errors,
}) => (
  <>
    {overdrawnFunds.map((select, index) => {
      const error =
        errors &&
        errors.overdrawnFunds !== undefined &&
        errors.overdrawnFunds[index] !== undefined;
      return (
        <SearchSelect
          key={index}
          name={`overdrawnFunds[${index}]`}
          label="Fund"
          options={options}
          TextFieldProps={{
            error: error,
            helperText: error ? 'Required' : '',
          }}
        />
      );
    })}
...
SelectOverdrawnFunds.propTypes = {
  overdrawnFunds: PropTypes.array,
  options: PropTypes.array,
  setFieldValue: PropTypes.func,
  setErrors: PropTypes.func,
  errors: PropTypes.object,
};

export default SelectOverdrawnFunds;
</code>```

答:
Yes, you can use optional chaining like this

const error = !!errors?.overdrawnFunds?.[index];
//or
const error = Boolean(errors?.overdrawnFunds?.[index]);
```

<p>or if you want to make strict compare with <code>undefined</code></p>

<pre class="lang-js prettyprint-override"><code>const error = errors?.overdrawnFunds?.[index] !== undefined;
</code>```

You can find more info about optional chaining on MDN

Body:
I have this prop coming into my component, errors, which is an empty object if my form has no errors.  If there are errors they will be added to the object.  My question is, im checking for a specific property on the object, right now I'm checking to see that is not undefined.  Is there a better way to perform a check like this? Here is a snippet of the code

const SelectOverdrawnFunds = ({
  overdrawnFunds = [],
  options,
  setFieldValue,
  setErrors,
  errors,
}) => (
  <>
    {overdrawnFunds.map((select, index) => {
      const error =
        errors &&
        errors.overdrawnFunds !== undefined &&
        errors.overdrawnFunds[index] !== undefined;
      return (
        <SearchSelect
          key={index}
          name={`overdrawnFunds[${index}]`}
          label="Fund"
          options={options}
          TextFieldProps={{
            error: error,
            helperText: error ? 'Required' : '',
          }}
        />
      );
    })}
...
SelectOverdrawnFunds.propTypes = {
  overdrawnFunds: PropTypes.array,
  options: PropTypes.array,
  setFieldValue: PropTypes.func,
  setErrors: PropTypes.func,
  errors: PropTypes.object,
};

export default SelectOverdrawnFunds;

Body:
Yes, you can use optional chaining like this

const error = !!errors?.overdrawnFunds?.[index];
//or
const error = Boolean(errors?.overdrawnFunds?.[index]);

or if you want to make strict compare with undefined

const error = errors?.overdrawnFunds?.[index] !== undefined;

You can find more info about optional chaining on MDN


问:
Matlab - numerical solution system of ode
I want to solve the following system of differntial equations in matlab with my own runge kutty method:

 $\frac{dx_{1}{dt}$  = $x_{2}$

 $\frac{dx_{2}{dt}$ = A $x_{1} + B $x_{2}$ + asin(Ct)

 I wrote

```<code>function xdot = NaszModel(x, aa, bb, AA, BB, CC)

  a= aa;
  A = AA;
  B = BB;
  C = CC;

  xdot = [ x(2)
           A*x(1) - B*x(2) + a*sin(C)];
end

function [x, t] = RK(f, x0, t0, T, h)

   t = t0:h:T;
   nt = numel(t);
   nx = numel(x0);

   x = nan(nx, nt);

   x(:,1) = x0;

   for k = 1:nt-1

     k1 = h*f(t(k), x(:,k));
     k2 = h*f(t(k) + h/3 ,  x(:,k) + h/3 );
     k3 = h*f(t(k) + (2*h)/3, x(:,k) - k1/3 + k2);
     k4 = h*f(t(k) + h, x(:,k) + k1 - k2 + k3);

     dx = (k1 + 3*k2 + 3*k3 + k4)/8;

     x(:,k+1) = x(:,k) + dx;

   end
end

a = 1;
A = 0.1;
B = 0.1;
C = 1;

f = @(t,x) NaszModel(x, a, b, A, B, C);
x0 = [1, 0];
t0 = 0;
T = 100;
h = 1;

[x, t] = RK(f, x0, t0, T, h);

plot(t,x);
legend('x', 'v');

plot(x(1,:), x(2,:));
xlabel('x');
ylabel('v(x)');
</code>```

Everything works fine, but when im trying to add t to sin, i mean: i have in my solution asin(C), but i have to solve eqution with asin(C*t). `

how it should be written to make it works also for asin(Ct)?

答:
You need to pass t also to the model function, then you can also use it in the ODE. This means that you need to change the interface of the function.

function xdot = NaszModel(t, x, a, b, A, B, C)
  xdot = [ x(2)
        A*x(1) - B*x(2) + a*sin(C*t)];
end

f = @(t,x) NaszModel(t, x, a, b, A, B, C);
```

Body:
I want to solve the following system of differntial equations in matlab with my own runge kutty method:

 $\frac{dx_{1}{dt}$  = $x_{2}$

 $\frac{dx_{2}{dt}$ = A $x_{1} + B $x_{2}$ + asin(Ct)

 I wrote

function xdot = NaszModel(x, aa, bb, AA, BB, CC)

  a= aa;
  A = AA;
  B = BB;
  C = CC;

  xdot = [ x(2)
           A*x(1) - B*x(2) + a*sin(C)];
end

function [x, t] = RK(f, x0, t0, T, h)

   t = t0:h:T;
   nt = numel(t);
   nx = numel(x0);

   x = nan(nx, nt);

   x(:,1) = x0;

   for k = 1:nt-1

     k1 = h*f(t(k), x(:,k));
     k2 = h*f(t(k) + h/3 ,  x(:,k) + h/3 );
     k3 = h*f(t(k) + (2*h)/3, x(:,k) - k1/3 + k2);
     k4 = h*f(t(k) + h, x(:,k) + k1 - k2 + k3);

     dx = (k1 + 3*k2 + 3*k3 + k4)/8;

     x(:,k+1) = x(:,k) + dx;

   end
end

a = 1;
A = 0.1;
B = 0.1;
C = 1;

f = @(t,x) NaszModel(x, a, b, A, B, C);
x0 = [1, 0];
t0 = 0;
T = 100;
h = 1;

[x, t] = RK(f, x0, t0, T, h);

plot(t,x);
legend('x', 'v');

plot(x(1,:), x(2,:));
xlabel('x');
ylabel('v(x)');

Everything works fine, but when im trying to add t to sin, i mean: i have in my solution asin(C), but i have to solve eqution with asin(C*t). `

how it should be written to make it works also for asin(Ct)?


问:
Why code not working for configuring while loop
Why my code not working

a “game” where, through input, enter the number of players who will play the game, how to make so many inputs (for player nicknames) be displayed, how many players are playing? and how to do something to add all the nicknames to the array later?
For example: the host introduced what 5 people play, how to output 5 inputs and then add all the nicknames to the array?

```<code>print("Add players!")
plam = int(input("How many players will be? \n"))

playersNames = []
i = len(playersNames)
while i < plam:
    writePlayerName = input("Write player's nickname:   " + Fore.GREEN)
    print(Fore.WHITE)
    playersNames.append(writePlayerName)
    print(playersNames)
    break;
</code>```

Problem statement

player names can be entered endlessly, but I here restricted that there will be 5 players

答:
Try this one

```<code>print("Add players!")
plam = int(input("How many players will be? \n"))

playersNames = []
i = len(playersNames)
for i in range(plam):
    writePlayerName = input("Write player's nickname:   " + Fore.GREEN)
    print(Fore.WHITE)
    playersNames.append(writePlayerName)
    print(playersNames)

</code>```

output

```<code>Add players!
How many players will be?
3
Write player's nickname:   jhon
['jhon']
Write player's nickname:   smith
['jhon', 'smith']
Write player's nickname:   roky
['jhon', 'smith', 'roky']
</code>```

Body:
Why my code not working

a “game” where, through input, enter the number of players who will play the game, how to make so many inputs (for player nicknames) be displayed, how many players are playing? and how to do something to add all the nicknames to the array later?
For example: the host introduced what 5 people play, how to output 5 inputs and then add all the nicknames to the array?

print("Add players!")
plam = int(input("How many players will be? \n"))

playersNames = []
i = len(playersNames)
while i < plam:
    writePlayerName = input("Write player's nickname:   " + Fore.GREEN)
    print(Fore.WHITE)
    playersNames.append(writePlayerName)
    print(playersNames)
    break;

Problem statement

player names can be entered endlessly, but I here restricted that there will be 5 players

Body:
Try this one

print("Add players!")
plam = int(input("How many players will be? \n"))

playersNames = []
i = len(playersNames)
for i in range(plam):
    writePlayerName = input("Write player's nickname:   " + Fore.GREEN)
    print(Fore.WHITE)
    playersNames.append(writePlayerName)
    print(playersNames)

output

Add players!
How many players will be?
3
Write player's nickname:   jhon
['jhon']
Write player's nickname:   smith
['jhon', 'smith']
Write player's nickname:   roky
['jhon', 'smith', 'roky']


问:
Why am I getting "undefined symbol" when I link my static library in my C program?
I'm trying to create a static library to allow me to use a C++ API in my C program. To get started, I'm trying to call an API function called APIName::Api_init(); So far, I have created a "wrapper" library which has the following:

c_api.h:

```<code>#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
EXTERNC int apiname_api_init(char const * user_app_name);
EXTERNC void apiname_api_shutdown();

#undef EXTERNC
</code>```

c_api.cpp:

```<code>#include "c_api.h"
#include "../include/apiname/api.h"   // Link to header files from API provider
int apiname_api_init(char const * user_app_name) {
        return to_return_code(APIName::Api_init(user_app_name));
}

void apiname_api_shutdown() {
        return APIName::api_shutdown();
}
</code>```

I then compile this into an object file called apiwrapper.o using the following command:

```<code>g++  -L../include/libs -lapinameapi  -shared -fPIC -c -D_LINUX_X86_64 -lpthread -lz -lm -lcrypto -lbz2 -I../include -DPROVIDE_LOG_UTILITIES -DTARGET_PLATFORM_LINUX  c_api.cpp -o lapiwrapper.o -lrt
</code>```

where apinameapi is the shared library from the API provider.  This works fine.  I then generate the library file using:

```<code>ar rc libapiwrapper.a apiwrapper.o
</code>```

Again, this is fine.

Now I create my C file (mycode.c), which contains:

```<code>#include "mycode.h"
#include <stdio.h>
#include <string.h>
#include <time.h>
#ifdef _WIN32
#include <Windows.h>
#else
#include <unistd.h>
#endif
int connectToApi() {

  // Init API
  rc = apiname_api_init("programname");

}
</code>```

The header file mycode.h contains:

```<code>#include <stdbool.h>
#include <stdint.h>
#include "c_api.h"
</code>```

(obviously there's other stuff as well, but I've left it out for brevity).

So, I compile my main program using:

```<code>gcc  -Linclude/libs -lapiwrapper  -shared -DKXVER=3 -fPIC -D_LINUX_X86_64 -lpthread -lz -lm -lcrypto -lbz2 -Iinclude -DPROVIDE_LOG_UTILITIES -DTARGET_PLATFORM_LINUX  src/mycode.c -o lib/mycode.so -lrt -Wno-discarded-qualifiers -Wno-incompatible-pointer-types
</code>```

which is also fine. Then, I run the program (this particular file gets loaded by another piece of code), and I get

undefined symbol: apiname_api_init

It seems that it's not finding the function in the library file.  Where am I going wrong? This is my first time building a library, so it's probably something fairly basic.

EDIT: I think the issue may be coming from the fact that the final compilation (which creates mycode.so) is producing a shared object file, and I need that to run on its own (without needing my generated library file to be present as well).  I have to run the final object from another program, so it needs to be standalone. Is there a way I can link it to "bundle" everything together into one final so file?

答:
You need to extern "C" your CPP file the same way you did your header; otherwise the method names will be mangled in the object.</p>

```<code>#ifdef __cplusplus
extern "C" {
#endif

int apiname_api_init(char const * user_app_name) {
        return to_return_code(APIName::Api_init(user_app_name));
}

void apiname_api_shutdown() {
        return APIName::api_shutdown();
}

#ifdef __cplusplus
}
#endif
</code>```

Body:
I'm trying to create a static library to allow me to use a C++ API in my C program. To get started, I'm trying to call an API function called APIName::Api_init(); So far, I have created a "wrapper" library which has the following:

c_api.h:

#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
EXTERNC int apiname_api_init(char const * user_app_name);
EXTERNC void apiname_api_shutdown();

#undef EXTERNC

c_api.cpp:

#include "c_api.h"
#include "../include/apiname/api.h"   // Link to header files from API provider
int apiname_api_init(char const * user_app_name) {
        return to_return_code(APIName::Api_init(user_app_name));
}

void apiname_api_shutdown() {
        return APIName::api_shutdown();
}

I then compile this into an object file called apiwrapper.o using the following command:

g++  -L../include/libs -lapinameapi  -shared -fPIC -c -D_LINUX_X86_64 -lpthread -lz -lm -lcrypto -lbz2 -I../include -DPROVIDE_LOG_UTILITIES -DTARGET_PLATFORM_LINUX  c_api.cpp -o lapiwrapper.o -lrt

where apinameapi is the shared library from the API provider.  This works fine.  I then generate the library file using:

ar rc libapiwrapper.a apiwrapper.o

Again, this is fine.

Now I create my C file (mycode.c), which contains:

#include "mycode.h"
#include <stdio.h>
#include <string.h>
#include <time.h>
#ifdef _WIN32
#include <Windows.h>
#else
#include <unistd.h>
#endif
int connectToApi() {

  // Init API
  rc = apiname_api_init("programname");

}

The header file mycode.h contains:

#include <stdbool.h>
#include <stdint.h>
#include "c_api.h"

(obviously there's other stuff as well, but I've left it out for brevity).

So, I compile my main program using:

gcc  -Linclude/libs -lapiwrapper  -shared -DKXVER=3 -fPIC -D_LINUX_X86_64 -lpthread -lz -lm -lcrypto -lbz2 -Iinclude -DPROVIDE_LOG_UTILITIES -DTARGET_PLATFORM_LINUX  src/mycode.c -o lib/mycode.so -lrt -Wno-discarded-qualifiers -Wno-incompatible-pointer-types

which is also fine. Then, I run the program (this particular file gets loaded by another piece of code), and I get

undefined symbol: apiname_api_init

It seems that it's not finding the function in the library file.  Where am I going wrong? This is my first time building a library, so it's probably something fairly basic.

EDIT: I think the issue may be coming from the fact that the final compilation (which creates mycode.so) is producing a shared object file, and I need that to run on its own (without needing my generated library file to be present as well).  I have to run the final object from another program, so it needs to be standalone. Is there a way I can link it to "bundle" everything together into one final so file?

Body:
You need to extern "C" your CPP file the same way you did your header; otherwise the method names will be mangled in the object.

#ifdef __cplusplus
extern "C" {
#endif

int apiname_api_init(char const * user_app_name) {
        return to_return_code(APIName::Api_init(user_app_name));
}

void apiname_api_shutdown() {
        return APIName::api_shutdown();
}

#ifdef __cplusplus
}
#endif


问:
Need help with file IO in C
I'm converting the following code from C# to C, and I don't think I'm doing this correctly.

Entry3D and entry_3d are just structs that contain int lookup, length, extra in both cases.
Here's the C# snippet (and it works perfectly fine):

```<code>    BinaryReader reader = new BinaryReader(File.Open("artidx.mul", FileMode.Open));
    BinaryReader art = new BinaryReader(File.Open("art.mul", FileMode.Open));
    int count = (int)(reader.BaseStream.Length / 12);
    int length = 0x10000;
    Entry3D[] index = new Entry3D[length];
    Console.WriteLine("Loading indexes {0}", count);
    for (int i = 0; i < count && i < length; i++)
    {
        index[i].lookup = reader.ReadInt32();
        index[i].length = reader.ReadInt32();
        index[i].extra = reader.ReadInt32();
    }
    for (int i = count; i < length; ++i)
    {
        index[i].lookup = -1;
        index[i].length = -1;
        index[i].extra = -1;
    }
</code>```

Here's the part in C that I'm having trouble with.

```<code>/* Init everything else */
printf( "Init maps & gfx" );
mapFile = fopen( "sd:/map0.mul",   "rb" ),
 artIdx = fopen( "sd:/artidx.mul", "rb" ),
    art = fopen( "sd:/art.mul",    "rb" );

if ( mapFile == NULL || artIdx == NULL || art == NULL )
{
  printf( "D'oh, file loading failed: [%d][%d][%d]", mapFile == NULL, artIdx == NULL, art == NULL  );
  return(1);
}

/* Find artidx count and set length */
printf( "Init art index" );
fseek( artIdx, 0, SEEK_END );
int count = (ftell(artIdx) / 12), length = 0x10000; // 0x10000 entries availible
entry_3d entries[length];
fseek( artIdx, 0, SEEK_SET );

printf( "Reading art-idx, count=%d", count );
int i;
for( i = 0; i < count && i < length; i++ )
{
  //printf( "loc: %u i: %u", ftell( artIdx ), i );
  //fread( &entries[i], 12, 1, artIdx );
  fread( &(entries[i].lookup), 4, 1, artIdx ); // read 12 bytes total
  fread( &(entries[i].length), 4, 1, artIdx );
  fread( &(entries[i].extra), 4, 1, artIdx );
}

printf( "Setting aidx remainders" );
for ( i = count; i < length; i++ )
{
  entries[i].lookup = -1;
  entries[i].length = -1;
  entries[i].extra = -1;
}
</code>```

It's a bit impossible for me to debug the C part, but I can tell that it "dies" somewhere in the first for-loop. I'm guessing that it's possibly reading past the end of the stream (even though it shouldn't)?

答:
If you don't have access to a debugger, you can add some printf statements inside the loop to see how far it gets before it dies.  Add something like printf("i == %i\n", i); at the top of each loop iteration.  Also, save the return value of fread to a variable and print it out as well (for each fread call).  When the program dies, this should at least leave a trail of bread crumbs that you can follow.

Also, check the return value of your fopen and fseek calls and make sure that they returned successfully.

ContentLicense: CC BY-SA 3.0

Title: Need help with file IO in C

Body:
I'm converting the following code from C# to C, and I don't think I'm doing this correctly.

Entry3D and entry_3d are just structs that contain int lookup, length, extra in both cases.
Here's the C# snippet (and it works perfectly fine):

    BinaryReader reader = new BinaryReader(File.Open("artidx.mul", FileMode.Open));
    BinaryReader art = new BinaryReader(File.Open("art.mul", FileMode.Open));
    int count = (int)(reader.BaseStream.Length / 12);
    int length = 0x10000;
    Entry3D[] index = new Entry3D[length];
    Console.WriteLine("Loading indexes {0}", count);
    for (int i = 0; i < count && i < length; i++)
    {
        index[i].lookup = reader.ReadInt32();
        index[i].length = reader.ReadInt32();
        index[i].extra = reader.ReadInt32();
    }
    for (int i = count; i < length; ++i)
    {
        index[i].lookup = -1;
        index[i].length = -1;
        index[i].extra = -1;
    }

Here's the part in C that I'm having trouble with.

/* Init everything else */
printf( "Init maps & gfx" );
mapFile = fopen( "sd:/map0.mul",   "rb" ),
 artIdx = fopen( "sd:/artidx.mul", "rb" ),
    art = fopen( "sd:/art.mul",    "rb" );

if ( mapFile == NULL || artIdx == NULL || art == NULL )
{
  printf( "D'oh, file loading failed: [%d][%d][%d]", mapFile == NULL, artIdx == NULL, art == NULL  );
  return(1);
}

/* Find artidx count and set length */
printf( "Init art index" );
fseek( artIdx, 0, SEEK_END );
int count = (ftell(artIdx) / 12), length = 0x10000; // 0x10000 entries availible
entry_3d entries[length];
fseek( artIdx, 0, SEEK_SET );

printf( "Reading art-idx, count=%d", count );
int i;
for( i = 0; i < count && i < length; i++ )
{
  //printf( "loc: %u i: %u", ftell( artIdx ), i );
  //fread( &entries[i], 12, 1, artIdx );
  fread( &(entries[i].lookup), 4, 1, artIdx ); // read 12 bytes total
  fread( &(entries[i].length), 4, 1, artIdx );
  fread( &(entries[i].extra), 4, 1, artIdx );
}

printf( "Setting aidx remainders" );
for ( i = count; i < length; i++ )
{
  entries[i].lookup = -1;
  entries[i].length = -1;
  entries[i].extra = -1;
}

It's a bit impossible for me to debug the C part, but I can tell that it "dies" somewhere in the first for-loop. I'm guessing that it's possibly reading past the end of the stream (even though it shouldn't)?


问:
Why is pandas not working and importing anymore?
I used this code before and it was working fine. Now no matter what I do pandas is not working. I tried uninstalling and reinstalling. I used the previous file that was working, none of it is working. Can you help me find out whats happening?

This code:

```<code>import pandas as pd

...
df = pd.read.csv('all_stocks_5yr')
</code>```

causes the following error:

```<code>---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-2-dc236c5894fa> in <module>
----> 1 df = pd.read.csv('all_stocks_5yr')

/Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-packages/pandas/__init__.py in __getattr__(name)
    261             return _SparseArray
    262
--> 263         raise AttributeError(f"module 'pandas' has no attribute '{name}'")
    264
    265

AttributeError: module 'pandas' has no attribute 'read'
</code>```

答:
the command you need here is
pd.read_csv('filepath'). You can learn more about it: here

Body:
I used this code before and it was working fine. Now no matter what I do pandas is not working. I tried uninstalling and reinstalling. I used the previous file that was working, none of it is working. Can you help me find out whats happening?

This code:

import pandas as pd

...
df = pd.read.csv('all_stocks_5yr')

causes the following error:

---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-2-dc236c5894fa> in <module>
----> 1 df = pd.read.csv('all_stocks_5yr')

/Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-packages/pandas/__init__.py in __getattr__(name)
    261             return _SparseArray
    262
--> 263         raise AttributeError(f"module 'pandas' has no attribute '{name}'")
    264
    265

AttributeError: module 'pandas' has no attribute 'read'


问:
Mask certain data based on user privilege
I need some inputs or guidance on the below scenario;

I have an existing aspx web application contains 10 different pages (search/list/details/reports etc..) using plain sql to fetch data back and forth. This application is to maintain student information. Would like to implement a new feature where certain teachers (access levels) should not be allowed to view student details (not to hide, masking a row in grid or table in all pages) based on some age (which can be configured in web config).

Would like to know the possible options to implement this feature in a best and efficient way in c# or sql server.

Thanks in advance guys

答:
If I was implementing a feature like this I would put a new property on the teacher to indicate the access level that they have.

Hopefully you can extract this logic into a shared location (and not on every page) but when you load your page you check if the logged in teacher has the necessary access level. If the user does not have the correct access level then you can either modify the query being sent to the database to exclude records that do not meet the age criteria, or you can filter what data gets sent back to the page to be displayed.

If you gave us some sample code or more details I could be more specific.


问:
C# HttpClient, getting error Cannot add value because header 'content-type' does not support multiple values
```<code>HttpClient serviceClient = new HttpClient();
serviceClient.DefaultRequestHeaders.Add("accept", "Application/JSON");

HttpContent content = new StringContent(text);
content.Headers.Add("content-type", "text/html");

var response = await serviceClient.PostAsync(new Uri(_serviceUrl), content);
</code>```

This is my code. I want to do a POST, and set the content type to text/html, but when I do this I get the above error.

I can set the content type it seems via content.Headers.ContentType but I don't know how to specifcy "text/html" if I do that. Can anyone help?

答:
As soon as you assign a text value to the HttpContent by doing this-

```<code>HttpContent content = new StringContent(text);
</code>```

the content type is automatically set for that content. This content type (in case of String Content) is - {text/plain; charset=utf-8}

So in the next step when you try to explicitly set the Content-Type header you get the error- Cannot add value because header 'Content-Type' does not support multiple values.

There are three ways by which you can set the content type and avoid this error:

Option 1. Specify the content type while setting the content

```<code>HttpContent content = new StringContent(text, System.Text.Encoding.UTF8, "text/html");
</code>```

Option 2. Setting the ContentType property

```<code>HttpContent content = new StringContent(text);
content.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("text/html");
</code>```

Option 3. First remove the automatically assigned content-type header and then add that header again.

```<code>HttpContent content = new StringContent(text);
content.Headers.Remove("content-type");
content.Headers.Add("content-type", "text/html");
</code>```

Body:
HttpClient serviceClient = new HttpClient();
serviceClient.DefaultRequestHeaders.Add("accept", "Application/JSON");

HttpContent content = new StringContent(text);
content.Headers.Add("content-type", "text/html");

var response = await serviceClient.PostAsync(new Uri(_serviceUrl), content);

This is my code. I want to do a POST, and set the content type to text/html, but when I do this I get the above error.

I can set the content type it seems via content.Headers.ContentType but I don't know how to specifcy "text/html" if I do that. Can anyone help?

Body:
As soon as you assign a text value to the HttpContent by doing this-

HttpContent content = new StringContent(text);

the content type is automatically set for that content. This content type (in case of String Content) is - {text/plain; charset=utf-8}

So in the next step when you try to explicitly set the Content-Type header you get the error- Cannot add value because header 'Content-Type' does not support multiple values.

There are three ways by which you can set the content type and avoid this error:

Option 1. Specify the content type while setting the content

HttpContent content = new StringContent(text, System.Text.Encoding.UTF8, "text/html");

Option 2. Setting the ContentType property

HttpContent content = new StringContent(text);
content.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("text/html");

Option 3. First remove the automatically assigned content-type header and then add that header again.

HttpContent content = new StringContent(text);
content.Headers.Remove("content-type");
content.Headers.Add("content-type", "text/html");


问:
Data Received from Laravel API Server Not Shown on Flutter Screen
I am trying to receive data from Laravel php server and show it on Flutter Login screen which directs to Dashboard after successful login , but there is no data shown and only the loading icon keeps  loading on screen.

Here is the code of Login:

```<code>class DashboardState extends State<Dashboard>{

  DataBaseHelper dataBaseHelper = new DataBaseHelper();
  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return MaterialApp(
      title: 'Dashboard',
      home: Scaffold(
        appBar: AppBar(
          title: Text('Dashboard'),
        ),
        floatingActionButton: FloatingActionButton(
          onPressed: ()=>
              Navigator.of(context).push(new MaterialPageRoute(
                builder: (BuildContext context)=> new AddData(),
              ))
          ,
          child: Icon(Icons.add),
        ),
        body: Container(
          child: FutureBuilder<List>(
            future: dataBaseHelper.getData(),
            builder: (context, snapshot){
              if(snapshot.hasError) print(snapshot.error);
              return snapshot.hasData
                  ? new ItemList(list: snapshot.data)
                  : new Center(child: CircularProgressIndicator(),);
            },
          )
        ),
      ),
    );
  }

}
</code>```

And here is getData() function which receive the data from server and located in databasehelper:

```<code>Future<List> getData() async{
final prefs = await SharedPreferences.getInstance();
final key = 'token';
final value =  prefs.get(key) ?? 0;

var url = '$serverUrl/cars/';
final response = await http.get(url,
    headers: {
      'Accept':'application/json',
      'Authorization' : 'Bearer $value'
    },

);
return json.decode(response.body);
}
</code>```

Note I receive the following message on console when the user logged in and go to dashboard:

```<code>I/flutter ( 9962): type '_InternalLinkedHashMap<String, dynamic>' is not a subtype of type 'FutureOr<List<dynamic>>'
</code>```

答: The issue is FutureBuilder<List> is expecting List and getData is returning InternalLinkedHashMap<String, dynamic>. Return the object model to increase code readability and expect the same object class for e.g. FutureBuilder<CustomModel>. Check this.

Body:
I am trying to receive data from Laravel php server and show it on Flutter Login screen which directs to Dashboard after successful login , but there is no data shown and only the loading icon keeps  loading on screen.

Here is the code of Login:

class DashboardState extends State<Dashboard>{

  DataBaseHelper dataBaseHelper = new DataBaseHelper();
  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return MaterialApp(
      title: 'Dashboard',
      home: Scaffold(
        appBar: AppBar(
          title: Text('Dashboard'),
        ),
        floatingActionButton: FloatingActionButton(
          onPressed: ()=>
              Navigator.of(context).push(new MaterialPageRoute(
                builder: (BuildContext context)=> new AddData(),
              ))
          ,
          child: Icon(Icons.add),
        ),
        body: Container(
          child: FutureBuilder<List>(
            future: dataBaseHelper.getData(),
            builder: (context, snapshot){
              if(snapshot.hasError) print(snapshot.error);
              return snapshot.hasData
                  ? new ItemList(list: snapshot.data)
                  : new Center(child: CircularProgressIndicator(),);
            },
          )
        ),
      ),
    );
  }

}

And here is getData() function which receive the data from server and located in databasehelper:

Future<List> getData() async{
final prefs = await SharedPreferences.getInstance();
final key = 'token';
final value =  prefs.get(key) ?? 0;

var url = '$serverUrl/cars/';
final response = await http.get(url,
    headers: {
      'Accept':'application/json',
      'Authorization' : 'Bearer $value'
    },

);
return json.decode(response.body);
}

Note I receive the following message on console when the user logged in and go to dashboard:

I/flutter ( 9962): type '_InternalLinkedHashMap<String, dynamic>' is not a subtype of type 'FutureOr<List<dynamic>>'


问:
Stop scipy.optimize.minimize after maximum runtime
I run scipy.optimize.minimize(method='L-BFGS-B') on a cluster. Tasks running longer than 72 hours will be killed without any option of saving the result. Is there a way to exit scipy.optimize.minimize() after a runtime of T=48h has passed?

答:
One approach is to estimate the evaluation time of one iteration and then set maxiter in the options argument accordingly.

Another approach is to define a class, which modifies a function fun such that it returns an error after a specified time and records the last input value x and its output fun(x):

```<code>from scipy.optimize import minimize
import numpy as np
import time

class TimedFun:
    def __init__(self, fun, stop_after=10):
        self.fun_in = fun
        self.started = False
        self.stop_after = stop_after

    def fun(self, x):
        if self.started is False:
            self.started = time.time()
        elif abs(time.time() - self.started) >= self.stop_after:
            raise ValueError("Time is over.")
        self.fun_value = self.fun_in(x)
        self.x = x
        return self.fun_value
</code>```

With that the optimization can be stopped after fun is called, say, later than 2 seconds after the first call:

```<code>## Objective function:
def fun(x):
    time.sleep(5)
    return sum(x**2)

## Minimize with early stopping:
fun_timed = TimedFun(fun=fun, stop_after=2)
try:
    minimize(fun=fun_timed.fun, x0=np.array([100]), method='L-BFGS-B')
except Exception as e:
    print("Error: " + str(e))
# Error: Time is over.

## Retrieve last evaluated `x` and `fun(x)`:
print('x=', fun_timed.x, ', fun(x)=', fun_timed.fun_value, sep='')
# x=[100.], fun(x)=10000.0
</code>```

BTW, checkout my package optimparallel, which allows you to speedup the optimization with parallel computing and to return the evaluated value x, fun(x), and jac(x) of every step.

```<code>from optimparallel import minimize_parallel
minimize_parallel(fun=fun, x0=np.array([100]), parallel={'loginfo': True})
#      fun: 2.565413976271745e-17
# hess_inv: array([[0.50000039]])
#      jac: array([-1.29983171e-10])
#  loginfo: {'x': array([[ 1.00000000e+02],
#       [ 9.90000000e+01],
#       [ 9.50000000e+01],
#       [ 7.90000000e+01],
#       [ 8.22875951e-05],
#       [-5.06499159e-09]]), 'fun': array([[1.00000000e+04],
#       [9.80100000e+03],
#       [9.02500000e+03],
#       [6.24100000e+03],
#       [6.77124832e-09],
#       [2.56541398e-17]]), 'jac': array([[ 1.99999886e+02],
#       [ 1.97999907e+02],
#       [ 1.89999810e+02],
#       [ 1.57999875e+02],
#       [ 1.64585190e-04],
#       [-1.29983171e-10]])}
#  message: b'CONVERGENCE: NORM_OF_PROJECTED_GRADIENT_<=_PGTOL'
#     nfev: 6
#      nit: 3
#   status: 0
#  success: True
#        x: array([-5.06499159e-09])
</code>```

Body:
One approach is to estimate the evaluation time of one iteration and then set maxiter in the options argument accordingly.

Another approach is to define a class, which modifies a function fun such that it returns an error after a specified time and records the last input value x and its output fun(x):

from scipy.optimize import minimize
import numpy as np
import time

class TimedFun:
    def __init__(self, fun, stop_after=10):
        self.fun_in = fun
        self.started = False
        self.stop_after = stop_after

    def fun(self, x):
        if self.started is False:
            self.started = time.time()
        elif abs(time.time() - self.started) >= self.stop_after:
            raise ValueError("Time is over.")
        self.fun_value = self.fun_in(x)
        self.x = x
        return self.fun_value

With that the optimization can be stopped after fun is called, say, later than 2 seconds after the first call:

## Objective function:
def fun(x):
    time.sleep(5)
    return sum(x**2)

## Minimize with early stopping:
fun_timed = TimedFun(fun=fun, stop_after=2)
try:
    minimize(fun=fun_timed.fun, x0=np.array([100]), method='L-BFGS-B')
except Exception as e:
    print("Error: " + str(e))
# Error: Time is over.

## Retrieve last evaluated `x` and `fun(x)`:
print('x=', fun_timed.x, ', fun(x)=', fun_timed.fun_value, sep='')
# x=[100.], fun(x)=10000.0

BTW, checkout my package optimparallel, which allows you to speedup the optimization with parallel computing and to return the evaluated value x, fun(x), and jac(x) of every step.

from optimparallel import minimize_parallel
minimize_parallel(fun=fun, x0=np.array([100]), parallel={'loginfo': True})
#      fun: 2.565413976271745e-17
# hess_inv: array([[0.50000039]])
#      jac: array([-1.29983171e-10])
#  loginfo: {'x': array([[ 1.00000000e+02],
#       [ 9.90000000e+01],
#       [ 9.50000000e+01],
#       [ 7.90000000e+01],
#       [ 8.22875951e-05],
#       [-5.06499159e-09]]), 'fun': array([[1.00000000e+04],
#       [9.80100000e+03],
#       [9.02500000e+03],
#       [6.24100000e+03],
#       [6.77124832e-09],
#       [2.56541398e-17]]), 'jac': array([[ 1.99999886e+02],
#       [ 1.97999907e+02],
#       [ 1.89999810e+02],
#       [ 1.57999875e+02],
#       [ 1.64585190e-04],
#       [-1.29983171e-10]])}
#  message: b'CONVERGENCE: NORM_OF_PROJECTED_GRADIENT_<=_PGTOL'
#     nfev: 6
#      nit: 3
#   status: 0
#  success: True
#        x: array([-5.06499159e-09])


问:
Laravel group by date and count
I'm trying to add extra information to a Laravel eloquent collection based on the counting number of start(date) field. so the scenario is I have an "appointments" table, I want to add extra attributes to the object in the collection that's returned by eloquent if any days have more than 10 appointments. I have tried many ways like group by and count but didn't work. anyway I have the code below that's I think I'm so close to it but I have been working on it but couldn't find how to make it achieve what I want. I think I'm stuck and I can't think any more. I have commented most of the lines.</p>

```<code>        $allAppointments = Appointment::get($columns); //returning all the appointments

        $days = Appointment::get()->groupBy(function ($val) {
                return Carbon::parse($val->start)->format('d');
            }); //here I'm returning appointments by group without the count

        $counter = [];

        foreach ($days as $day => $appointments) {
            foreach ($appointments as $appointment) {

                if (Carbon::parse($appointment->start)->format('d') == $day) {
                    $counter = [Carbon::parse($appointment->start)->format('d') => $day]; //here I'm trying to make an array and count the days but not working
                }
                dd($counter);
                foreach ($allAppointments as $allAppointment) {
                    if (Carbon::parse($allAppointment->start)->format('d') == $day && count($counter) == 10) //here I want to compare the dates and check if that day have more than 10 appointments
                        $allAppointment->setAttribute('backgroundColor', 'red'); //here I want to add the extra information
                }
            }
        }
</code>```

答:
It's strange after working on it more than almost 10 hours, just 20 minutes after posting it here I could make it work. the code is below:</p>

```<code>public function all()
    {
        $columns = [
            'id',
            'title',
            'start',
            'end',
            'note',
            'allDay',
            'editable',
        ];

        $allAppointments = Appointment::get($columns);
        $days = Appointment::get()
            ->groupBy(function ($val) {
                return Carbon::parse($val->start)->format('d');
            });

        foreach ($days as $day => $appointments) {
            foreach ($appointments as $appointment) {
                foreach ($allAppointments as $key => $allAppointment) {
                    if (Carbon::parse($allAppointment->start)->format('d') == $day && $appointments->count() >= 10){
                        $allAppointment->setAttribute('backgroundColor', 'red');
                    }
                }
            }
        }

        return $allAppointments;
    }
</code>```

Title: Laravel group by date and count

Body:
I'm trying to add extra information to a Laravel eloquent collection based on the counting number of start(date) field. so the scenario is I have an "appointments" table, I want to add extra attributes to the object in the collection that's returned by eloquent if any days have more than 10 appointments. I have tried many ways like group by and count but didn't work. anyway I have the code below that's I think I'm so close to it but I have been working on it but couldn't find how to make it achieve what I want. I think I'm stuck and I can't think any more. I have commented most of the lines.

        $allAppointments = Appointment::get($columns); //returning all the appointments

        $days = Appointment::get()->groupBy(function ($val) {
                return Carbon::parse($val->start)->format('d');
            }); //here I'm returning appointments by group without the count

        $counter = [];

        foreach ($days as $day => $appointments) {
            foreach ($appointments as $appointment) {

                if (Carbon::parse($appointment->start)->format('d') == $day) {
                    $counter = [Carbon::parse($appointment->start)->format('d') => $day]; //here I'm trying to make an array and count the days but not working
                }
                dd($counter);
                foreach ($allAppointments as $allAppointment) {
                    if (Carbon::parse($allAppointment->start)->format('d') == $day && count($counter) == 10) //here I want to compare the dates and check if that day have more than 10 appointments
                        $allAppointment->setAttribute('backgroundColor', 'red'); //here I want to add the extra information
                }
            }
        }

Body:
It's strange after working on it more than almost 10 hours, just 20 minutes after posting it here I could make it work. the code is below:

public function all()
    {
        $columns = [
            'id',
            'title',
            'start',
            'end',
            'note',
            'allDay',
            'editable',
        ];

        $allAppointments = Appointment::get($columns);
        $days = Appointment::get()
            ->groupBy(function ($val) {
                return Carbon::parse($val->start)->format('d');
            });

        foreach ($days as $day => $appointments) {
            foreach ($appointments as $appointment) {
                foreach ($allAppointments as $key => $allAppointment) {
                    if (Carbon::parse($allAppointment->start)->format('d') == $day && $appointments->count() >= 10){
                        $allAppointment->setAttribute('backgroundColor', 'red');
                    }
                }
            }
        }

        return $allAppointments;
    }


问:
Firebase Phone Auth won't send me the sms with my code
I migrated my app from using Digits Phone Auth to the new Firebase Phone Auth but while I was testing my app I had troubles signing out my user (Already fixed that) so I just deleted it from the "User list" on the console but now every time I try to sign in with that phone number it won't send me the sms with my code, it works fine with any other number but this one. Does someone knows how can I fix this?</p>

答:
I changed my initial loading activity to logout activity through AndroidManifest file. Here is the final version:

```<code><activity android:name=".OtpActivity"></activity>
    <activity android:name=".LoginActivity" />
    <activity android:name=".MainActivity" />
    <activity android:name=".MainPageActivity">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
</code>```

MainPageActivity was my Logout Activity.

Body:
I changed my initial loading activity to logout activity through AndroidManifest file. Here is the final version:

<activity android:name=".OtpActivity"></activity>
    <activity android:name=".LoginActivity" />
    <activity android:name=".MainActivity" />
    <activity android:name=".MainPageActivity">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>

MainPageActivity was my Logout Activity.


问:
Not Popping up Permission box while clicking on Button- Android Studio
When I run the app, At the runtime it is not asking for the permission but after clicking on the back button, the popup message comes for the permission. I am not able to find out the mistake.</p>

```<code>public void onClickSignUp(View view){
    String permission = Manifest.permission.RECEIVE_SMS;
    int grant = ContextCompat.checkSelfPermission(this, permission);

    Intent intent = new Intent(FirstTimeUserPage.this,SignUpActivity.class);
    if ( grant != PackageManager.PERMISSION_GRANTED) {
        String[] permission_list = new String[1];
        permission_list[0] = permission;
        ActivityCompat.requestPermissions(this, permission_list, 1);
    }
    startActivity(intent);
}
</code>```

答:
First of all be careful that you declare these permission in the manifest too .If it don't work .you can use easy permission library that make it easy to request permissions.

Easy permission implementation:

```<code>implementation 'pub.devrel:easypermissions:3.0.0'
</code>```

after that you implement the library use this code at the runtime in your MainActivity.

```<code>String[] perms = {Manifest.permission.RECEIVE_SMS};
    if (!EasyPermissions.hasPermissions(this, perms)) {
        EasyPermissions.requestPermissions(this, "We need this permission",
                123, perms);
    }
</code>```

For handling that if the permission was granted or not implement this in your activity like the code below:

```<code>public class MenuActivity extends AppCompatActivity implements EasyPermissions.PermissionCallbacks
</code>```

After you implement the code at the top 3 methods come for you that you can handle the situation in your way.

```<code>@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
    EasyPermissions.onRequestPermissionsResult(requestCode, permissions, grantResults, this);
}

@Override
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
}

@Override
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
    if (EasyPermissions.somePermissionPermanentlyDenied(this, perms)) {
        new AppSettingsDialog.Builder(this).build().show();
    }
}
</code>```

Body:
When I run the app, At the runtime it is not asking for the permission but after clicking on the back button, the popup message comes for the permission. I am not able to find out the mistake.

public void onClickSignUp(View view){
    String permission = Manifest.permission.RECEIVE_SMS;
    int grant = ContextCompat.checkSelfPermission(this, permission);

    Intent intent = new Intent(FirstTimeUserPage.this,SignUpActivity.class);
    if ( grant != PackageManager.PERMISSION_GRANTED) {
        String[] permission_list = new String[1];
        permission_list[0] = permission;
        ActivityCompat.requestPermissions(this, permission_list, 1);
    }
    startActivity(intent);
}

Body:
First of all be careful that you declare these permission in the manifest too .If it don't work .you can use easy permission library that make it easy to request permissions.

Easy permission implementation:

implementation 'pub.devrel:easypermissions:3.0.0'

after that you implement the library use this code at the runtime in your MainActivity.

String[] perms = {Manifest.permission.RECEIVE_SMS};
    if (!EasyPermissions.hasPermissions(this, perms)) {
        EasyPermissions.requestPermissions(this, "We need this permission",
                123, perms);
    }

For handling that if the permission was granted or not implement this in your activity like the code below:

public class MenuActivity extends AppCompatActivity implements EasyPermissions.PermissionCallbacks

After you implement the code at the top 3 methods come for you that you can handle the situation in your way.

@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
    EasyPermissions.onRequestPermissionsResult(requestCode, permissions, grantResults, this);
}

@Override
public void onPermissionsGranted(int requestCode, @NonNull List<String> perms) {
}

@Override
public void onPermissionsDenied(int requestCode, @NonNull List<String> perms) {
    if (EasyPermissions.somePermissionPermanentlyDenied(this, perms)) {
        new AppSettingsDialog.Builder(this).build().show();
    }
}


问:
Group By in java 8 with multiple levels of grouping
I have such structure

```<code>| Director1 | Manager1 | Employee1 |
| Director1 | Manager1 | Employee2 |
| Director1 | Manager2 | Employee3 |
| Director2 | Manager3 | Employee4 |
</code>```

I fetch this data from Db to Pojo like this

```<code>@Data
public class Workers {
 private String directorName;
 private String managerName;
 private String employeeName;
}
</code>```

DB is denormalized.

Mow in java code I need to group this response to not to return redundant data. My response data looks like

```<code>@Data
public class WorkersResponse{
 private String directorName;
 ...
 private List<Manager> managers;
}

@Data
public class Manager{
 private String manager;
  ...
 private List<Employee> employee;
}

@Data
public class Employee{
 private String employee;
 ...
}
</code>```

With grouping I want to receive List. For now I figured out how to group directors :

```<code>Map<WorkersResponse, List<Workers >> collect = all.stream()
            .collect(Collectors.groupingBy(v -> {
                WorkersResponse workersResponse= new WorkersResponse();
                workersResponse.setDirector(v.getDirectorName());
                return workersResponse;
            }));
</code>```

But how should then I populate list with Managers and Employees?

答:
@Naman already given the better answer, just want to add,
you can get WorkersResponse in this way also using collectingAndThen

```<code>List<WorkersResponse> requirement = workersList.stream()
        .collect(Collectors.collectingAndThen(Collectors.groupingBy(Workers::getDirectorName,
                Collectors.collectingAndThen(Collectors.groupingBy(Workers::getManagerName,
                        Collectors.mapping(w -> new Employee(w.getEmployeeName()),Collectors.toList())),
                    e -> e.entrySet().stream().map(ie -> new Manager(ie.getKey(), ie.getValue()))
                          .collect(Collectors.toList()))),
            e -> e.entrySet().stream().map(ie -> new WorkersResponse(ie.getKey(), ie.getValue()))
                          .collect(Collectors.toList())));
</code>```

Body:
I have such structure

| Director1 | Manager1 | Employee1 |
| Director1 | Manager1 | Employee2 |
| Director1 | Manager2 | Employee3 |
| Director2 | Manager3 | Employee4 |

I fetch this data from Db to Pojo like this

@Data
public class Workers {
 private String directorName;
 private String managerName;
 private String employeeName;
}

DB is denormalized.

Mow in java code I need to group this response to not to return redundant data. My response data looks like

@Data
public class WorkersResponse{
 private String directorName;
 ...
 private List<Manager> managers;
}

@Data
public class Manager{
 private String manager;
  ...
 private List<Employee> employee;
}

@Data
public class Employee{
 private String employee;
 ...
}

With grouping I want to receive List. For now I figured out how to group directors :

Map<WorkersResponse, List<Workers >> collect = all.stream()
            .collect(Collectors.groupingBy(v -> {
                WorkersResponse workersResponse= new WorkersResponse();
                workersResponse.setDirector(v.getDirectorName());
                return workersResponse;
            }));

But how should then I populate list with Managers and Employees?

Body:
@Naman already given the better answer, just want to add,
you can get WorkersResponse in this way also using collectingAndThen

List<WorkersResponse> requirement = workersList.stream()
        .collect(Collectors.collectingAndThen(Collectors.groupingBy(Workers::getDirectorName,
                Collectors.collectingAndThen(Collectors.groupingBy(Workers::getManagerName,
                        Collectors.mapping(w -> new Employee(w.getEmployeeName()),Collectors.toList())),
                    e -> e.entrySet().stream().map(ie -> new Manager(ie.getKey(), ie.getValue()))
                          .collect(Collectors.toList()))),
            e -> e.entrySet().stream().map(ie -> new WorkersResponse(ie.getKey(), ie.getValue()))
                          .collect(Collectors.toList())));


问:
Different execution time of C++ program in cmd.exe vs Powershell
I was benchmarking this fairly simple program:

```<code>#include <Windows.h>
#include <stdio.h>

void dotp(float *array1, float *array2, float *dest, size_t N) {
  for (size_t i = 0; i < N; ++i) {
      dest[i] += array1[i] * array2[i];
  }
}

float *newArray(int N) {
  float *x = new float[N];
  for (size_t i = 0; i < N; ++i) {
    x[i] = i;
  }
  return x;
}

int main(int argc, const char *argv[])
{
  SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
  LARGE_INTEGER StartingTime, EndingTime, ElapsedMicroseconds;
  LARGE_INTEGER Frequency;

  size_t LOOPS = 10 * 1000 * 1000;
  int N =  1024;

  float* x = newArray(N);
  float* y = newArray(N);
  float* z = newArray(N);

  QueryPerformanceFrequency(&Frequency);
  QueryPerformanceCounter(&StartingTime);
  for (size_t i = 0; i < LOOPS; ++i) {
    dotp(x, y, z, N);
  }
  QueryPerformanceCounter(&EndingTime);
  ElapsedMicroseconds.QuadPart = EndingTime.QuadPart - StartingTime.QuadPart;
  ElapsedMicroseconds.QuadPart *= 1000000;
  ElapsedMicroseconds.QuadPart /= Frequency.QuadPart;

  printf("%lld\r\n", Frequency.QuadPart);
  QueryPerformanceFrequency(&Frequency);
  printf("%lld\r\n", ElapsedMicroseconds.QuadPart);
  printf("%lld\r\n", Frequency.QuadPart);

  return 0;
}
</code>```

and compiling it with cl.exe /arch:AVX2 /O2 main.cpp.

When running it in in cmd.exe, it takes about 1 seconds to run (I did many runs, no difference):

```<code>.\main.exe
10000000
1023448
10000000
</code>```

However when running it in Powershell, it's substantially (and consistently over many runs, no matter what else is going on in my OS) faster:

```<code> .\main.exe
10000000
620746
10000000
</code>```

Using some simple shell commands corroborate what the performance counters say:

```<code>cmd /v:on /c "echo !time! & .\main.exe & echo !time!
11:59:11.38
10000000
1004120
10000000
11:59:12.39
</code>```

```<code> Measure-Command {.\main.exe}

Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 630
Ticks             : 6308918
TotalDays         : 7.30198842592593E-06
TotalHours        : 0.000175247722222222
TotalMinutes      : 0.0105148633333333
TotalSeconds      : 0.6308918
TotalMilliseconds : 630.8918
</code>```

I printed the performance counter frequency before and after the profiled code in case there was a change and also set the priority class of the process just in case cmd.exe and Powershell treated it differently. No differences.

On top of that, as soon as include iostream and use it to print something else, the cmd.exe and Powershell give equivalent results (speed increase for cmd.exe, speed decrease for Powershell).

```<code>#include <Windows.h>
#include <stdio.h>
#include <iostream>

void dotp(float *array1, float *array2, float *dest, size_t N) {
  for (size_t i = 0; i < N; ++i) {
      dest[i] += array1[i] * array2[i];
  }
}

float *newArray(int N) {
  float *x = new float[N];
  for (size_t i = 0; i < N; ++i) {
    x[i] = i;
  }
  return x;
}

int main(int argc, const char *argv[])
{
  SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
  LARGE_INTEGER StartingTime, EndingTime, ElapsedMicroseconds;
  LARGE_INTEGER Frequency;

  size_t LOOPS = 10 * 1000 * 1000;
  int N =  1024;

  float* x = newArray(N);
  float* y = newArray(N);
  float* z = newArray(N);

  QueryPerformanceFrequency(&Frequency);
  QueryPerformanceCounter(&StartingTime);
  for (size_t i = 0; i < LOOPS; ++i) {
    dotp(x, y, z, N);
  }
  QueryPerformanceCounter(&EndingTime);
  ElapsedMicroseconds.QuadPart = EndingTime.QuadPart - StartingTime.QuadPart;
  ElapsedMicroseconds.QuadPart *= 1000000;
  ElapsedMicroseconds.QuadPart /= Frequency.QuadPart;

  printf("%lld\r\n", Frequency.QuadPart);
  QueryPerformanceFrequency(&Frequency);
  printf("%lld\r\n", ElapsedMicroseconds.QuadPart);
  printf("%lld\r\n", Frequency.QuadPart);
  std::cout << "blah" << std::endl;

  return 0;
}
</code>```

cmd.exe:

```<code>.\main.exe
10000000
776086
10000000
blah
</code>```

Powershell:

```<code>.\main.exe
10000000
763109
10000000
blah
</code>```

I'm not sure how to explain these discrepancies.

答:
Timing an application is a REALLY COMPLICATED deal. And the reasons for that is that you are NOT using a real time operational system.

Your processor stops executing your application to change the context to another process and so for so you have illusion of real time.

Check this to better undestand why your code wont work correctly:
https://en.wikipedia.org/wiki/Scheduling_(computing)

Hope I helped

Body:
I was benchmarking this fairly simple program:

#include <Windows.h>
#include <stdio.h>

void dotp(float *array1, float *array2, float *dest, size_t N) {
  for (size_t i = 0; i < N; ++i) {
      dest[i] += array1[i] * array2[i];
  }
}

float *newArray(int N) {
  float *x = new float[N];
  for (size_t i = 0; i < N; ++i) {
    x[i] = i;
  }
  return x;
}

int main(int argc, const char *argv[])
{
  SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
  LARGE_INTEGER StartingTime, EndingTime, ElapsedMicroseconds;
  LARGE_INTEGER Frequency;

  size_t LOOPS = 10 * 1000 * 1000;
  int N =  1024;

  float* x = newArray(N);
  float* y = newArray(N);
  float* z = newArray(N);

  QueryPerformanceFrequency(&Frequency);
  QueryPerformanceCounter(&StartingTime);
  for (size_t i = 0; i < LOOPS; ++i) {
    dotp(x, y, z, N);
  }
  QueryPerformanceCounter(&EndingTime);
  ElapsedMicroseconds.QuadPart = EndingTime.QuadPart - StartingTime.QuadPart;
  ElapsedMicroseconds.QuadPart *= 1000000;
  ElapsedMicroseconds.QuadPart /= Frequency.QuadPart;

  printf("%lld\r\n", Frequency.QuadPart);
  QueryPerformanceFrequency(&Frequency);
  printf("%lld\r\n", ElapsedMicroseconds.QuadPart);
  printf("%lld\r\n", Frequency.QuadPart);

  return 0;
}

and compiling it with cl.exe /arch:AVX2 /O2 main.cpp.

When running it in in cmd.exe, it takes about 1 seconds to run (I did many runs, no difference):

.\main.exe
10000000
1023448
10000000

However when running it in Powershell, it's substantially (and consistently over many runs, no matter what else is going on in my OS) faster:

 .\main.exe
10000000
620746
10000000

Using some simple shell commands corroborate what the performance counters say:

cmd /v:on /c "echo !time! & .\main.exe & echo !time!
11:59:11.38
10000000
1004120
10000000
11:59:12.39

 Measure-Command {.\main.exe}

Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 630
Ticks             : 6308918
TotalDays         : 7.30198842592593E-06
TotalHours        : 0.000175247722222222
TotalMinutes      : 0.0105148633333333
TotalSeconds      : 0.6308918
TotalMilliseconds : 630.8918

I printed the performance counter frequency before and after the profiled code in case there was a change and also set the priority class of the process just in case cmd.exe and Powershell treated it differently. No differences.

On top of that, as soon as include iostream and use it to print something else, the cmd.exe and Powershell give equivalent results (speed increase for cmd.exe, speed decrease for Powershell).

#include <Windows.h>
#include <stdio.h>
#include <iostream>

void dotp(float *array1, float *array2, float *dest, size_t N) {
  for (size_t i = 0; i < N; ++i) {
      dest[i] += array1[i] * array2[i];
  }
}

float *newArray(int N) {
  float *x = new float[N];
  for (size_t i = 0; i < N; ++i) {
    x[i] = i;
  }
  return x;
}

int main(int argc, const char *argv[])
{
  SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
  LARGE_INTEGER StartingTime, EndingTime, ElapsedMicroseconds;
  LARGE_INTEGER Frequency;

  size_t LOOPS = 10 * 1000 * 1000;
  int N =  1024;

  float* x = newArray(N);
  float* y = newArray(N);
  float* z = newArray(N);

  QueryPerformanceFrequency(&Frequency);
  QueryPerformanceCounter(&StartingTime);
  for (size_t i = 0; i < LOOPS; ++i) {
    dotp(x, y, z, N);
  }
  QueryPerformanceCounter(&EndingTime);
  ElapsedMicroseconds.QuadPart = EndingTime.QuadPart - StartingTime.QuadPart;
  ElapsedMicroseconds.QuadPart *= 1000000;
  ElapsedMicroseconds.QuadPart /= Frequency.QuadPart;

  printf("%lld\r\n", Frequency.QuadPart);
  QueryPerformanceFrequency(&Frequency);
  printf("%lld\r\n", ElapsedMicroseconds.QuadPart);
  printf("%lld\r\n", Frequency.QuadPart);
  std::cout << "blah" << std::endl;

  return 0;
}

cmd.exe:

.\main.exe
10000000
776086
10000000
blah

Powershell:

.\main.exe
10000000
763109
10000000
blah

I'm not sure how to explain these discrepancies.


问:
Vim, autoindent, xml and autoclosing tag
Here my vimrc

```<code>filetype plugin indent on
set autoindent
set tabstop=2
set shiftwidth=2
set softtabstop=2
</code>```

And that all.

Let suppose I start a new xml file.

WHen a use normal tag, autoindent work well

```<code><div>
  <p>
     Some text
  </p>
</div>
</code>```

But if I insert autoclosing tags, autoindnet don't recognize the autoclosing feature,and I get something like this.

```<code><div>
  <p>
     Some text<lb />
        Some text<lb />
             Some text<lb />
  </p>
</div>
</code>```

I use vim 8.1.2269. I tried with nvim 0.4.3 > same problem. WHat is strange is that in the past (before my new fresh installation of Ubuntu), I didn't get any problem...

答:
Yes was a bug, solved by the maintener.

https://github.com/chrisbra/vim-xml-runtime/issues/25

Body:
Here my vimrc

filetype plugin indent on
set autoindent
set tabstop=2
set shiftwidth=2
set softtabstop=2

And that all.

Let suppose I start a new xml file.

WHen a use normal tag, autoindent work well

     Some text

But if I insert autoclosing tags, autoindnet don't recognize the autoclosing feature,and I get something like this.

     Some text<lb />
        Some text<lb />
             Some text<lb />

I use vim 8.1.2269. I tried with nvim 0.4.3 > same problem. WHat is strange is that in the past (before my new fresh installation of Ubuntu), I didn't get any problem...