问:
Two Inputs side by side CSS
I'm currently practicing some WebDev and I'm working on an interactive food pyramid. I've been able to align the other inputs but the inputs on top of the triangle are giving me trouble, I've tried everything from floats to flex and inline blocks. Nothing seems to work, any help would be greatly appreciated.

function incrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number1').value = value;
}

function decrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number1').value = value;
}

function incrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number2').value = value;
}

function decrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number2').value = value;
}

function incrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number3').value = value;
}

function decrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number3').value = value;
}

function incrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number4').value = value;
}

function decrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number4').value = value;
}

function incrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number5').value = value;
}

function decrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number5').value = value;
}

function incrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number6').value = value;
}

function decrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number6').value = value;
}

var colors = ["red", "blue", "green", "yellow", "purple", "gold", "pink", "grey", "turquoise", "aqua"];
var i = 0;
var selectedColor;

function changeColour() {
  selectedColor = colors[i];
  document.getElementById("number" + 1).style.backgroundColor = selectedColor;
  i++;
  if (i > colors.length)
    i = 0;
}

function printDate() {
  let value = document.getElementById("date").value;
  document.getElementById("check").innerHTML = "Date: " + value;
}```
<pre class="snippet-code-css lang-css prettyprint-override"><code>.container {
  text-align: center;
  position: relative;
  top: 40%;
}

.inside-text1 {
  display: none;
  position: absolute;
  top: 20px;
  left: 248px;
  text-align: center;
  bottom: -65px;
}

.inside-text {
  display: none;
  position: relative;
  text-align: center;
  bottom: -25px;
}

.inside-text6 {
  display: none;
  position: relative;
  text-align: center;
  bottom: -120px;
  /*float: left;*/
}

#p6 {
  border-bottom: 200px solid blue;
  border-left: 100px solid transparent;
  border-right: 100px solid transparent;
  height: 0;
  width: 0;
  margin-right: auto;
  margin-left: auto;
}

#p5-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 10px;
  margin-right: auto;
  margin-left: auto;
}

#p5 {
  border-bottom: 80px solid black;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 220px;
  margin-right: auto;
  margin-left: auto;
}

#p4-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 240px;
  margin-right: auto;
  margin-left: auto;
}

#p4 {
  border-bottom: 80px solid purple;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 330px;
  margin-right: auto;
  margin-left: auto;
}

#p3 {
  border-bottom: 80px solid green;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 420px;
  margin-right: auto;
  margin-left: auto;
}

#p2 {
  border-bottom: 80px solid yellow;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 510px;
  margin-right: auto;
  margin-left: auto;
}

#p1 {
  position: relative;
  top: 40%;
  border-bottom: 80px solid red;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 600px;
  margin-right: auto;
  margin-left: auto;
}

#p1:hover .inside-text1 {
  display: block;
}

#p2:hover .inside-text {
  display: block;
}

#p3:hover .inside-text {
  display: block;
}

#p4:hover .inside-text {
  display: block;
}

#p5:hover .inside-text {
  display: block;
}

#p6:hover .inside-text6 {
  display: block;
}

.button {
  margin-right: auto;
  margin-left: auto;
  position: relative;
}

#b1 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number1 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  background-color: grey;
  text-align: center;
}

#b2 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b3 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number2 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b4 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b5 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number3 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b6 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b7 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number4 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b8 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b9 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number5 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b10 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b11 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number6 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b12 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#check {
  display: block;
  position: center;
  height: 25px;
  width: 125px;
  /*border-radius: 50%;*/
  border: solid red;
  text-align: center;
}</code>```

      <input type="button" onclick="decrementValue6()" value="-" id="b11" />
      <input type="text" id="number6" value="0" />
      <input type="button" onclick="incrementValue6()" value="+" id="b12" />

      <form>
        <input type="button" onclick="decrementValue5()" value="-" id="b9" />
        <input type="text" id="number5" value="1" />
        <input type="button" onclick="incrementValue5()" value="+" id="b10" />
      </form>

      <form>
        <input type="button" onclick="decrementValue4()" value="-" id="b7" />
        <input type="text" id="number4" value="2" />
        <input type="button" onclick="incrementValue4();" value="+" id="b8" />
      </form>

      <form>
        <input type="button" onclick="decrementValue3()" value="-" id="b5" />
        <input type="text" id="number3" value="3" />
        <input type="button" onclick="incrementValue3()" value="+" id="b6" />
      </form>

      <form>
        <input type="button" onclick="decrementValue2()" value="-" id="b3" />
        <input type="text" id="number2" value="4" />
        <input type="button" onclick="incrementValue2()" value="+" id="b4" />
      </form>

      <form>
        <input type="button" onclick="decrementValue1('number6');changeColour()" value="-" id="b2" />
        <input type="text" id="number1" value="6" />
        <input type="button" onclick="incrementValue1();changeColour()" value="+" id="b1" />
      </form>

Enter Date of Submission:
<input type="date" id="date" value="0" />
<input type="button" onclick="printDate()" value="Record" />

```

答:
You can use flex + justify-content to center content and avoid it to wrap on a few lines :

```<code>#p6:hover .inside-text6 {
    display:flex;
  justify-content:center;/* it will center content which might overflow on both sides too */
}
</code>```

Demo of you code updated to run below :

function incrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number1').value = value;
}

function decrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number1').value = value;
}

function incrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number2').value = value;
}

function decrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number2').value = value;
}

function incrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number3').value = value;
}

function decrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number3').value = value;
}

function incrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number4').value = value;
}

function decrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number4').value = value;
}

function incrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number5').value = value;
}

function decrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number5').value = value;
}

function incrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number6').value = value;
}

function decrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number6').value = value;
}

var colors = ["red", "blue", "green", "yellow", "purple", "gold", "pink", "grey", "turquoise", "aqua"];
var i = 0;
var selectedColor;

function changeColour() {
  selectedColor = colors[i];
  document.getElementById("number" + 1).style.backgroundColor = selectedColor;
  i++;
  if (i > colors.length)
    i = 0;
}

function printDate() {
  let value = document.getElementById("date").value;
  document.getElementById("check").innerHTML = "Date: " + value;
}```
<pre class="snippet-code-css lang-css prettyprint-override"><code>.container {
  text-align: center;
  position: relative;
  top: 40%;
}

.inside-text1 {
  display: none;
  position: absolute;
  top: 20px;
  left: 248px;
  text-align: center;
  bottom: -65px;
}

.inside-text {
  display: none;
  position: relative;
  text-align: center;
  bottom: -25px;
}

.inside-text6 {
  display: none;
  position: relative;
  text-align: center;
  bottom: -120px
}

#p6 {
  border-bottom: 200px solid blue;
  border-left: 100px solid transparent;
  border-right: 100px solid transparent;
  height: 0;
  width: 0;
  margin-right: auto;
  margin-left: auto;
}

#p5-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 10px;
  margin-right: auto;
  margin-left: auto;
}

#p5 {
  border-bottom: 80px solid black;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 220px;
  margin-right: auto;
  margin-left: auto;
}

#p4-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 240px;
  margin-right: auto;
  margin-left: auto;
}

#p4 {
  border-bottom: 80px solid purple;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 330px;
  margin-right: auto;
  margin-left: auto;
}

#p3 {
  border-bottom: 80px solid green;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 420px;
  margin-right: auto;
  margin-left: auto;
}

#p2 {
  border-bottom: 80px solid yellow;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 510px;
  margin-right: auto;
  margin-left: auto;
}

#p1 {
  position: relative;
  top: 40%;
  border-bottom: 80px solid red;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 600px;
  margin-right: auto;
  margin-left: auto;
}

#p1:hover .inside-text1 {
  display: block;
}

#p2:hover .inside-text {
  display: block;
}

#p3:hover .inside-text {
  display: block;
}

#p4:hover .inside-text {
  display: block;
}

#p5:hover .inside-text {
  display: block;
}

#p6:hover .inside-text6 {
    display:flex;
  justify-content:center;
}

.button {
  margin-right: auto;
  margin-left: auto;
  position: relative;
}

#b1 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number1 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  background-color: grey;
  text-align: center;
}

#b2 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b3 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number2 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b4 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b5 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number3 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b6 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b7 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number4 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b8 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b9 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number5 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b10 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b11 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number6 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b12 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#check {
  display: block;
  position: center;
  height: 25px;
  width: 125px;
  /*border-radius: 50%;*/
  border: solid red;
  text-align: center;
}</code>```

      <input type="button" onclick="decrementValue6()" value="-" id="b11" />
      <input type="text" id="number6" value="0" />
      <input type="button" onclick="incrementValue6()" value="+" id="b12" />

      <form>
        <input type="button" onclick="decrementValue5()" value="-" id="b9" />
        <input type="text" id="number5" value="1" />
        <input type="button" onclick="incrementValue5()" value="+" id="b10" />
      </form>

      <form>
        <input type="button" onclick="decrementValue4()" value="-" id="b7" />
        <input type="text" id="number4" value="2" />
        <input type="button" onclick="incrementValue4();" value="+" id="b8" />
      </form>

      <form>
        <input type="button" onclick="decrementValue3()" value="-" id="b5" />
        <input type="text" id="number3" value="3" />
        <input type="button" onclick="incrementValue3()" value="+" id="b6" />
      </form>

      <form>
        <input type="button" onclick="decrementValue2()" value="-" id="b3" />
        <input type="text" id="number2" value="4" />
        <input type="button" onclick="incrementValue2()" value="+" id="b4" />
      </form>

      <form>
        <input type="button" onclick="decrementValue1('number6');changeColour()" value="-" id="b2" />
        <input type="text" id="number1" value="6" />
        <input type="button" onclick="incrementValue1();changeColour()" value="+" id="b1" />
      </form>

Enter Date of Submission:
<input type="date" id="date" value="0" />
<input type="button" onclick="printDate()" value="Record" />

```

Title: Two Inputs side by side CSS

Body:
I'm currently practicing some WebDev and I'm working on an interactive food pyramid. I've been able to align the other inputs but the inputs on top of the triangle are giving me trouble, I've tried everything from floats to flex and inline blocks. Nothing seems to work, any help would be greatly appreciated.

function incrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number1').value = value;
}

function decrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number1').value = value;
}

function incrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number2').value = value;
}

function decrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number2').value = value;
}

function incrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number3').value = value;
}

function decrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number3').value = value;
}

function incrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number4').value = value;
}

function decrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number4').value = value;
}

function incrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number5').value = value;
}

function decrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number5').value = value;
}

function incrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number6').value = value;
}

function decrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number6').value = value;
}

var colors = ["red", "blue", "green", "yellow", "purple", "gold", "pink", "grey", "turquoise", "aqua"];
var i = 0;
var selectedColor;

function changeColour() {
  selectedColor = colors[i];
  document.getElementById("number" + 1).style.backgroundColor = selectedColor;
  i++;
  if (i > colors.length)
    i = 0;
}

function printDate() {
  let value = document.getElementById("date").value;
  document.getElementById("check").innerHTML = "Date: " + value;
}

.container {
  text-align: center;
  position: relative;
  top: 40%;
}

.inside-text1 {
  display: none;
  position: absolute;
  top: 20px;
  left: 248px;
  text-align: center;
  bottom: -65px;
}

.inside-text {
  display: none;
  position: relative;
  text-align: center;
  bottom: -25px;
}

.inside-text6 {
  display: none;
  position: relative;
  text-align: center;
  bottom: -120px;
  /*float: left;*/
}

#p6 {
  border-bottom: 200px solid blue;
  border-left: 100px solid transparent;
  border-right: 100px solid transparent;
  height: 0;
  width: 0;
  margin-right: auto;
  margin-left: auto;
}

#p5-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 10px;
  margin-right: auto;
  margin-left: auto;
}

#p5 {
  border-bottom: 80px solid black;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 220px;
  margin-right: auto;
  margin-left: auto;
}

#p4-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 240px;
  margin-right: auto;
  margin-left: auto;
}

#p4 {
  border-bottom: 80px solid purple;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 330px;
  margin-right: auto;
  margin-left: auto;
}

#p3 {
  border-bottom: 80px solid green;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 420px;
  margin-right: auto;
  margin-left: auto;
}

#p2 {
  border-bottom: 80px solid yellow;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 510px;
  margin-right: auto;
  margin-left: auto;
}

#p1 {
  position: relative;
  top: 40%;
  border-bottom: 80px solid red;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 600px;
  margin-right: auto;
  margin-left: auto;
}

#p1:hover .inside-text1 {
  display: block;
}

#p2:hover .inside-text {
  display: block;
}

#p3:hover .inside-text {
  display: block;
}

#p4:hover .inside-text {
  display: block;
}

#p5:hover .inside-text {
  display: block;
}

#p6:hover .inside-text6 {
  display: block;
}

.button {
  margin-right: auto;
  margin-left: auto;
  position: relative;
}

#b1 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number1 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  background-color: grey;
  text-align: center;
}

#b2 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b3 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number2 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b4 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b5 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number3 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b6 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b7 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number4 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b8 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b9 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number5 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b10 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b11 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number6 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b12 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#check {
  display: block;
  position: center;
  height: 25px;
  width: 125px;
  /*border-radius: 50%;*/
  border: solid red;
  text-align: center;
}

      <input type="button" onclick="decrementValue6()" value="-" id="b11" />
      <input type="text" id="number6" value="0" />
      <input type="button" onclick="incrementValue6()" value="+" id="b12" />

      <form>
        <input type="button" onclick="decrementValue5()" value="-" id="b9" />
        <input type="text" id="number5" value="1" />
        <input type="button" onclick="incrementValue5()" value="+" id="b10" />
      </form>

      <form>
        <input type="button" onclick="decrementValue4()" value="-" id="b7" />
        <input type="text" id="number4" value="2" />
        <input type="button" onclick="incrementValue4();" value="+" id="b8" />
      </form>

      <form>
        <input type="button" onclick="decrementValue3()" value="-" id="b5" />
        <input type="text" id="number3" value="3" />
        <input type="button" onclick="incrementValue3()" value="+" id="b6" />
      </form>

      <form>
        <input type="button" onclick="decrementValue2()" value="-" id="b3" />
        <input type="text" id="number2" value="4" />
        <input type="button" onclick="incrementValue2()" value="+" id="b4" />
      </form>

      <form>
        <input type="button" onclick="decrementValue1('number6');changeColour()" value="-" id="b2" />
        <input type="text" id="number1" value="6" />
        <input type="button" onclick="incrementValue1();changeColour()" value="+" id="b1" />
      </form>

Enter Date of Submission:
<input type="date" id="date" value="0" />
<input type="button" onclick="printDate()" value="Record" />

Body:
You can use flex + justify-content to center content and avoid it to wrap on a few lines :

#p6:hover .inside-text6 {
    display:flex;
  justify-content:center;/* it will center content which might overflow on both sides too */
}

Demo of you code updated to run below :

function incrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number1').value = value;
}

function decrementValue1() {
  let value = parseInt(document.getElementById('number1').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number1').value = value;
}

function incrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number2').value = value;
}

function decrementValue2() {
  let value = parseInt(document.getElementById('number2').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number2').value = value;
}

function incrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number3').value = value;
}

function decrementValue3() {
  let value = parseInt(document.getElementById('number3').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number3').value = value;
}

function incrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number4').value = value;
}

function decrementValue4() {
  let value = parseInt(document.getElementById('number4').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number4').value = value;
}

function incrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number5').value = value;
}

function decrementValue5() {
  let value = parseInt(document.getElementById('number5').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number5').value = value;
}

function incrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  value++;
  document.getElementById('number6').value = value;
}

function decrementValue6() {
  let value = parseInt(document.getElementById('number6').value, 10);
  value = isNaN(value) ? 0 : value;
  if (value > 0) {
    value--;
  }
  document.getElementById('number6').value = value;
}

var colors = ["red", "blue", "green", "yellow", "purple", "gold", "pink", "grey", "turquoise", "aqua"];
var i = 0;
var selectedColor;

function changeColour() {
  selectedColor = colors[i];
  document.getElementById("number" + 1).style.backgroundColor = selectedColor;
  i++;
  if (i > colors.length)
    i = 0;
}

function printDate() {
  let value = document.getElementById("date").value;
  document.getElementById("check").innerHTML = "Date: " + value;
}

.container {
  text-align: center;
  position: relative;
  top: 40%;
}

.inside-text1 {
  display: none;
  position: absolute;
  top: 20px;
  left: 248px;
  text-align: center;
  bottom: -65px;
}

.inside-text {
  display: none;
  position: relative;
  text-align: center;
  bottom: -25px;
}

.inside-text6 {
  display: none;
  position: relative;
  text-align: center;
  bottom: -120px
}

#p6 {
  border-bottom: 200px solid blue;
  border-left: 100px solid transparent;
  border-right: 100px solid transparent;
  height: 0;
  width: 0;
  margin-right: auto;
  margin-left: auto;
}

#p5-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 10px;
  margin-right: auto;
  margin-left: auto;
}

#p5 {
  border-bottom: 80px solid black;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 220px;
  margin-right: auto;
  margin-left: auto;
}

#p4-5 {
  border-bottom: 20px solid white;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 240px;
  margin-right: auto;
  margin-left: auto;
}

#p4 {
  border-bottom: 80px solid purple;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 330px;
  margin-right: auto;
  margin-left: auto;
}

#p3 {
  border-bottom: 80px solid green;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 420px;
  margin-right: auto;
  margin-left: auto;
}

#p2 {
  border-bottom: 80px solid yellow;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 510px;
  margin-right: auto;
  margin-left: auto;
}

#p1 {
  position: relative;
  top: 40%;
  border-bottom: 80px solid red;
  border-left: 45px solid transparent;
  border-right: 45px solid transparent;
  height: 0;
  width: 600px;
  margin-right: auto;
  margin-left: auto;
}

#p1:hover .inside-text1 {
  display: block;
}

#p2:hover .inside-text {
  display: block;
}

#p3:hover .inside-text {
  display: block;
}

#p4:hover .inside-text {
  display: block;
}

#p5:hover .inside-text {
  display: block;
}

#p6:hover .inside-text6 {
    display:flex;
  justify-content:center;
}

.button {
  margin-right: auto;
  margin-left: auto;
  position: relative;
}

#b1 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number1 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  background-color: grey;
  text-align: center;
}

#b2 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b3 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number2 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b4 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b5 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number3 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b6 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b7 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number4 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b8 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b9 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number5 {
  display: inline-block;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b10 {
  display: inline-block;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b11 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#number6 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 25px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#b12 {
  /*display: inline-flex;*/
  float: left;
  height: 25px;
  width: 30px;
  border-radius: 50%;
  border: solid red;
  text-align: center;
}

#check {
  display: block;
  position: center;
  height: 25px;
  width: 125px;
  /*border-radius: 50%;*/
  border: solid red;
  text-align: center;
}

<div class="container">
  <div id="p6">
    <div class="inside-text6">
      <input type="button" onclick="decrementValue6()" value="-" id="b11" />
      <label for="number6"></label><input type="text" id="number6" value="0" />
      <input type="button" onclick="incrementValue6()" value="+" id="b12" />
    </div>
  </div>

  <div id="p5-5"></div>

  <div id="p5">
    <div class="inside-text">
      <form>
        <input type="button" onclick="decrementValue5()" value="-" id="b9" />
        <label for="number5"></label><input type="text" id="number5" value="1" />
        <input type="button" onclick="incrementValue5()" value="+" id="b10" />
      </form>
    </div>
  </div>

  <div id="p4-5"></div>

  <div id="p4">
    <div class="inside-text">
      <form>
        <input type="button" onclick="decrementValue4()" value="-" id="b7" />
        <label for="number4"></label><input type="text" id="number4" value="2" />
        <input type="button" onclick="incrementValue4();" value="+" id="b8" />
      </form>
    </div>
  </div>

  <div id="p3">
    <div class="inside-text">
      <form>
        <input type="button" onclick="decrementValue3()" value="-" id="b5" />
        <label for="number3"></label><input type="text" id="number3" value="3" />
        <input type="button" onclick="incrementValue3()" value="+" id="b6" />
      </form>
    </div>
  </div>

  <div id="p2">
    <div class="inside-text">
      <form>
        <input type="button" onclick="decrementValue2()" value="-" id="b3" />
        <label for="number2"></label><input type="text" id="number2" value="4" />
        <input type="button" onclick="incrementValue2()" value="+" id="b4" />
      </form>
    </div>
  </div>
  <div id="p1">
    <div class="inside-text1">
      <form>
        <input type="button" onclick="decrementValue1('number6');changeColour()" value="-" id="b2" />
        <input type="text" id="number1" value="6" />
        <input type="button" onclick="incrementValue1();changeColour()" value="+" id="b1" />
      </form>
    </div>
  </div>
</div>

<label for="date">Enter Date of Submission:</label>
<input type="date" id="date" value="0" />
<input type="button" onclick="printDate()" value="Record" />

<div id="check"></div>


来源: stackexchange

问:
Why do i still get warnings when using @SuppressWarnings("unchecked")?
```<code>class Lenkeliste<T> implements Liste<T>{
  @SuppressWarnings({"unchecked"})
  private int iBruk = 0;
  private T[] liste = (T[]) new Object[10];

  public int stoerrelse(){
    return iBruk;
  }
  public void leggTil(int pos, T x) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    if (iBruk == liste.lenght) {
      @SuppressWarnings({"unchecked"})
      T[] ny = (T[]) new Object[2*iBruk];
      for (int i = pos; i < iBruk; i++) {
        ny[i] = liste[i];
        liste = ny;
        liste[i+1] = liste[i];
      }
      liste[pos] = x;
      iBruk++;
    }
  }
  public void leggTil(T x) {
    if (iBruk == liste.lenght) {
      @SuppressWarnings({"unchecked"})
      T[] ny = (T[]) new Object[2*iBruk];
      for (int i = 0; i < iBruk; i++) {
        ny[i] = liste[i];
        liste = ny;
      }
      liste[iBruk] = x;
      iBruk++;
    }
  }
  public void sett(int pos, T x) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    liste[pos] = x;
  }
  public T hent(int pos) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    return liste[pos];
  }
  public T fjern(int pos) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    T bort = liste[pos];
    for (int i = pos+1; i < iBruk; i++) {
      liste[i-1] = liste[i];
    }
    iBruk--;
    return bort;
  }
  public T fjern() {
    T ut = liste[0];
    for (int i = 1; i < iBruk; i++) {
      liste[i-1] = liste[i];
    }
    iBruk--;
    return ut;
  }
}
</code>```

This is the code i have. The teacher used similar code and got it to work, but I still get warnings.
Here are the errors i get:

```<code>Lenkeliste.java:15: error: cannot find symbol
    if (iBruk == liste.lenght) {
                      ^
  symbol:   variable lenght
  location: variable liste of type T[]
  where T is a type-variable:
    T extends Object declared in class Lenkeliste
Lenkeliste.java:28: error: cannot find symbol
    if (iBruk == liste.lenght) {
                      ^
  symbol:   variable lenght
  location: variable liste of type T[]
  where T is a type-variable:
    T extends Object declared in class Lenkeliste
Note: Lenkeliste.java uses unchecked or unsafe operations.
Note: Recompile with -Xlint:unchecked for details.
</code>```

答:
```<code>@SuppressWarnings({"unchecked"})
private int iBruk = 0;
private T[] liste = (T[]) new Object[10];
</code>```

The SuppressWarnings applies to the declaration of the int, not the T[].

Put the suppression on the second declaration.

```<code>private int iBruk = 0;
@SuppressWarnings({"unchecked"})
private T[] liste = (T[]) new Object[10];
</code>```

Also, note that the liste = ny; lines in the leggTil methods shouldn't be inside the loop. If they are, you will only copy the first element of the array to the new array before you overwrite the liste, so the subsequent iterations will just set array elements to their current value (i.e. null).

```<code>  for (int i = 0; i < iBruk; i++) {
    ny[i] = liste[i];
  }
  liste = ny;
</code>```

ContentLicense: CC BY-SA 4.0

Body:
class Lenkeliste<T> implements Liste<T>{
  @SuppressWarnings({"unchecked"})
  private int iBruk = 0;
  private T[] liste = (T[]) new Object[10];

  public int stoerrelse(){
    return iBruk;
  }
  public void leggTil(int pos, T x) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    if (iBruk == liste.lenght) {
      @SuppressWarnings({"unchecked"})
      T[] ny = (T[]) new Object[2*iBruk];
      for (int i = pos; i < iBruk; i++) {
        ny[i] = liste[i];
        liste = ny;
        liste[i+1] = liste[i];
      }
      liste[pos] = x;
      iBruk++;
    }
  }
  public void leggTil(T x) {
    if (iBruk == liste.lenght) {
      @SuppressWarnings({"unchecked"})
      T[] ny = (T[]) new Object[2*iBruk];
      for (int i = 0; i < iBruk; i++) {
        ny[i] = liste[i];
        liste = ny;
      }
      liste[iBruk] = x;
      iBruk++;
    }
  }
  public void sett(int pos, T x) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    liste[pos] = x;
  }
  public T hent(int pos) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    return liste[pos];
  }
  public T fjern(int pos) {
    if (pos < 0 || pos >= iBruk) {
      throw new UgyldigListeIndeks(pos);
    }
    T bort = liste[pos];
    for (int i = pos+1; i < iBruk; i++) {
      liste[i-1] = liste[i];
    }
    iBruk--;
    return bort;
  }
  public T fjern() {
    T ut = liste[0];
    for (int i = 1; i < iBruk; i++) {
      liste[i-1] = liste[i];
    }
    iBruk--;
    return ut;
  }
}

This is the code i have. The teacher used similar code and got it to work, but I still get warnings.
Here are the errors i get:

Lenkeliste.java:15: error: cannot find symbol
    if (iBruk == liste.lenght) {
                      ^
  symbol:   variable lenght
  location: variable liste of type T[]
  where T is a type-variable:
    T extends Object declared in class Lenkeliste
Lenkeliste.java:28: error: cannot find symbol
    if (iBruk == liste.lenght) {
                      ^
  symbol:   variable lenght
  location: variable liste of type T[]
  where T is a type-variable:
    T extends Object declared in class Lenkeliste
Note: Lenkeliste.java uses unchecked or unsafe operations.
Note: Recompile with -Xlint:unchecked for details.

Body:
@SuppressWarnings({"unchecked"})
private int iBruk = 0;
private T[] liste = (T[]) new Object[10];

The SuppressWarnings applies to the declaration of the int, not the T[].

Put the suppression on the second declaration.

private int iBruk = 0;
@SuppressWarnings({"unchecked"})
private T[] liste = (T[]) new Object[10];

Also, note that the liste = ny; lines in the leggTil methods shouldn't be inside the loop. If they are, you will only copy the first element of the array to the new array before you overwrite the liste, so the subsequent iterations will just set array elements to their current value (i.e. null).

  for (int i = 0; i < iBruk; i++) {
    ny[i] = liste[i];
  }
  liste = ny;


问:
for loop repeats itself in python
I have created a web bot that iterates over a website e.g example.com/?id=int where int is some integer. the function gets the result in raw html using requests library then hands it to parseAndWrite to extract a div and save its value in a sqlite db:

```<code>def archive(initial_index, final_index):
    while True:
        try:
            for i in range(initial_index, final_index):
                res = requests.get('https://www.example.com/?id='+str(i))
                parseAndWrite(res.text)
                print(i, ' archived')

        except requests.exceptions.ConnectionError:
            print("[-] Connection lost. ")
            continue
        except:
            exit(1)
        break

archive(1, 10000)
</code>```

My problem is that, after some time, the loop doesn't continue to 10000 but repeats itself from a random value, resulting in many duplicate records in the database. What is causing this inconsistency ?

答:
A general rule for a try statement is to execute as little code as possible inside one; only put the code you expect will produce the error you want to catch in it; all other code goes before or after the statement.

Don't catch errors you don't know what to do with. Exiting the program is rarely the right thing to do; that will happen anyway if no one else catches the exception, so given your caller the chance to handle it.

And finally, don't build URLs yourself; let the requests library do that for you. The base URL is http://www.example.com; the id parameter and its value can be passed via a dict to requests.get.

Your outer loop will iterate over the various parameters used to construct the URL; the inner loop will try the request until it succeeds. Once the inner loop terminates, then you can use the response to call parseAndWrite.

```<code>def archive(initial_index, final_index):

    base_url = 'https://www.example.com/'
    for i in range(initial_index, final_index + 1):
        while True:
            try:
                res = requests.get(base_url, params={'id': i})
            except requests.exception.ConnectionError:
                print("[-] Connection lost, trying again")
                continue
            else:
                break
        parseAndWrite(res.text)
        print('{} archived'.format(i))

archived(1, 10000)
</code>```

You might also consider letting requests handle the retries for you. See Can I set max_retries for requests.request? for a start.

Title: for loop repeats itself in python

Body:
I have created a web bot that iterates over a website e.g example.com/?id=int where int is some integer. the function gets the result in raw html using requests library then hands it to parseAndWrite to extract a div and save its value in a sqlite db:

def archive(initial_index, final_index):
    while True:
        try:
            for i in range(initial_index, final_index):
                res = requests.get('https://www.example.com/?id='+str(i))
                parseAndWrite(res.text)
                print(i, ' archived')

        except requests.exceptions.ConnectionError:
            print("[-] Connection lost. ")
            continue
        except:
            exit(1)
        break

archive(1, 10000)

My problem is that, after some time, the loop doesn't continue to 10000 but repeats itself from a random value, resulting in many duplicate records in the database. What is causing this inconsistency ?

Body:
A general rule for a try statement is to execute as little code as possible inside one; only put the code you expect will produce the error you want to catch in it; all other code goes before or after the statement.

Don't catch errors you don't know what to do with. Exiting the program is rarely the right thing to do; that will happen anyway if no one else catches the exception, so given your caller the chance to handle it.

And finally, don't build URLs yourself; let the requests library do that for you. The base URL is http://www.example.com; the id parameter and its value can be passed via a dict to requests.get.

Your outer loop will iterate over the various parameters used to construct the URL; the inner loop will try the request until it succeeds. Once the inner loop terminates, then you can use the response to call parseAndWrite.

def archive(initial_index, final_index):

    base_url = 'https://www.example.com/'
    for i in range(initial_index, final_index + 1):
        while True:
            try:
                res = requests.get(base_url, params={'id': i})
            except requests.exception.ConnectionError:
                print("[-] Connection lost, trying again")
                continue
            else:
                break
        parseAndWrite(res.text)
        print('{} archived'.format(i))

archived(1, 10000)

You might also consider letting requests handle the retries for you. See Can I set max_retries for requests.request? for a start.


问:
Ansible - Change user password on Linux
I'm doing some playbook to change username password on linux. I want to use the same playbook for all users.

What i am doing is:

```<code>    - name: change users password
  hosts: localhost
  vars_files: ['credentials.yml']
  tasks:
    - user:
        name: "{{ user_name }}"
        password: "{{ dynamic_password | password_hash('sha512') }}"
</code>```

And my file.yml:

```<code>credentials.yml
dynamic_password: "$6$mysecretsalt$QF9IdmmJLZWuEO8PKQ0w7c81Rre0hv.udU83ypIO3cG5DbAo90IXwHX6wcuhDJaLAkdE5KSSl9lKvdMFh810b."
generic_password: "$6$IxMDgSamMRSMAEY1$rfGAWC8xBgGMMGOFJXAMxnUuiKVKrH3SDOuNIrJpx4rMZy/FG5spqp1f9oSAcDBpTJ2vOK2rAboWHZ6Zn5qZm."
</code>```

What i am executing:

```<code>ansible-playbook prueba81.yml --extra-vars "user_name=pepito type_password=dynamic_password"
</code>```

What i want to do, is indicate in the command line, the user and what password (inside of the file yml) should it use. But seems that the variable type_password is not recognized.

Can you help me?.

Thanks!!!!

答:
Your extra-vars on the command line isn't setting type_password to the value of the variable dynamic_password.  You're literally setting the variable type_password to be the string "dynamic_password".

If you want to tell ansible what variable to use from the command line, you can do it several ways.  Here's one example:

ansible-playbook prueba81.yml --extra-vars "user_name=pepito type_password=dynamic"

```<code>tasks:
  - user:
      name: "{{ user_name }}"
      password: "{{ dynamic_password | password_hash('sha512') }}"
    when type_password == "dynamic"
</code>```

Title: Ansible - Change user password on Linux

Body:
I'm doing some playbook to change username password on linux. I want to use the same playbook for all users.

What i am doing is:

    - name: change users password
  hosts: localhost
  vars_files: ['credentials.yml']
  tasks:
    - user:
        name: "{{ user_name }}"
        password: "{{ dynamic_password | password_hash('sha512') }}"

And my file.yml:

credentials.yml
dynamic_password: "$6$mysecretsalt$QF9IdmmJLZWuEO8PKQ0w7c81Rre0hv.udU83ypIO3cG5DbAo90IXwHX6wcuhDJaLAkdE5KSSl9lKvdMFh810b."
generic_password: "$6$IxMDgSamMRSMAEY1$rfGAWC8xBgGMMGOFJXAMxnUuiKVKrH3SDOuNIrJpx4rMZy/FG5spqp1f9oSAcDBpTJ2vOK2rAboWHZ6Zn5qZm."

What i am executing:

ansible-playbook prueba81.yml --extra-vars "user_name=pepito type_password=dynamic_password"

What i want to do, is indicate in the command line, the user and what password (inside of the file yml) should it use. But seems that the variable type_password is not recognized.

Can you help me?.

Thanks!!!!

Body:
Your extra-vars on the command line isn't setting type_password to the value of the variable dynamic_password.  You're literally setting the variable type_password to be the string "dynamic_password".

If you want to tell ansible what variable to use from the command line, you can do it several ways.  Here's one example:

ansible-playbook prueba81.yml --extra-vars "user_name=pepito type_password=dynamic"

tasks:
  - user:
      name: "{{ user_name }}"
      password: "{{ dynamic_password | password_hash('sha512') }}"
    when type_password == "dynamic"


问:
Get the last string printed in C/C++
I am trying to create a tester using googletest. the problem is that the function that I am testing is returning void and printing a result instead. I want to get the last string printed into the console so I can test the output. the string may include \n.

so I have the function itself:

void f_sequence(char sequenceStr[])
{
   //logic...
    if(condotion1)
        printf("somthing1");
    else if(condotion2)
        printf("somthing2")
(...)
}
```

<p>and then the tester:</p>

<pre class="lang-cpp prettyprint-override"><code>TEST(TesterGroup, TesterName)
{
    f_sequence("input");
    EXPECT_EQ("somthing1", /*how do i get the output?*/);
}
</code>```

Is it possible?

The functions I test are in c, while the Test function itself (the tester) is in c++. the output is printed using printf. I cannot change the function itself. I am using CLion latest version.

答:
One solution: You can write a separate program that executes the function, and in the unit test, you can execute that program as a sub process and inspect the output. This can be done with std::system, but be very careful to not pass any non-constant input to it. You don't want shell injection vulnerability even in a unit test. System specific functions exist that avoid the use of shell in the subprocess.

Another solution, which is possible at least on POSIX: Replace the the standard out / err streams with file descriptors, and read the files afterwards.

Googletest specific: There seems to be testing::internal::CaptureStdout, which appears to implement the idea of replacing standard streams. But as the namespace implies, this is not official API, so may change in future.

Title: Get the last string printed in C/C++

Body:
I am trying to create a tester using googletest. the problem is that the function that I am testing is returning void and printing a result instead. I want to get the last string printed into the console so I can test the output. the string may include \n.

so I have the function itself:

void f_sequence(char sequenceStr[])
{
   //logic...
    if(condotion1)
        printf("somthing1");
    else if(condotion2)
        printf("somthing2")
(...)
}

and then the tester:

TEST(TesterGroup, TesterName)
{
    f_sequence("input");
    EXPECT_EQ("somthing1", /*how do i get the output?*/);
}

Is it possible?

The functions I test are in c, while the Test function itself (the tester) is in c++. the output is printed using printf. I cannot change the function itself. I am using CLion latest version.


问:
Typescript (3.8+), what are the downsides of #private fields?
TypeScript 3.8 supports the #private fields. I'm used to the TypeScript's private fields to prevent access to these fields.

I know that these fields are not really private on the generated JavaScript, and the new #private is private in the generated code.

Putting the "real private" vs "fake private" aside, Is there a reason for me not to convert all my private to #private?
What are the downsides of this move? is it slower?
Is the generated code supported by all browsers?

Thanks!

答:
Is there a reason for me not to convert all my private to #private?

If you have to support non ES6 browsers.

What are the downsides of this move? Is the generated code supported by all browsers?

Major downside / browser support: It is only supported by ES6 browsers

is it slower?

It is. But be careful of premature performance optimization.

Advantage : Hard privacy

The unasked question is why would you do it. The old keyword private was only a compile time thing. The new # private is truly private:

```<code>class C {
    #foo = 10;
}

const c = new C();
console.log(new C()["#foo"]); // prints undefined as its private
</code>```

Body:
Is there a reason for me not to convert all my private to #private?

If you have to support non ES6 browsers.

What are the downsides of this move? Is the generated code supported by all browsers?

Major downside / browser support: It is only supported by ES6 browsers

is it slower?

It is. But be careful of premature performance optimization.

Advantage : Hard privacy

The unasked question is why would you do it. The old keyword private was only a compile time thing. The new # private is truly private:

class C {
    #foo = 10;
}

const c = new C();
console.log(new C()["#foo"]); // prints undefined as its private


问:
System.ArgumentOutOfRangeException: 'Specified argument was out of the range of valid values. Parameter name: index' in asp.net
Default.aspx

```<code>        <Columns>
            <asp:TemplateField HeaderText="Type">
                <ItemTemplate>
                    <asp:DropDownList ID="typeHobby" runat="server">
                        <asp:ListItem style="display:none">--Select--</asp:ListItem>
                        <asp:ListItem Value="Sports">Sports</asp:ListItem>
                        <asp:ListItem Value="FineArt">Fine Arts</asp:ListItem>
                        <asp:ListItem Value="Other">Other</asp:ListItem>
                    </asp:DropDownList>
                </ItemTemplate>
            </asp:TemplateField>

            <asp:TemplateField HeaderText="Name">
                <ItemTemplate>
                     <asp:TextBox  ID="nameSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server" ></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Details of participation">
                <ItemTemplate>
                     <asp:TextBox ID="detailSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server"></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Distinction achieved">
                <ItemTemplate>
                     <asp:TextBox ID="distSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server"></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Whether still intrested">
                <ItemTemplate>
                    <asp:DropDownList ID="intrestSport" runat="server">
                        <asp:ListItem style="display:none">--Select--</asp:ListItem>
                        <asp:ListItem Value="yes">Yes</asp:ListItem>
                        <asp:ListItem Value="no">No</asp:ListItem>
                    </asp:DropDownList>
                </ItemTemplate>
                <FooterStyle HorizontalAlign="Right" />
                    <FooterTemplate>
                        <asp:Button ID="addHobby" runat="server" Text="Add" OnClick="ButtonAdd_Click_Hobby" CausesValidation="false" />
                    </FooterTemplate>
            </asp:TemplateField>
        </Columns>

    </asp:GridView>
</code>```

Default.aspx.cs

```<code>protected void ButtonAdd_Click_Hobby(object sender, EventArgs e)
        {
            addHobby();
        }

        protected void addHobby()
        {
         //   MessageBox.Show("add hobby");
            try
            {
                int rowIndex = 0;
                if (ViewState["HoobyTable"] != null)
                {
                    MessageBox.Show("if true");
                    DataTable dtHobbyTable = (DataTable)ViewState["HoobyTable"];
                    DataRow drHobbyRow = null;
                    if (dtHobbyTable.Rows.Count > 0)
                    {
                        MessageBox.Show(dtHobbyTable.Rows.Count.ToString());
                        for (int i = 1; i <= dtHobbyTable.Rows.Count; i++)
                        {
                            //extract the TextBox values
                            MessageBox.Show("loop");
                            DropDownList txh1 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[1].FindControl("typeHobby");
                            TextBox txh2 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[2].FindControl("nameSport");
                            TextBox txh3 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[3].FindControl("detailSport");
                            TextBox txh4 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[4].FindControl("distSport");
                            DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");
                            MessageBox.Show("Hello" + txh1.Text);
                            drHobbyRow = dtHobbyTable.NewRow();
                            drHobbyRow["Slno"] = i + 1;

                            dtHobbyTable.Rows[i - 1]["hoType"] = txh1.Text;
                            dtHobbyTable.Rows[i - 1]["Name"] = txh2.Text;
                            dtHobbyTable.Rows[i - 1]["Detail"] = txh3.Text;
                            dtHobbyTable.Rows[i - 1]["Distinction"] = txh4.Text;
                            dtHobbyTable.Rows[i - 1]["Interest"] ="interest";

                            rowIndex++;
                        }
                        dtHobbyTable.Rows.Add(drHobbyRow);
                        ViewState["HoobyTable"] = dtHobbyTable;

                        hobbyGrid.DataSource = dtHobbyTable;
                        hobbyGrid.DataBind();
                    }
                }
                else
                {
                    Response.Write("ViewState is null");
                }
            }
            catch (Exception e)
            {
                // MessageBox.Show(e.ToString());
            }
            //Set Previous Data on Postbacks
          SetPreviousDataHobby();

        }
        private void SetPreviousDataHobby()
        {
            int rowIndex = 0;
            if (ViewState["HoobyTable"] != null)
            {
                DataTable dt = (DataTable)ViewState["HoobyTable"];
                if (dt.Rows.Count > 0)
                {
                    for (int i = 0; i < dt.Rows.Count; i++)
                    {

                        DropDownList txh1 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[1].FindControl("typeHobby");
                        TextBox txh2 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[2].FindControl("nameSport");
                        TextBox txh3 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[3].FindControl("detailSport");
                        TextBox txh4 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[4].FindControl("distSport");
                        DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");
                        MessageBox.Show("type hobby" + dt.Rows[i]["hoType"].ToString());
                        txh1.Text = dt.Rows[i]["hoType"].ToString();
                        txh2.Text = dt.Rows[i]["Name"].ToString();
                        txh3.Text = dt.Rows[i]["Detail"].ToString();
                        txh4.Text = dt.Rows[i]["Distinction"].ToString();
                        txh5.Text = dt.Rows[i]["Interest"].ToString();

                        rowIndex++;
                    }
                }
            }
        }
</code>```

System.ArgumentOutOfRangeException: 'Specified argument was out of the range of valid values.
Parameter name: index'
-> got an error like above in line:
DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");

(line from SetPreviousDataHobby() function)

答:
I believe this should point you in the right direction

Rows and Columns of DataGrid starts at index 0

hobbyGrid.Rows[rowIndex].Cells[5] indicates that there are 6 columns, do you think that's true ?

The error message simply indicates that you are accessing an index that is outside the limits of the data structure.

You can validate how many columns are available at row[0] by hobbyGrid.Rows[0].Cells.Count-1; Cells[5] should not exceed this

OR

You can also check number of colums from table like  int cols= dtHobbyTable.Columns.Count

Body:
Default.aspx

        <Columns>
            <asp:TemplateField HeaderText="Type">
                <ItemTemplate>
                    <asp:DropDownList ID="typeHobby" runat="server">
                        <asp:ListItem style="display:none">--Select--</asp:ListItem>
                        <asp:ListItem Value="Sports">Sports</asp:ListItem>
                        <asp:ListItem Value="FineArt">Fine Arts</asp:ListItem>
                        <asp:ListItem Value="Other">Other</asp:ListItem>
                    </asp:DropDownList>
                </ItemTemplate>
            </asp:TemplateField>

            <asp:TemplateField HeaderText="Name">
                <ItemTemplate>
                     <asp:TextBox  ID="nameSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server" ></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Details of participation">
                <ItemTemplate>
                     <asp:TextBox ID="detailSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server"></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Distinction achieved">
                <ItemTemplate>
                     <asp:TextBox ID="distSport" style="margin:2px" CssClass="cap" pattern="[A-Za-z]{2,15}" runat="server"></asp:TextBox>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Whether still intrested">
                <ItemTemplate>
                    <asp:DropDownList ID="intrestSport" runat="server">
                        <asp:ListItem style="display:none">--Select--</asp:ListItem>
                        <asp:ListItem Value="yes">Yes</asp:ListItem>
                        <asp:ListItem Value="no">No</asp:ListItem>
                    </asp:DropDownList>
                </ItemTemplate>
                <FooterStyle HorizontalAlign="Right" />
                    <FooterTemplate>
                        <asp:Button ID="addHobby" runat="server" Text="Add" OnClick="ButtonAdd_Click_Hobby" CausesValidation="false" />
                    </FooterTemplate>
            </asp:TemplateField>
        </Columns>

    </asp:GridView>

Default.aspx.cs

protected void ButtonAdd_Click_Hobby(object sender, EventArgs e)
        {
            addHobby();
        }

        protected void addHobby()
        {
         //   MessageBox.Show("add hobby");
            try
            {
                int rowIndex = 0;
                if (ViewState["HoobyTable"] != null)
                {
                    MessageBox.Show("if true");
                    DataTable dtHobbyTable = (DataTable)ViewState["HoobyTable"];
                    DataRow drHobbyRow = null;
                    if (dtHobbyTable.Rows.Count > 0)
                    {
                        MessageBox.Show(dtHobbyTable.Rows.Count.ToString());
                        for (int i = 1; i <= dtHobbyTable.Rows.Count; i++)
                        {
                            //extract the TextBox values
                            MessageBox.Show("loop");
                            DropDownList txh1 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[1].FindControl("typeHobby");
                            TextBox txh2 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[2].FindControl("nameSport");
                            TextBox txh3 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[3].FindControl("detailSport");
                            TextBox txh4 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[4].FindControl("distSport");
                            DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");
                            MessageBox.Show("Hello" + txh1.Text);
                            drHobbyRow = dtHobbyTable.NewRow();
                            drHobbyRow["Slno"] = i + 1;

                            dtHobbyTable.Rows[i - 1]["hoType"] = txh1.Text;
                            dtHobbyTable.Rows[i - 1]["Name"] = txh2.Text;
                            dtHobbyTable.Rows[i - 1]["Detail"] = txh3.Text;
                            dtHobbyTable.Rows[i - 1]["Distinction"] = txh4.Text;
                            dtHobbyTable.Rows[i - 1]["Interest"] ="interest";

                            rowIndex++;
                        }
                        dtHobbyTable.Rows.Add(drHobbyRow);
                        ViewState["HoobyTable"] = dtHobbyTable;

                        hobbyGrid.DataSource = dtHobbyTable;
                        hobbyGrid.DataBind();
                    }
                }
                else
                {
                    Response.Write("ViewState is null");
                }
            }
            catch (Exception e)
            {
                // MessageBox.Show(e.ToString());
            }
            //Set Previous Data on Postbacks
          SetPreviousDataHobby();

        }
        private void SetPreviousDataHobby()
        {
            int rowIndex = 0;
            if (ViewState["HoobyTable"] != null)
            {
                DataTable dt = (DataTable)ViewState["HoobyTable"];
                if (dt.Rows.Count > 0)
                {
                    for (int i = 0; i < dt.Rows.Count; i++)
                    {

                        DropDownList txh1 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[1].FindControl("typeHobby");
                        TextBox txh2 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[2].FindControl("nameSport");
                        TextBox txh3 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[3].FindControl("detailSport");
                        TextBox txh4 = (TextBox)hobbyGrid.Rows[rowIndex].Cells[4].FindControl("distSport");
                        DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");
                        MessageBox.Show("type hobby" + dt.Rows[i]["hoType"].ToString());
                        txh1.Text = dt.Rows[i]["hoType"].ToString();
                        txh2.Text = dt.Rows[i]["Name"].ToString();
                        txh3.Text = dt.Rows[i]["Detail"].ToString();
                        txh4.Text = dt.Rows[i]["Distinction"].ToString();
                        txh5.Text = dt.Rows[i]["Interest"].ToString();

                        rowIndex++;
                    }
                }
            }
        }

System.ArgumentOutOfRangeException: 'Specified argument was out of the range of valid values.
Parameter name: index'
-> got an error like above in line:
DropDownList txh5 = (DropDownList)hobbyGrid.Rows[rowIndex].Cells[5].FindControl("intrestSport");

(line from SetPreviousDataHobby() function)


问:
Create a numpy matrix from content in dictionary labelled by i,j
Suppose I have a dictionary:

```<code>d = {(0,0): 1, (0,1): 2, (1,0): 3, (1,1): 4}
</code>```

I want to make this into the array (i.e. the keys correspond to array indices)

```<code>array([[1, 2],
       [3, 4]])
</code>```

Is there a better way to do this than for loops?
(I tried np.fromfunction but it did not work.)

答:
It seems you have a dictionary of keys situation, which can be handled by scipy's dok_matrix:

```<code>from scipy.sparse import dok_matrix

d = {(0,0): 1, (0,1): 2, (1,0): 3, (1,1): 4}

mat = dok_matrix((2,2))
mat._update(d)
mat = mat.todense()
</code>```

Which gives you:

```<code>>>> mat
matrix([[1., 2.],
        [3., 4.]])
</code>```

Body:
Suppose I have a dictionary:

d = {(0,0): 1, (0,1): 2, (1,0): 3, (1,1): 4}

I want to make this into the array (i.e. the keys correspond to array indices)

array([[1, 2],
       [3, 4]])

Is there a better way to do this than for loops?
(I tried np.fromfunction but it did not work.)

Body:
It seems you have a dictionary of keys situation, which can be handled by scipy's dok_matrix:

from scipy.sparse import dok_matrix

d = {(0,0): 1, (0,1): 2, (1,0): 3, (1,1): 4}

mat = dok_matrix((2,2))
mat._update(d)
mat = mat.todense()

Which gives you:

>>> mat
matrix([[1., 2.],
        [3., 4.]])


问:
Search through multiple files/dirs for string, then print content of text file
I'm trying to make a small script that will allow me to search through text files located in a specific directory and folders nested inside that one. I've managed to get it to list all files in that path, but can't seem to get it to search for a specific string in those files and then print the full text file.

Code:

```<code>import os
from os import listdir
from os.path import isfile, join

path = "<PATH>"

for root, dirs, files in os.walk(path):
    for file in files:
        if file.endswith('.txt'):
            dfiles = str(file)

sTerm = input("Search: ")

for files in os.walk(path):
    for file in files:
        with open(dfiles) as f:
            if sTerm in f.read():
                print(f.read())
</code>```

First part was from a test I did to list all the files, once that worked I tried using the second part to search through all of them for a matching string and then print the full file if it finds one. There's probably an easier way for me to do this.

答:
Here is a solution with Python 3.4+ because of pathlib:

from pathlib import Path

path = Path('/some/dir')

search_string = 'string'

for o in path.rglob('*.txt'):
    if o.is_file():
        text = o.read_text()
        if search_string in text:
            print(o)
            print(text)
```

The code above will look for all *.txt in path and its sub-directories, read the content of each file in text, search for search_string in text and, if it matches, print the file name and its contents.

Body:
I'm trying to make a small script that will allow me to search through text files located in a specific directory and folders nested inside that one. I've managed to get it to list all files in that path, but can't seem to get it to search for a specific string in those files and then print the full text file.

Code:

import os
from os import listdir
from os.path import isfile, join

path = "<PATH>"

for root, dirs, files in os.walk(path):
    for file in files:
        if file.endswith('.txt'):
            dfiles = str(file)

sTerm = input("Search: ")

for files in os.walk(path):
    for file in files:
        with open(dfiles) as f:
            if sTerm in f.read():
                print(f.read())

First part was from a test I did to list all the files, once that worked I tried using the second part to search through all of them for a matching string and then print the full file if it finds one. There's probably an easier way for me to do this.

Body:
Here is a solution with Python 3.4+ because of pathlib:

from pathlib import Path

path = Path('/some/dir')

search_string = 'string'

for o in path.rglob('*.txt'):
    if o.is_file():
        text = o.read_text()
        if search_string in text:
            print(o)
            print(text)

The code above will look for all *.txt in path and its sub-directories, read the content of each file in text, search for search_string in text and, if it matches, print the file name and its contents.


问:
Different scenarios for git merge conflicts
I am trying to understand which are the situations when a git conflict can happen after a git merge and how they could be avoided.

I've created a git repository and added a text file to it.

I've added "1" to the text file and committed it to master.

I've created a new branch from master(branch2) and appended a new line to the text file with the content "2".

I've created a new branch from master(branch3) and appended a new line to the text file with the content "3".

After this, I've done the following :

I've merged branch2 into master. No conflicts which is right and I've expected.

I've merged master into branch3. I had conflicts because the second line of the text file has different content. I've fixed the conflicts by keeping "3" instead of "2".

I want to merge branch3 into master. Now my questions are : 1. Are there any possibilities to have conflicts when I do that merge? If yes, why? If no, why? 2. If there shouldn't be conflicts, but I still have conflicts, what could be the reasons?

答:
Merge conflicts happen during merges, not after them.

The conflict part is really very simple: A conflict occurs in file F when:

"our" changes—the difference from the merge base commit to our HEAD commit—has a change to file F, and

"their" changes—the difference from the same merge base commit to their tip commit—also have a change to file F as well, and

our changes and their changes overlap (edit: or abut—see comments), but are not identical.

To understand this, you need to:

understand the output of git diff; and

understand what a merge base is.

The output of git diff is pretty straightforward, really, but it requires remembering that each commit holds a snapshot of all of your files.  This means we must give git diff two snapshots: an old one, and a new one.  That's two "pictures" of what the file were like at two points in time.  Git then plays a game of Spot the Difference: it tells you that to go from the left-side snapshot to the right-side snapshot, you must make some set of changes to some set of files.  These changes may involve renaming some files; they might involve adding new files; they might involve deleting files; and they might involve deleting some particular lines from some files, and adding some lines to some files, in some particular places.

The output of git diff is not necessarily anything any person did.  It's just a set of changes that, if applied to the left-side snapshot, get you the right-side snapshot.  The "left side" here is the left argument to git diff and the "right side" here is the right argument, when you use:

```<code>git diff <hash1> <hash2>
</code>```

where the two hashes are the hash IDs of commits.  (This is what git merge does, in effect, although it does all of this internally.)  The diff engine is designed to produce the smallest set of changes that give the right effect.  This, as it turns out, is usually what someone actually did do ... but not always; it's therefore usually right, but not always.

The last, but probably trickiest, part of understanding git merge is the concept of a merge base.  Technically, the merge base is the (single) commit that emerges from an algorithm that finds the Lowest Common Ancestor (LCA) of nodes chosen from a a Directed Acyclic Graph (DAG).  Not all DAG node pairs (or sets) have an LCA: some have none, and some have more than one.  It's pretty common for your Git's commit graph to have a single LCA here, though, and git merge has some methods for dealing with multiple LCAs.  (When there is no LCA, the modern git merge refuses to run by default, telling you that the two branches have unrelated histories.  Old Git ran the merge anyway, and you can make modern Git do the merge anyway; in this case, Git uses a synthetic commit with no files as the merge base.)

The important part here is having a conceptual "feel" for the merge base.  For some graphs, this is easy.  Consider for instance the case of a Git commit graph where your two branches simply fork from a common ancestor commit whose hash ID is H:

```<code>          I--J   <-- branch1 (HEAD)
         /
...--G--H
         \
          K--L   <-- branch2
</code>```

Here, when merging branch1 and branch2—which means commits J and L—the common starting point is clearly commit H.  So git merge will run two git diff commands, and the merge base in each will be H:

```<code>git diff --find-renames <hash-of-H> <hash-of-J>    # what we changed on branch1
git diff --find-renames <hash-of-H> <hash-of-L>    # what they changed on branch2
</code>```

Git will now combine the set of changes produced by these two git diff commands.  Where they overlap, but don't make the same change, is where you will get merge conflicts.

Git will apply the combined changes to the snapshot in H.  Applying your change to this snapshot results in commit J; applying their changes results in commit L; applying the combined changes results in, well, the combination.

If there are no conflicts, Git will be able to combine the changes on its own.  Having applied the combined changes, Git will commit the result on its own, as a new merge commit M:

```<code>          I--J
         /    \
...--G--H      M   <-- branch1 (HEAD)
         \    /
          K--L   <-- branch2
</code>```

and this will be your merge result.

If the combining fails, Git stops in the middle of the merge.  Your job is now to finish the merge (combine the changes yourself), then tell Git you've done it and to the merge commit.  If this is too big a mess, you can tell Git: abort the merge entirely and it will back out all of its attempts to combine things and leave you back on commit J, as if you'd never even run git merge at all.

The last tricky bit is this: when you do finish a merge—automatically through Git, or manually—the resulting merge commit records two parents.  That is, if you look at merge M above, you'll see that it connects back to both commits J and L.  In many merges we'd draw this a little differently:

```<code>                o--o   <-- small-feature
               /    \
...--o--B--o--D--o---o--o   <-- mainline
         \
          o--o--o--o--o--o   <-- big-feature
</code>```

Here the small feature got merged into the mainline, and the big feature is still in progress.  The merge base of the small feature was commit D.  The merge base of the big feature will be commit B.  (The rest of the commits are not very interesting.)  In some cases, though, we get a more-tangled graph:

```<code>                  o--o---o   <-- offshoot-feature
                 /      / \
                o--o---o---o--o   <-- medium-feature
               /    \ /
...--o--o--o--o--o---o----o   <-- mainline
</code>```

This graph isn't all that complicated, but it's really hard, now, to see where the merge bases are, because of all the cross merging from the various features into mainline and each other.

Git will find the merge bases.  You can find merge bases yourself using git merge-base --all.  You can draw the graph, or have Git draw it with git log --graph, and try to find merge bases by eyeball.  Having found merge bases, however you did it, you can run the two git diff commands that git merge would run.  This will tell you where your conflicts will be.  But usually, there's no point: just run git merge and find the conflicts.

Body:
Merge conflicts happen during merges, not after them.

The conflict part is really very simple: A conflict occurs in file F when:

"our" changes—the difference from the merge base commit to our HEAD commit—has a change to file F, and

"their" changes—the difference from the same merge base commit to their tip commit—also have a change to file F as well, and

our changes and their changes overlap (edit: or abut—see comments), but are not identical.

To understand this, you need to:

understand the output of git diff; and

understand what a merge base is.

The output of git diff is pretty straightforward, really, but it requires remembering that each commit holds a snapshot of all of your files.  This means we must give git diff two snapshots: an old one, and a new one.  That's two "pictures" of what the file were like at two points in time.  Git then plays a game of Spot the Difference: it tells you that to go from the left-side snapshot to the right-side snapshot, you must make some set of changes to some set of files.  These changes may involve renaming some files; they might involve adding new files; they might involve deleting files; and they might involve deleting some particular lines from some files, and adding some lines to some files, in some particular places.

The output of git diff is not necessarily anything any person did.  It's just a set of changes that, if applied to the left-side snapshot, get you the right-side snapshot.  The "left side" here is the left argument to git diff and the "right side" here is the right argument, when you use:

git diff <hash1> <hash2>

where the two hashes are the hash IDs of commits.  (This is what git merge does, in effect, although it does all of this internally.)  The diff engine is designed to produce the smallest set of changes that give the right effect.  This, as it turns out, is usually what someone actually did do ... but not always; it's therefore usually right, but not always.

The last, but probably trickiest, part of understanding git merge is the concept of a merge base.  Technically, the merge base is the (single) commit that emerges from an algorithm that finds the Lowest Common Ancestor (LCA) of nodes chosen from a a Directed Acyclic Graph (DAG).  Not all DAG node pairs (or sets) have an LCA: some have none, and some have more than one.  It's pretty common for your Git's commit graph to have a single LCA here, though, and git merge has some methods for dealing with multiple LCAs.  (When there is no LCA, the modern git merge refuses to run by default, telling you that the two branches have unrelated histories.  Old Git ran the merge anyway, and you can make modern Git do the merge anyway; in this case, Git uses a synthetic commit with no files as the merge base.)

The important part here is having a conceptual "feel" for the merge base.  For some graphs, this is easy.  Consider for instance the case of a Git commit graph where your two branches simply fork from a common ancestor commit whose hash ID is H:

          I--J   <-- branch1 (HEAD)
         /
...--G--H
         \
          K--L   <-- branch2

Here, when merging branch1 and branch2—which means commits J and L—the common starting point is clearly commit H.  So git merge will run two git diff commands, and the merge base in each will be H:

git diff --find-renames <hash-of-H> <hash-of-J>    # what we changed on branch1
git diff --find-renames <hash-of-H> <hash-of-L>    # what they changed on branch2

Git will now combine the set of changes produced by these two git diff commands.  Where they overlap, but don't make the same change, is where you will get merge conflicts.

Git will apply the combined changes to the snapshot in H.  Applying your change to this snapshot results in commit J; applying their changes results in commit L; applying the combined changes results in, well, the combination.

If there are no conflicts, Git will be able to combine the changes on its own.  Having applied the combined changes, Git will commit the result on its own, as a new merge commit M:

          I--J
         /    \
...--G--H      M   <-- branch1 (HEAD)
         \    /
          K--L   <-- branch2

and this will be your merge result.

If the combining fails, Git stops in the middle of the merge.  Your job is now to finish the merge (combine the changes yourself), then tell Git you've done it and to the merge commit.  If this is too big a mess, you can tell Git: abort the merge entirely and it will back out all of its attempts to combine things and leave you back on commit J, as if you'd never even run git merge at all.

The last tricky bit is this: when you do finish a merge—automatically through Git, or manually—the resulting merge commit records two parents.  That is, if you look at merge M above, you'll see that it connects back to both commits J and L.  In many merges we'd draw this a little differently:

                o--o   <-- small-feature
               /    \
...--o--B--o--D--o---o--o   <-- mainline
         \
          o--o--o--o--o--o   <-- big-feature

Here the small feature got merged into the mainline, and the big feature is still in progress.  The merge base of the small feature was commit D.  The merge base of the big feature will be commit B.  (The rest of the commits are not very interesting.)  In some cases, though, we get a more-tangled graph:

                  o--o---o   <-- offshoot-feature
                 /      / \
                o--o---o---o--o   <-- medium-feature
               /    \ /
...--o--o--o--o--o---o----o   <-- mainline

This graph isn't all that complicated, but it's really hard, now, to see where the merge bases are, because of all the cross merging from the various features into mainline and each other.

Git will find the merge bases.  You can find merge bases yourself using git merge-base --all.  You can draw the graph, or have Git draw it with git log --graph, and try to find merge bases by eyeball.  Having found merge bases, however you did it, you can run the two git diff commands that git merge would run.  This will tell you where your conflicts will be.  But usually, there's no point: just run git merge and find the conflicts.


问:
Get sender mail in gmail-api
I am trying to figure it out went through gmail-api developer guide.The message part in gmail-api does not contain any detail about sender any help is appreciated thanks. </p>

答:
From documentation we can know that Users.messages will give us the message with following properties

```<code>{
  "id": string,
  "threadId": string,
  "labelIds": [
    string
  ],
  "snippet": string,
  "historyId": unsigned long,
  "internalDate": long,
  "payload": {
    "partId": string,
    "mimeType": string,
    "filename": string,
    "headers": [
      {
        "name": string,
        "value": string
      }
    ],
    "body": users.messages.attachments Resource,
    "parts": [
      (MessagePart)
    ]
  },
  "sizeEstimate": integer,
  "raw": bytes
}
</code>```

From the above properties we can use payload.headers[] to know the Sender mail.
The payload.headers[] will contain array of dictionaries of form {"name":string , "value":string}. To get the sender's mail, we have to find the dictionary with name == 'From' and its corresponding value will give us the sender's mail

I am attaching my python code for reference

    #Call the Gmail API
    #Before calling the API you have to create service using User credentials
    results = service.users().messages().list(userId='me',labelIds = ['INBOX']).execute()
    msgs = results.get('messages',[])
    for msg in msgs:
        mg = service.users().messages().get(userId='me', id=msg['id']).execute()
        msg_headers = mg['payload']['headers']
        for k in range(len(msg_headers)):
            if msg_headers[k]['name'] == 'From':
                print(msg_headers[k]['value'])
                print("\n")
```

ContentLicense: CC BY-SA 3.0

Title: Get sender mail in gmail-api

Body:
From documentation we can know that Users.messages will give us the message with following properties

{
  "id": string,
  "threadId": string,
  "labelIds": [
    string
  ],
  "snippet": string,
  "historyId": unsigned long,
  "internalDate": long,
  "payload": {
    "partId": string,
    "mimeType": string,
    "filename": string,
    "headers": [
      {
        "name": string,
        "value": string
      }
    ],
    "body": users.messages.attachments Resource,
    "parts": [
      (MessagePart)
    ]
  },
  "sizeEstimate": integer,
  "raw": bytes
}

From the above properties we can use payload.headers[] to know the Sender mail.
The payload.headers[] will contain array of dictionaries of form {"name":string , "value":string}. To get the sender's mail, we have to find the dictionary with name == 'From' and its corresponding value will give us the sender's mail

I am attaching my python code for reference

    #Call the Gmail API
    #Before calling the API you have to create service using User credentials
    results = service.users().messages().list(userId='me',labelIds = ['INBOX']).execute()
    msgs = results.get('messages',[])
    for msg in msgs:
        mg = service.users().messages().get(userId='me', id=msg['id']).execute()
        msg_headers = mg['payload']['headers']
        for k in range(len(msg_headers)):
            if msg_headers[k]['name'] == 'From':
                print(msg_headers[k]['value'])
                print("\n")


问:
TypeScript type definition for flatten function
I have simple flatten function. The idea is that it can take array of strings or array of arrays of strings and always return just 1 level array of strings. For example:

```<code>flatten(['a', ['b']]) // returns ['a', 'b']
flatten(['a', 'b']) // returns ['a', 'b']
</code>```

Here is implementation of this function

```<code>function flatten(arr: ReadonlyArray<string | string[]>): string[] {
   return [].concat(...arr);
}
</code>```

I'm getting following TypeScript compiler Error:

```<code>  error TS2769: No overload matches this call.
    Overload 1 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
      Argument of type 'string | string[]' is not assignable to parameter of type 'ConcatArray<never>'.
        Type 'string' is not assignable to type 'ConcatArray<never>'.
    Overload 2 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
      Argument of type 'string | string[]' is not assignable to parameter of type 'ConcatArray<never>'.
        Type 'string' is not assignable to type 'ConcatArray<never>'.

  105   return [].concat(...arr);
                        ~~~~~~
</code>```

How can I define types for input and output of this flatten function? I want to avoid using any type.

答:
I'm thinking the compiler can't figure out what array type the [] value is supposed to be.  The easiest workaround here is to tell it that it's a string[] with a type assertion:

```<code>function flatten(arr: ReadonlyArray<string | string[]>): string[] {
   return ([] as string[]).concat(...arr);
}
</code>```

Hope that helps; good luck!

Playground link to code

Body:
I have simple flatten function. The idea is that it can take array of strings or array of arrays of strings and always return just 1 level array of strings. For example:

flatten(['a', ['b']]) // returns ['a', 'b']
flatten(['a', 'b']) // returns ['a', 'b']

Here is implementation of this function

function flatten(arr: ReadonlyArray<string | string[]>): string[] {
   return [].concat(...arr);
}

I'm getting following TypeScript compiler Error:

  error TS2769: No overload matches this call.
    Overload 1 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
      Argument of type 'string | string[]' is not assignable to parameter of type 'ConcatArray<never>'.
        Type 'string' is not assignable to type 'ConcatArray<never>'.
    Overload 2 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
      Argument of type 'string | string[]' is not assignable to parameter of type 'ConcatArray<never>'.
        Type 'string' is not assignable to type 'ConcatArray<never>'.

  105   return [].concat(...arr);
                        ~~~~~~

How can I define types for input and output of this flatten function? I want to avoid using any type.

Body:
I'm thinking the compiler can't figure out what array type the [] value is supposed to be.  The easiest workaround here is to tell it that it's a string[] with a type assertion:

function flatten(arr: ReadonlyArray<string | string[]>): string[] {
   return ([] as string[]).concat(...arr);
}

Hope that helps; good luck!

Playground link to code