问:
How would you simplify this if/else statement?
I'm very new to learning JavaScript, so I've used an if/else to categorise some data, but the amount of data is huge.

It's part of a VO2 Max calculator that works out a persons VO2max and then decides if that value is Excellent, down to poor.

The data tables which the values are pulled from might be a way to go? But I don't know how:

How could I simplify this? What can I read to figure it out? Or is it not bad practice to use the below? Thanks.

```<code>if(vitals.gender === 1) {
            if(vitals.age >= 18 && vitals.age <= 25) {
                if(vo2 > 60) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 52) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 47) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 42) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 37) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 26 && vitals.age <= 35) {
                 if(vo2 > 56) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 49) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 43) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 40) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 36 && vitals.age <= 45) {
                 if(vo2 > 51) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 43) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 46 && vitals.age <= 55) {
                 if(vo2 > 45) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 36) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 29) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 56 && vitals.age <= 65) {
                 if(vo2 > 41) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 36) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 65) {
                 if(vo2 > 37) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 33) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 29) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 20) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else {
                VO2MaxRating = "Missing";
                document.getElementById("outputVo2").textContent = 'Either you\re under 18 or missing details';
            }
        } else {
            if(vitals.age >= 18 && vitals.age <= 25) {
                if(vo2 > 56) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 47) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 42) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 38) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 33) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 26 && vitals.age <= 35) {
                 if(vo2 > 52) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 45) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 36 && vitals.age <= 45) {
                 if(vo2 > 45) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 38) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 34) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 27) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 46 && vitals.age <= 55) {
                 if(vo2 > 40) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 34) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 20) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 56 && vitals.age <= 65) {
                 if(vo2 > 37) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 18) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 65) {
                 if(vo2 > 32) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 19) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 17) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else {
                VO2MaxRating =
                document.getElementById("outputVo2").textContent = 'Either you\re under 18 or missing details';
            }
        }
</code>```

答:
Make an object of the values you want each option to print out. Based on how your boolean checks are, you can enumerate over the object where the keys are the cutoffs. Then you break out of the loop after you get a match.

edit: if you turn the loop into a function, it becomes reusable. Just pass in your vo2 and the object of values.

```<code>const VO2MaxRating = {
  52: 'Excellent',
  47: 'Good',
  42: 'Above Average',
  37: 'Average',
  30: 'Below Average',
  0: 'Poor',
}

const setRating = (rate, maxRatingObject) => {
  for (let vo2Rating in maxRatingObject) {
    if (rate >= parseInt(vo2Rating)) {
      return maxRatingObject[vo2Rating]
    }
  }
}
document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + setRating(vo2, VO2MaxRating) + ")";
</code>```

Body:
I'm very new to learning JavaScript, so I've used an if/else to categorise some data, but the amount of data is huge.

It's part of a VO2 Max calculator that works out a persons VO2max and then decides if that value is Excellent, down to poor.

The data tables which the values are pulled from might be a way to go? But I don't know how:

How could I simplify this? What can I read to figure it out? Or is it not bad practice to use the below? Thanks.

if(vitals.gender === 1) {
            if(vitals.age >= 18 && vitals.age <= 25) {
                if(vo2 > 60) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 52) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 47) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 42) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 37) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 26 && vitals.age <= 35) {
                 if(vo2 > 56) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 49) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 43) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 40) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 36 && vitals.age <= 45) {
                 if(vo2 > 51) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 43) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 46 && vitals.age <= 55) {
                 if(vo2 > 45) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 36) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 29) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 56 && vitals.age <= 65) {
                 if(vo2 > 41) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 36) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 30) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 65) {
                 if(vo2 > 37) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 33) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 29) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 20) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else {
                VO2MaxRating = "Missing";
                document.getElementById("outputVo2").textContent = 'Either you\re under 18 or missing details';
            }
        } else {
            if(vitals.age >= 18 && vitals.age <= 25) {
                if(vo2 > 56) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 47) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 42) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 38) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 33) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 26 && vitals.age <= 35) {
                 if(vo2 > 52) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 45) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 39) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 35) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 26) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 36 && vitals.age <= 45) {
                 if(vo2 > 45) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 38) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 34) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 27) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 46 && vitals.age <= 55) {
                 if(vo2 > 40) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 34) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 31) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 20) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 56 && vitals.age <= 65) {
                 if(vo2 > 37) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 32) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 18) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else if (vitals.age >= 65) {
                 if(vo2 > 32) {
                    VO2MaxRating = "Excellent";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 28) {
                    VO2MaxRating = "Good";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 25) {
                    VO2MaxRating = "Above Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 22) {
                    VO2MaxRating = "Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 19) {
                    VO2MaxRating = "Below Average";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else if (vo2 >= 17) {
                    VO2MaxRating = "Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                } else {
                    VO2MaxRating = "Very Poor";
                    document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + VO2MaxRating + ")";
                }
            } else {
                VO2MaxRating =
                document.getElementById("outputVo2").textContent = 'Either you\re under 18 or missing details';
            }
        }

Body:
Make an object of the values you want each option to print out. Based on how your boolean checks are, you can enumerate over the object where the keys are the cutoffs. Then you break out of the loop after you get a match.

edit: if you turn the loop into a function, it becomes reusable. Just pass in your vo2 and the object of values.

const VO2MaxRating = {
  52: 'Excellent',
  47: 'Good',
  42: 'Above Average',
  37: 'Average',
  30: 'Below Average',
  0: 'Poor',
}

const setRating = (rate, maxRatingObject) => {
  for (let vo2Rating in maxRatingObject) {
    if (rate >= parseInt(vo2Rating)) {
      return maxRatingObject[vo2Rating]
    }
  }
}
document.getElementById("outputVo2").textContent = vo2 + ' ml/kg/min (' + setRating(vo2, VO2MaxRating) + ")";


来源: stackexchange

问:
msbuild pack command includes directory structure
I'm using dotnet core 2.0, building in Visual Studio Team Services (VSTS).  I added the built-in Visual Studio Build step and am using msbuild with the following arguments:

```<code>/p:DeployOnBuild=true
/p:WebPublishMethod=Package
/p:PackageAsSingleFile=true
/p:SkipInvalidConfigurations=true
/p:DeployIisAppPath="Default Web Site"
/p:DesktopBuildPackageLocation="$(build.artifactstagingdirectory)\MyProject.BuildVersion.zip"
</code>```

This would build a zip file, but the internal structure was ugly and included the entire artifact staging directory as subfolders.  E.g., the path inside my zip file until I got to the actual website file structure was Content\d_C\a\1\s\src\MyProjectName\obj\Release\netcoreapp2.0\PubTmp\Out

Is there a way to zip up just the project files and have those in the root of the zip file?  I have a workaround using a few extra steps, but it would be nice to be able to use a single build step that also zips everything.

Edit

We use Octopus Deploy for deploying to Azure.

答:
Since it is a dotnet core 2.0 project, you can publish project through .NET Core task:

For Visual Studio Build task, you can try to specify /P:PackageTempRootDir="" argument, it will remove source path.

On the other hand, with Azure App Service deploy, the folder structure won’t be remained after deploying to the azure, you can check the folder and files by accessing https://[app name].scm.azurewebsites.net/DebugConsole.

ContentLicense: CC BY-SA 3.0

Body:
I'm using dotnet core 2.0, building in Visual Studio Team Services (VSTS).  I added the built-in Visual Studio Build step and am using msbuild with the following arguments:

/p:DeployOnBuild=true
/p:WebPublishMethod=Package
/p:PackageAsSingleFile=true
/p:SkipInvalidConfigurations=true
/p:DeployIisAppPath="Default Web Site"
/p:DesktopBuildPackageLocation="$(build.artifactstagingdirectory)\MyProject.BuildVersion.zip"

This would build a zip file, but the internal structure was ugly and included the entire artifact staging directory as subfolders.  E.g., the path inside my zip file until I got to the actual website file structure was Content\d_C\a\1\s\src\MyProjectName\obj\Release\netcoreapp2.0\PubTmp\Out

Is there a way to zip up just the project files and have those in the root of the zip file?  I have a workaround using a few extra steps, but it would be nice to be able to use a single build step that also zips everything.

Edit

We use Octopus Deploy for deploying to Azure.


问:
How to change link path in certain container with jQuery
I'm looking to change the links in two containers I have from link.php to ../link.php on certain pages.

Can someone help my with the jQuery code I need to do this?

The containers are two divs, one with the id="nav" and one with the id="fnav"

Thanks

答:
I assume by links, you mean the a elements. You can use the multiple selector, to get a reference to your divs, search for all a elements using find and change the href with attr:

```<code>$('#nav, #fnav')
.find('a')
.attr('href', function(i, value){return '../' + value});
</code>```

You can pass a function to attr which gets the old value as parameter. So this prepending all paths with "../".

If you only want to change the links that refer to index.php, then use the attribute selector: .find('a[href="index.php"]')

ContentLicense: CC BY-SA 2.5

Body:
I assume by links, you mean the a elements. You can use the multiple selector, to get a reference to your divs, search for all a elements using find and change the href with attr:

$('#nav, #fnav')
.find('a')
.attr('href', function(i, value){return '../' + value});

You can pass a function to attr which gets the old value as parameter. So this prepending all paths with "../".

If you only want to change the links that refer to index.php, then use the attribute selector: .find('a[href="index.php"]')


问:
Counting documents by property occurrence in Kibana
I'm trying to create a visualization that looks like this:

Foobar, 10

Bar, 8

Baz, 5.6

The first column is the aggregation itself. Imagine i have documents like this:

```<code>{
  id: 1,
  name: 'lorem ipsum',
  type: 'A'
  author: {
    name: 'Foobar',
  }
}
{
  id: 2,
  name: 'dolor sit amet',
  type: 'B',
  author: {
    name: 'Foobar',
  }
}
</code>```

So, i want to add a +1 to the score of "Foobar" everytime i find a document of type A. And a +2 to the score if i find a document of type B. Basically, aggregating by the author name, and calculating a dynamic value on results.

Is this possible in Kibana? Thanks for the help.

答: AFAIK, you can't do this in Kibana in visualize panel, maybe you can try it in program then index the result into es.

Body:
I'm trying to create a visualization that looks like this:

Foobar, 10

Bar, 8

Baz, 5.6

The first column is the aggregation itself. Imagine i have documents like this:

{
  id: 1,
  name: 'lorem ipsum',
  type: 'A'
  author: {
    name: 'Foobar',
  }
}
{
  id: 2,
  name: 'dolor sit amet',
  type: 'B',
  author: {
    name: 'Foobar',
  }
}

So, i want to add a +1 to the score of "Foobar" everytime i find a document of type A. And a +2 to the score if i find a document of type B. Basically, aggregating by the author name, and calculating a dynamic value on results.

Is this possible in Kibana? Thanks for the help.


问:
Config file XDT transformation InsertIfMissing is skipping children
I am having trouble doing config transform, adding app settings on nuget package install where element appSetting may or may not exist.

What I want to happen:

appSetting element does not exist

Insert appSetting element and its children

appSetting element exist

Insert children if missing

I only get one or the other to work, but not both occasions.

web.config.install.xdt

<?xml version="1.0"?>
<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
  <appSettings xdt:Transform="InsertIfMissing" >
    <add key="Swagger.Contact.Name" value="Some Name" xdt:Transform="InsertIfMissing" />
    <add key="Swagger.Contact.Email" value="some@email.address" xdt:Transform="InsertIfMissing" />
  </appSettings>
</configuration>
```

<h1>Example 1</h1>

<p><strong>web.config</strong> BEFORE</p>

<pre class="lang-xml prettyprint-override"><code><?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
</configuration>
</code>```

appSettings element not present before transformation.

web.config AFTER

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Swagger.Contact.Name" value="Some Name" />
    <add key="Swagger.Contact.Email" value="some@email.address" />
  </appSettings>
</configuration>
```

<h1>Example 2</h1>

<p><strong>web.config</strong> BEFORE</p>

<pre class="lang-xml prettyprint-override"><code><?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Other.Key" value="With Some Value" />
  </appSettings>
</configuration>
</code>```

appSettings element present before transformation.

web.config AFTER

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Other.Key" value="With Some Value" />
  </appSettings>
</configuration>
```

Nothing happens in example 2 as the appSettings element already exist, I would like it to still evaluate its child elements and insert those if they do not exist, but it seems they are just ignored. Is there any other value for the attribute xdt:Transform I can use, or any other hacks to work around this issue?

答:
I had a similar problem quite a while back. The workaround I applied was to have two entries with <appSettings> in the XDT file, one to check if its absent and if yes, then go ahead and insert it. The other was for the scenario when the <appSettings> element was already present. Here is short snippet to help you with your problem:

```<code><?xml version="1.0"?>
<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
    <appSettings xdt:Transform="InsertIfMissing">
    </appSettings>
    <appSettings>
      <add key="Swagger.Contact.Name" value="Some Name" xdt:Transform="InsertIfMissing" />
      <add key="Swagger.Contact.Email" value="some@email.address" xdt:Transform="InsertIfMissing" />
    </appSettings>
</configuration>
</code>```

Let me know if this works for you.

Body:
I am having trouble doing config transform, adding app settings on nuget package install where element appSetting may or may not exist.

What I want to happen:

appSetting element does not exist

Insert appSetting element and its children

appSetting element exist

Insert children if missing

I only get one or the other to work, but not both occasions.

web.config.install.xdt

<?xml version="1.0"?>
<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
  <appSettings xdt:Transform="InsertIfMissing" >
    <add key="Swagger.Contact.Name" value="Some Name" xdt:Transform="InsertIfMissing" />
    <add key="Swagger.Contact.Email" value="some@email.address" xdt:Transform="InsertIfMissing" />
  </appSettings>
</configuration>

Example 1

web.config BEFORE

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
</configuration>

appSettings element not present before transformation.

web.config AFTER

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Swagger.Contact.Name" value="Some Name" />
    <add key="Swagger.Contact.Email" value="some@email.address" />
  </appSettings>
</configuration>

Example 2

web.config BEFORE

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Other.Key" value="With Some Value" />
  </appSettings>
</configuration>

appSettings element present before transformation.

web.config AFTER

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.5.2" />
    <httpRuntime targetFramework="4.5.2" maxRequestLength="51200" />
    <customErrors mode="Off" />
  </system.web>
  <appSettings>
    <add key="Other.Key" value="With Some Value" />
  </appSettings>
</configuration>

Nothing happens in example 2 as the appSettings element already exist, I would like it to still evaluate its child elements and insert those if they do not exist, but it seems they are just ignored. Is there any other value for the attribute xdt:Transform I can use, or any other hacks to work around this issue?

Body:
I had a similar problem quite a while back. The workaround I applied was to have two entries with <appSettings> in the XDT file, one to check if its absent and if yes, then go ahead and insert it. The other was for the scenario when the <appSettings> element was already present. Here is short snippet to help you with your problem:

<?xml version="1.0"?>
<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
    <appSettings xdt:Transform="InsertIfMissing">
    </appSettings>
    <appSettings>
      <add key="Swagger.Contact.Name" value="Some Name" xdt:Transform="InsertIfMissing" />
      <add key="Swagger.Contact.Email" value="some@email.address" xdt:Transform="InsertIfMissing" />
    </appSettings>
</configuration>

Let me know if this works for you.


问:
Checking values in a class list
Basically, I have a class for the Player of a game

```<code>class Player:
    def __init__(self,inventory,hp):
        self.inventory = []
        self.hp = 20
    ...
    ...

P = Player()
</code>```

And I simply want to check for an item in the inventory (where items are each a class as well)

```<code>class Book():
    def __init__(self,name,description):
        ...
        ...
</code>```

Then do this.

```<code>if Book() in P.inventory:
    print("You have a book.")
else:
    print("You don't have a book.")
</code>```

The problem I'm having is that even if the Book() object is in the player's inventory, it reads the if statement as false and runs the else statement.

I'm thinking I could try to use a for loop like so

```<code>for i in P.inventory:
    counter = 0
    if i == Book():
        print("You have a book.")
        counter = 1
if counter == 0:
    print("You don't have a book.")
</code>```

but I'm hoping I won't have to use that much code for such a simple task.

答:
Actually if just care about the book, treating the books with the same name and same description as an identity book. You'd better overwrite the eq and hash method of the book.

```<code>class Player:
    def __init__(self, inventory=None, hp=None):
        if inventory is None:
            inventory = []
        self.inventory = inventory
        self.hp = hp

class Book:
    def __init__(self, name, description):
        self.name = name
        self.description = description

    def __eq__(self, other):
        return other and self.name == other.name and self.description == other.description

    def __ne__(self, other):
        return not self.__eq__(other)

    def __hash__(self):
        return hash((self.name, self.description))

player = Player([Book('Harry Potter', 'Volume I'), Book('Harry Potter', 'Volume II')], 20)

print(Book('Harry Potter', 'Volume I') in player.inventory) # True
print(Book('Harry Potter', 'Volume V') in player.inventory) # False
</code>```

So you don't have to worry about if the book you wanna check is exactly the instance in memory. Due to in most cases, your data should be stored in db, not in the memory.

Title: Checking values in a class list

Body:
Basically, I have a class for the Player of a game

class Player:
    def __init__(self,inventory,hp):
        self.inventory = []
        self.hp = 20
    ...
    ...

P = Player()

And I simply want to check for an item in the inventory (where items are each a class as well)

class Book():
    def __init__(self,name,description):
        ...
        ...

Then do this.

if Book() in P.inventory:
    print("You have a book.")
else:
    print("You don't have a book.")

The problem I'm having is that even if the Book() object is in the player's inventory, it reads the if statement as false and runs the else statement.

I'm thinking I could try to use a for loop like so

for i in P.inventory:
    counter = 0
    if i == Book():
        print("You have a book.")
        counter = 1
if counter == 0:
    print("You don't have a book.")

but I'm hoping I won't have to use that much code for such a simple task.

Body:
Actually if just care about the book, treating the books with the same name and same description as an identity book. You'd better overwrite the eq and hash method of the book.

class Player:
    def __init__(self, inventory=None, hp=None):
        if inventory is None:
            inventory = []
        self.inventory = inventory
        self.hp = hp

class Book:
    def __init__(self, name, description):
        self.name = name
        self.description = description

    def __eq__(self, other):
        return other and self.name == other.name and self.description == other.description

    def __ne__(self, other):
        return not self.__eq__(other)

    def __hash__(self):
        return hash((self.name, self.description))

player = Player([Book('Harry Potter', 'Volume I'), Book('Harry Potter', 'Volume II')], 20)

print(Book('Harry Potter', 'Volume I') in player.inventory) # True
print(Book('Harry Potter', 'Volume V') in player.inventory) # False

So you don't have to worry about if the book you wanna check is exactly the instance in memory. Due to in most cases, your data should be stored in db, not in the memory.


问:
How to access particular variable of object stored in node of singly linked list (iteration)
This is a very specific question, and I can't seem to find anything in particular which helps. I have a singly linked list( not an implemented linked list, which is all I've been able to find)in which the nodes store a Student object.Each Student object has variables, although I'm having trouble accessing each variable.

I think it's supposed to be similar to how you'd iterate through an array of objects.But that uses the for loop.And to traverse a linked list you have to work with the nodes and their next&data values.

I'm not entirely sure how to go about combining the 2 ideas.I feel like it's either something stupidly simple I'm not getting, or there's an entirely different approach I'm supposed to be taking.

```<code>import java.util.scanner;

public class StudentNode extends Student
{
private Student data;
private StudentNode next;

class SinglyLinkedList
{

 private StudentNode first;

 //constructor
 public SinglyLinkedList()
 {
     first=null;
 }

 public addToList(Student newData)
 {
     StudentNode newNode= new StudentNode();
     newNode.data=newData;
     newNode.next=first; //refs to the element first is currently pointing to
     first=newNode;//first now refs to added element
 }

 public courseMark(Student data)
 {
     double cm=courseMark(StudentNode.data);
     return "Student number : "+stuNum +"Course Mark: "+cm;

 }

public double classAverage(Student data)
{
//traverses linked list, not enirely sure about how to access the course mark
    double classAvg=0;
    double sum = 0;
    int i=0;
    StudentNode current = first;
    StudentNode previous = null;
    while (current != null)
    {
        i++;
        StudentNode current= Student.courseMark();
        sum += current.data;//not sure bout course mark access
        previous = current;
        current = current.next;
     }
   return classAvg=sum/i;
  }
</code>```

And here's the Student class which the data component uses. Not sure if it'll be needed to answer.

```<code>public class Student
{
private String name;
private String stuNum;
private int firstTest;
private int secondTest;
private int thirdTest;

public Student(String n,String sN,int fT,int sT,int tT)
{
    name=n;
    stuName=sN;
    firstTest=fT;
    secondTest=sT;
    thirsTest=tT;
}

//setters
public void setName(String n)
{
    name=n;
}

public void setStuNum(String sN)
{
    stuNum=sN;
}

public void setFirstTest(int fT)
{
    firstTest=fT;
}

public void setSecondTest(int sT)
{
    secondTest=sT;
}

public void setThirdTest(int tT)
{
    thirdTest=tT;
}

//getters

public String getName()
{
    return name;
}

public String getStuNum()
{
    return stuNum;
}

public int getFirstTest()
{
    return firstTest;
}

public int getSecondTest()
{
    return secondTest;
}

public int getThirdTest()
{
    return thirdTest;
}

//course mark computer

public double courseMark()
{
    double crseMark=(firstTest*0.25)+(secondTest*0.25)+(thirdTest*0.50);
    return crseMark;
}
</code>```

}

答:
You must traverse from the node to the student data to get the courseMark.

    while (current != null) {
        ...
        double courseMark = current.data.courseMark();
        ...
    }

Body:
This is a very specific question, and I can't seem to find anything in particular which helps. I have a singly linked list( not an implemented linked list, which is all I've been able to find)in which the nodes store a Student object.Each Student object has variables, although I'm having trouble accessing each variable.

I think it's supposed to be similar to how you'd iterate through an array of objects.But that uses the for loop.And to traverse a linked list you have to work with the nodes and their next&data values.

I'm not entirely sure how to go about combining the 2 ideas.I feel like it's either something stupidly simple I'm not getting, or there's an entirely different approach I'm supposed to be taking.

import java.util.scanner;

public class StudentNode extends Student
{
private Student data;
private StudentNode next;

class SinglyLinkedList
{

 private StudentNode first;

 //constructor
 public SinglyLinkedList()
 {
     first=null;
 }

 public addToList(Student newData)
 {
     StudentNode newNode= new StudentNode();
     newNode.data=newData;
     newNode.next=first; //refs to the element first is currently pointing to
     first=newNode;//first now refs to added element
 }

 public courseMark(Student data)
 {
     double cm=courseMark(StudentNode.data);
     return "Student number : "+stuNum +"Course Mark: "+cm;

 }

public double classAverage(Student data)
{
//traverses linked list, not enirely sure about how to access the course mark
    double classAvg=0;
    double sum = 0;
    int i=0;
    StudentNode current = first;
    StudentNode previous = null;
    while (current != null)
    {
        i++;
        StudentNode current= Student.courseMark();
        sum += current.data;//not sure bout course mark access
        previous = current;
        current = current.next;
     }
   return classAvg=sum/i;
  }

And here's the Student class which the data component uses. Not sure if it'll be needed to answer.

public class Student
{
private String name;
private String stuNum;
private int firstTest;
private int secondTest;
private int thirdTest;

public Student(String n,String sN,int fT,int sT,int tT)
{
    name=n;
    stuName=sN;
    firstTest=fT;
    secondTest=sT;
    thirsTest=tT;
}

//setters
public void setName(String n)
{
    name=n;
}

public void setStuNum(String sN)
{
    stuNum=sN;
}

public void setFirstTest(int fT)
{
    firstTest=fT;
}

public void setSecondTest(int sT)
{
    secondTest=sT;
}

public void setThirdTest(int tT)
{
    thirdTest=tT;
}

//getters

public String getName()
{
    return name;
}

public String getStuNum()
{
    return stuNum;
}

public int getFirstTest()
{
    return firstTest;
}

public int getSecondTest()
{
    return secondTest;
}

public int getThirdTest()
{
    return thirdTest;
}

//course mark computer

public double courseMark()
{
    double crseMark=(firstTest*0.25)+(secondTest*0.25)+(thirdTest*0.50);
    return crseMark;
}

}


问:
Custom Subview on a iOS view has null outlets
I have a view called FeedView, handled by FeedViewController.

I also have a XIB called "NearestStore" which is handled by a view controller named "NearestStoreViewController". NearestStore xib has labels, buttons, etc. In the view controller I have outlets that are connected to the subviews in NearestStore.xib.

NearestStore inherits from UIButton (so it's easier to handle click event).

On FeedViewController.xib I have a UIButton that has been set to be of type NearestStore.

So far so good. This is on my FeedViewController:

```<code>__weak IBOutlet NearestStoreButton *btn_nearestStore;
</code>```

The outlet is connected on the xib to the outlet.

NearestStoreViewController has several outlets to subviews like:

```<code>@property (nonatomic, weak) IBOutlet  UILabel *lbl_distance;
@property (nonatomic, weak) IBOutlet  UIImageView *img_distance;
</code>```

For some reason, on my FeedViewController the reference to btn_nearestStore is fine, but all the subviews are nil.

For example:

```<code>btn_nearestStore.lbl_distance
</code>```

is nil

What am I missing?

答:
Following post contains detailed explanation about creating custom views using Nib:

creating custom view using Nib

After I create the customInit as mentioned in the post, I am able to get the IBOutlets allocated.

Body:
I have a view called FeedView, handled by FeedViewController.

I also have a XIB called "NearestStore" which is handled by a view controller named "NearestStoreViewController". NearestStore xib has labels, buttons, etc. In the view controller I have outlets that are connected to the subviews in NearestStore.xib.

NearestStore inherits from UIButton (so it's easier to handle click event).

On FeedViewController.xib I have a UIButton that has been set to be of type NearestStore.

So far so good. This is on my FeedViewController:

__weak IBOutlet NearestStoreButton *btn_nearestStore;

The outlet is connected on the xib to the outlet.

NearestStoreViewController has several outlets to subviews like:

@property (nonatomic, weak) IBOutlet  UILabel *lbl_distance;
@property (nonatomic, weak) IBOutlet  UIImageView *img_distance;

For some reason, on my FeedViewController the reference to btn_nearestStore is fine, but all the subviews are nil.

For example:

btn_nearestStore.lbl_distance

is nil

What am I missing?


问:
How to get argument type hint in decorator?
How can I do the following:

```<code>import typing

def needs_parameter_type(decorated):
    def decorator(*args):
        [do something with the *type* of bar (aka args[0]), some_class]
        decorated(*args)
    return decorator

@needs_parameter_type
def foo(bar: SomeClass):
    …

foo(…)
</code>```

The use case is to avoid the following repetition:

```<code>@needs_parameter_type(SomeClass)
def foo(bar: SomeClass):
    …
</code>```

答:
These are stored in the __annotations__ property of the function, you can access them by this:

```<code>def needs_parameter_type(decorated):
    def decorator(*args):
        print(decorated.__annotations__)
        decorated(*args)
    return decorator

@needs_parameter_type
def foo(bar: int):
   pass

foo(1)
#  {"bar": <class "int">}
</code>```

Body:
How can I do the following:

import typing

def needs_parameter_type(decorated):
    def decorator(*args):
        [do something with the *type* of bar (aka args[0]), some_class]
        decorated(*args)
    return decorator

@needs_parameter_type
def foo(bar: SomeClass):
    …

foo(…)

The use case is to avoid the following repetition:

@needs_parameter_type(SomeClass)
def foo(bar: SomeClass):
    …

Body:
These are stored in the __annotations__ property of the function, you can access them by this:

def needs_parameter_type(decorated):
    def decorator(*args):
        print(decorated.__annotations__)
        decorated(*args)
    return decorator

@needs_parameter_type
def foo(bar: int):
   pass

foo(1)
#  {"bar": <class "int">}


问:
How to set version-script file in CMakeLists.txt file of Android Studio
I have a ndk project in Android Studio, and I want to control the exported symbols by this way:

set (CMAKE_SHARED_LINKER_FLAGS ${CMAKE_SHARED_LINKER_FLAGS} "-Wl,--version-script=D:\ProjectFolder\export_symbols")

or

set (CMAKE_SHARED_LINKER_FLAGS ${CMAKE_SHARED_LINKER_FLAGS} "-Wl,--version-script=export_symbols")

This export_symbols file is put together with CMaleLists.txt.
The problem is that the compiler would report an error during link and complain that:  'error: no such file or directory'.

So the question is how can I tell the compiler where my export_symbols file is? Any suggestion is welcomed. Thanks.

答:
Solved by adding ${CMAKE_SOURCE_DIR} before the file name.

```<code>set (CMAKE_SHARED_LINKER_FLAGS ${CMAKE_SHARED_LINKER_FLAGS} "-Wl,--version-script=" ${CMAKE_SOURCE_DIR} "/export_symbols")
</code>```

Body:
Solved by adding ${CMAKE_SOURCE_DIR} before the file name.

set (CMAKE_SHARED_LINKER_FLAGS ${CMAKE_SHARED_LINKER_FLAGS} "-Wl,--version-script=" ${CMAKE_SOURCE_DIR} "/export_symbols")


问:
Disable animation on md-tabs, angularjs material
The animation when switching tabs is so laggy. Makes my entire application unusable. A true show-stopper.

I've read many questions on the topic. Is it really total impossible to remove this animation?

https://material.angularjs.org/latest/api/directive/mdTabs

答:
Just add this line of css to disabled it: (PLUNKER)

```<code>/* This will disable the panel animation */
md-tabs [role="tabpanel"] {
    transition: none;
}

/* This will disable the `ink-bar` animation (border-bottom of selected tab) */
md-tabs md-ink-bar {
  transition: none;
}
</code>```

Additionally, if you want to hide/remove the ink-bar (use display: none instead transition: none) and add custom style the selected tab...

```<code>md-tabs .md-active {
   font-weight: bold;
   /* Add your custom css styles to selected tab here */
}
</code>```

** Tested and worked from angularjs-material versions > 1.0.0

Body:
Just add this line of css to disabled it: (PLUNKER)

/* This will disable the panel animation */
md-tabs [role="tabpanel"] {
    transition: none;
}

/* This will disable the `ink-bar` animation (border-bottom of selected tab) */
md-tabs md-ink-bar {
  transition: none;
}

Additionally, if you want to hide/remove the ink-bar (use display: none instead transition: none) and add custom style the selected tab...

md-tabs .md-active {
   font-weight: bold;
   /* Add your custom css styles to selected tab here */
}

** Tested and worked from angularjs-material versions > 1.0.0


问:
How to make submenus?
I would like a help to make submenus, from the menu number "1". I tried using the code below but it did not work.

Here is my code:

```<code>@signals.message_received.connect
def handle(message):
    # Main menu
    if message.command == "Olá":
        menuPrincipal(message)
    # 1 - Budgeting
    elif message.command == "1":
        orcamentos(message)
    # 2 - Track an order already in progress
    elif message.command == "2":
        pedidoAndamento(message)
    # 3 - Change the date, time or location of the event
    elif message.command == "3":
        alterarPedido(message)
    # 4 - Special Offers
    elif message.command == "4":
        promocoes(message)
    # 5 - Speak to a representative
    elif message.command == "5":
        chamarRepresentante(message)
</code>```

Below is the orcamentos() function that I would like to put as a submenu:

```<code>def orcamentos(message):
    mac.send_message(txtOrcamentos, message.conversation)
        # 1 Party kit
    if message.command == "1":
        partyKit(message)
        # 2 Confectionery cake
    elif message.command == "2":
        confCake(message)
        # 3 Salty pie
    elif message.command == "3":
        saltPie(message)
        # 4 Cupcakes
    elif message.command == "4":
        cupcakes(message)
        # 5 Sweets
    elif message.command == "5":
        sweets(message)
        # 6 Salty
    elif message.command == "6":
        salty(message)
</code>```

答:
you can use regex or 'in' keyword, ex : if "1" in message.command:
but i will prefer using regex so it will be more specified that what user types is a command or not.

also if you like to compress your files(because i am having like 30+menu in my bot) you will probably like to keep them in seperate file, so you can use this interface file 'yowsup.layers.interface' which contains 'YowInterfaceLayer, ProtocolEntityCallback'.

"^fun$" this regex will detect the word fun and "^wiki (?P[^$]+)$" will detect the word after the keyword wiki so it have far more control over commands.

Title: How to make submenus?

Body:
I would like a help to make submenus, from the menu number "1". I tried using the code below but it did not work.

Here is my code:

@signals.message_received.connect
def handle(message):
    # Main menu
    if message.command == "Olá":
        menuPrincipal(message)
    # 1 - Budgeting
    elif message.command == "1":
        orcamentos(message)
    # 2 - Track an order already in progress
    elif message.command == "2":
        pedidoAndamento(message)
    # 3 - Change the date, time or location of the event
    elif message.command == "3":
        alterarPedido(message)
    # 4 - Special Offers
    elif message.command == "4":
        promocoes(message)
    # 5 - Speak to a representative
    elif message.command == "5":
        chamarRepresentante(message)

Below is the orcamentos() function that I would like to put as a submenu:

def orcamentos(message):
    mac.send_message(txtOrcamentos, message.conversation)
        # 1 Party kit
    if message.command == "1":
        partyKit(message)
        # 2 Confectionery cake
    elif message.command == "2":
        confCake(message)
        # 3 Salty pie
    elif message.command == "3":
        saltPie(message)
        # 4 Cupcakes
    elif message.command == "4":
        cupcakes(message)
        # 5 Sweets
    elif message.command == "5":
        sweets(message)
        # 6 Salty
    elif message.command == "6":
        salty(message)


问:
Switching from zsh to bash on OS X, and back again?
I'm learning to develop in Rails, and have discovered the power of zsh. However, for some of my other tasks, I wish to use normal bash.

Although they are the same, I just feel comfortable with the layout of bash in some situations.

How do I switch back and forth, or turn zsh on and off?

答:
For Bash, try

```<code>chsh -s $(which bash)
</code>```

For zsh, try

```<code>chsh -s $(which zsh)
</code>```

ContentLicense: CC BY-SA 4.0

Body:
For Bash, try

chsh -s $(which bash)

For zsh, try

chsh -s $(which zsh)


问:
How to use where condition multiple times within one single sql query
In my table1 there is date like:

```<code>id      value
1       500
2       400
3       300
4       200
5       100
</code>```

I want to set the data above within the show table:

```<code>d1      d2      d3      d4      d5
500     400     300     200     100
</code>```

I am using the following sql query.

```<code>"SELECT `value` as d1 from `table1` WHERE `id`=1"
"SELECT `value` as d2 from `table1` WHERE `id`=2"
"SELECT `value` as d3 from `table1` WHERE `id`=3"
"SELECT `value` as d4 from `table1` WHERE `id`=4"
"SELECT `value` as d5 from `table1` WHERE `id`=5"
</code>```

How will I make all the queries within single sql query?

答:
If you can work with separate rows, just filter the values:

```<code>select id,
    value
from t
where id in (1,2,3,4,5);
</code>```

If you need all the values in a single row, use where to filter all the rows and conditional aggregation to pivot the data:

```<code>select max(case when id = 1 then value end) as d1,
       max(case when id = 2 then value end) as d2,
       max(case when id = 3 then value end) as d3,
       max(case when id = 4 then value end) as d4,
       max(case when id = 5 then value end) as d5
from t
where id in (1,2,3,4,5);
</code>```

Body:
In my table1 there is date like:

id      value
1       500
2       400
3       300
4       200
5       100

I want to set the data above within the show table:

d1      d2      d3      d4      d5
500     400     300     200     100

I am using the following sql query.

"SELECT `value` as d1 from `table1` WHERE `id`=1"
"SELECT `value` as d2 from `table1` WHERE `id`=2"
"SELECT `value` as d3 from `table1` WHERE `id`=3"
"SELECT `value` as d4 from `table1` WHERE `id`=4"
"SELECT `value` as d5 from `table1` WHERE `id`=5"

How will I make all the queries within single sql query?

Body:
If you can work with separate rows, just filter the values:

select id,
    value
from t
where id in (1,2,3,4,5);

If you need all the values in a single row, use where to filter all the rows and conditional aggregation to pivot the data:

select max(case when id = 1 then value end) as d1,
       max(case when id = 2 then value end) as d2,
       max(case when id = 3 then value end) as d3,
       max(case when id = 4 then value end) as d4,
       max(case when id = 5 then value end) as d5
from t
where id in (1,2,3,4,5);


答:
You'll need to group the array first, group them by ID, then Date. Assign them in a new container as multi dimensional array, first level the ID, and on each ID each Date.

Idea:

```<code>$arr = array();
// group them
foreach ($list_data as $v) {
    // first by id, then by date
    $arr[$v[0]][$v[1]][] = $v[2];
}

// present it
foreach ($arr as $id => $sorted) {
    foreach ($sorted as $date => $times) {
        $times = array_map('strtotime', $times);
        $smallest = date('H:i:s', min($times));
        $biggest = date('H:i:s', max($times));
        echo "ID '{$id}' on '{$date}' SMALLEST TIME is {$smallest}<br/>";
        echo "ID '{$id}' on '{$date}' BIGGEST TIME is {$biggest}<br/>";
    }
}
</code>```

Basically each time is designated to each date, just simply convert them to unix timestamp and as an array, just use min and max to get the lowest and highest.

Sample Out

Title: Get min & max value from array every `id` depend on `date` PHP

Body:
I need help for logic to get min & max value from an array for every id depend on date.

Here's the example of array :

$list_data  = array(
            array('20', '2016-08-04', '10:07:42'),
            array('20', '2016-08-04', '18:07:34'),
            array('35', '2016-08-05', '10:09:39'),
            array('35', '2016-08-05', '10:09:45'),
            array('35', '2016-08-05', '18:03:18'),
            array('35', '2016-08-05', '18:03:18'),
            array('39', '2016-08-05', '10:09:23'),
            array('39', '2016-08-05', '10:09:25'),
            array('39', '2016-08-05', '18:03:36'),
            array('39', '2016-08-05', '18:03:37'),
            array('35', '2016-08-08', '10:09:39'),
            array('35', '2016-08-08', '10:09:45'),
            array('35', '2016-08-08', '18:03:18'),
            array('35', '2016-08-08', '18:03:18'),
            array('39', '2016-08-08', '10:09:23'),
            array('39', '2016-08-08', '10:09:25'),
            array('39', '2016-08-08', '18:03:36'),
            array('39', '2016-08-08', '18:03:37'),
        );

index[0] = ID,
index[1] = Date,
index[2] = Time,

How i print the array

foreach($list_data as $data){
            echo $data[0];
            echo '
';
            echo $data[1];
            echo '
';
            echo $data[2];
            echo '
';
            echo '
';
        }

Now, what i want is to find the smallest time and biggest time for every ID on every Date

Example list i want to show :

ID '35' on '2016-08-05' SMALLEST TIME is '10:09:39';

ID '35' on '2016-08-05' BIGGEST TIME is '18:03:18';

ID '39' on '2016-08-05' SMALLEST TIME is '10:09:23';

ID '39' on '2016-08-05' BIGGEST TIME is '18:03:37';

Thank you

Conclusion :
Caused list data of array comes from another machine (format date and time can not be changed into unixtimestamp), so this is how i avoid to use 'strtotime'.

Result :

function to convert date so i'm not using 'strtotime' function

function date_convert_to_time($date){
    $new_date   = new DateTime($date);
    return $new_date->format('U');
}

first group array

$arr = array();
// group them
foreach ($list_data as $v) {
    // first by id, then by date
    $arr[$v[0]][$v[1]][] = date_convert_to_time($v[1].' '.$v[2]);
}

// present it
foreach ($arr as $id => $sorted) {
    foreach ($sorted as $date => $times) {
        // $times = array_map('strtotime', $times); <--commented
        $smallest = date('H:i:s', min($times));
        $biggest = date('H:i:s', max($times));
        echo "ID '{$id}' on '{$date}' SMALLEST TIME is {$smallest}\n";
        echo "ID '{$id}' on '{$date}' BIGGEST TIME is {$biggest}\n";
    }
}

Body:
You'll need to group the array first, group them by ID, then Date. Assign them in a new container as multi dimensional array, first level the ID, and on each ID each Date.

Idea:

$arr = array();
// group them
foreach ($list_data as $v) {
    // first by id, then by date
    $arr[$v[0]][$v[1]][] = $v[2];
}

// present it
foreach ($arr as $id => $sorted) {
    foreach ($sorted as $date => $times) {
        $times = array_map('strtotime', $times);
        $smallest = date('H:i:s', min($times));
        $biggest = date('H:i:s', max($times));
        echo "ID '{$id}' on '{$date}' SMALLEST TIME is {$smallest}<br/>";
        echo "ID '{$id}' on '{$date}' BIGGEST TIME is {$biggest}<br/>";
    }
}

Basically each time is designated to each date, just simply convert them to unix timestamp and as an array, just use min and max to get the lowest and highest.

Sample Out


答:
Should be pretty simple:

```<code>$('#nav, #fnav').find('a').attr('href', function(index, href) {
    return '../' + href;
});
</code>```

Ref.: .attr()

Title: How to change link path in certain container with jQuery

Body:
I'm looking to change the links in two containers I have from link.php to ../link.php on certain pages.

Can someone help my with the jQuery code I need to do this?

The containers are two divs, one with the id="nav" and one with the id="fnav"

Thanks

Body:
Should be pretty simple:

$('#nav, #fnav').find('a').attr('href', function(index, href) {
    return '../' + href;
});

Ref.: .attr()


问:
Sphinx: automatically label headings?
In Sphinx, is it possible to automatically define labels for headings? I've found that my documents end up looking a lot like this:

```
.._doing stuff:

Doing Stuff
-----------

You might also want :ref:`other stuff`.

.._other stuff:

Other Stuff
-----------

No, you want :ref:`doing stuff`.
```

And it would be nice to remove that duplication.

答: Sphinx 1.4 added sphinx.ext.autosectionlabel which supports this. It includes an option that will prefix the document name to the label to avoid cross-document clashes.

Title: Sphinx: automatically label headings?

Body:
In Sphinx, is it possible to automatically define labels for headings? I've found that my documents end up looking a lot like this:

.._doing stuff:

Doing Stuff
-----------

You might also want :ref:`other stuff`.

.._other stuff:

Other Stuff
-----------

No, you want :ref:`doing stuff`.

And it would be nice to remove that duplication.


问:
data frame condition multiple rows
Say one has a data frame as follows:

```<code>data <- data.frame('obs' = c('a','c','b'), 'top1' = c('a','b','c'), 'top2' = c('b', 'c', 'f'), 'top3' = c('g', 'h', 'd'))
</code>```

I wan to compute a new column topn which is a conditional that works in the following fashion: if the value of obs is in any of the top columns then topn should be equal to obs, otherwise topn can be assigned any value, say top1. Of course I know I can do this with an or and ifelse, but I'm looking for a shorter way to write it because in my table I can have up to 10 top columns.

```<code> obs top1 top2 top3 topn
   a    a    b    g  a
   c    b    c    h  c
   b    c    f    d  c
</code>```

答:
If we are looking for a vectorized approach, then we can use the rowSums on a logical matrix to find if there are any matches, then with ifelse get the column values based on the logical vector

```<code>i1 <- data[-1] == data['obs'][col(data[-1])]
data$topn <- ifelse(rowSums(i1) != 0, as.character(data$obs), as.character(data$top1))
data$topn
#[1] "a" "c" "c"
</code>```

Title: data frame condition multiple rows

Body:
Say one has a data frame as follows:

data <- data.frame('obs' = c('a','c','b'), 'top1' = c('a','b','c'), 'top2' = c('b', 'c', 'f'), 'top3' = c('g', 'h', 'd'))

I wan to compute a new column topn which is a conditional that works in the following fashion: if the value of obs is in any of the top columns then topn should be equal to obs, otherwise topn can be assigned any value, say top1. Of course I know I can do this with an or and ifelse, but I'm looking for a shorter way to write it because in my table I can have up to 10 top columns.

 obs top1 top2 top3 topn
   a    a    b    g  a
   c    b    c    h  c
   b    c    f    d  c

Body:
If we are looking for a vectorized approach, then we can use the rowSums on a logical matrix to find if there are any matches, then with ifelse get the column values based on the logical vector

i1 <- data[-1] == data['obs'][col(data[-1])]
data$topn <- ifelse(rowSums(i1) != 0, as.character(data$obs), as.character(data$top1))
data$topn
#[1] "a" "c" "c"


问:
to set MutationObserver, How to inject javascript before page-loading using Selenium
I'm trying to set MutationObserver for observing page mutation while loading.

In order to do that, MutationObserver should be configured before page loading.

With selenium-chromedriver, couldn't find the way to inject JS for such purpose.

I know chrome extension can do that but extensions won't work on headless mode.

That's the problem.

答:
It's possible via the DevTool API by calling Page.addScriptToEvaluateOnNewDocument

from selenium import webdriver
from selenium.webdriver.remote.webdriver import WebDriver
import json

def send(driver, cmd, params={}):
  resource = "/session/%s/chromium/send_command_and_get_result" % driver.session_id
  url = driver.command_executor._url + resource
  body = json.dumps({'cmd': cmd, 'params': params})
  response = driver.command_executor._request('POST', url, body)
  if response['status']:
    raise Exception(response.get('value'))
  return response.get('value')

def add_script(driver, script):
  send(driver, "Page.addScriptToEvaluateOnNewDocument", {"source": script})

WebDriver.add_script = add_script

# launch Chrome
driver = webdriver.Chrome()

# add a script which will be executed when the page starts loading
driver.add_script("""
  if (window.self === window.top) { // if main document
    console.log('add script');
  }
  """)

# load a page
driver.get("https://stackoverflow.com/questions")
```


问:
How can i repeat a script?
i've search for command or solution to repeat a script after n times but i can't find it.
This is my rusty script:

```<code>#!/bin/csh -f
rm -rf result120
rm -rf result127
rm -rf result126
rm -rf result125
rm -rf result128
rm -rf result129
rm -rf result122
rm -rf output
rm -rf aaa
### Get job id from user name
foreach file ( `cat name` )
        echo `bjobs -u $file | awk '$1 ~ /^[0-9]+/ {print $1}' >> aaa`
        echo "loading"
end
### Read in job id
foreach file ( `cat aaa` )
    echo `bjobs -l $file >> result120`
    echo "loading"
end
### Get pattern in < >
awk '{\
gsub(/                     /,"",$0)}\
BEGIN {\
RS =""\
FS=","\
}\
{\
s=1\
e=150\
if ($1 ~/Job/){\
for(i=s;i<=e;i++){\
    printf("%s", $(i))}\
}\
}' result120 > result126
grep -oE '<[^>]+>' result126 > result125
### Get Current Work Location
awk '$1 ~ /<lsf_login..>/ {getline; print $1}' result125 >result122 #result127
### Get another information and paste it with CWD
foreach file1 ( `cat aaa` )
    echo `bjobs $file1 >> result128`
    echo "getting data"
end
awk '$1 ~ /JOBID/ {getline; printf "%-15s %-15s %-15s %-15s %-20s\n", $1, $2, $3, $4, $5}' result128 >> result129
paste result129 result122 >> output
### Summary
awk '{count1[$2]++}{count2[$4]++}{count3[$3]++}\
END{\
print "\n"\
print "##########################################################################"\
print "There are: ", NR " Jobs"\
for(name in count1){ print name, count1[name]}\
print "\n"\
for(queqe in count2){ print queqe, count2[queqe]}\
print "\n"\
for(stt in count3){ print stt, count3[stt]}\
}' output >> output
</code>```

And my desire is run it again per 15 minutes to get report. Someone told me use Wait but i've searched for it in man wait and can't find any
useful example. That's why i need yours help to solve this problem.
Thanks a lot.

答:
Following @karakfa answer, you have basically 2 options.

1) Your first option, even if you use a sleep implements a kind of busy-waiting strategy (https://en.wikipedia.org/wiki/Busy_waiting), this stragegy uses more CPU/memory than your second option (the cron approach) because you will have in memory your processus footprint even if it is actually doing nothing.

2) On the other hand, in the cron approach your processus will only appear while doing useful activities.

Just Imagine if you implement this kind of approach for many programs running on your machine, a lot of memory will be consume by processus in waiting states, it will also have an impact (memory/CPU usage) on the scheduling algorithm of your OS since it will have more processes in queue to manage.

Therefore, I would absolutely recommend the cron/scheduling approach.

Anyway,your cron daemon will be running in background whether you add the entry or not in the crontab, so why not adding it?

Last but not least, imagine if your busy-waiting processus is killed for any reason, if you go for the first option you will need to restart it manually and you might lose a couple of monitoring entries.

Hope it helps you.

Title: How can i repeat a script?

Body:
i've search for command or solution to repeat a script after n times but i can't find it.
This is my rusty script:

#!/bin/csh -f
rm -rf result120
rm -rf result127
rm -rf result126
rm -rf result125
rm -rf result128
rm -rf result129
rm -rf result122
rm -rf output
rm -rf aaa
### Get job id from user name
foreach file ( `cat name` )
        echo `bjobs -u $file | awk '$1 ~ /^[0-9]+/ {print $1}' >> aaa`
        echo "loading"
end
### Read in job id
foreach file ( `cat aaa` )
    echo `bjobs -l $file >> result120`
    echo "loading"
end
### Get pattern in < >
awk '{\
gsub(/                     /,"",$0)}\
BEGIN {\
RS =""\
FS=","\
}\
{\
s=1\
e=150\
if ($1 ~/Job/){\
for(i=s;i<=e;i++){\
    printf("%s", $(i))}\
}\
}' result120 > result126
grep -oE '<[^>]+>' result126 > result125
### Get Current Work Location
awk '$1 ~ /<lsf_login..>/ {getline; print $1}' result125 >result122 #result127
### Get another information and paste it with CWD
foreach file1 ( `cat aaa` )
    echo `bjobs $file1 >> result128`
    echo "getting data"
end
awk '$1 ~ /JOBID/ {getline; printf "%-15s %-15s %-15s %-15s %-20s\n", $1, $2, $3, $4, $5}' result128 >> result129
paste result129 result122 >> output
### Summary
awk '{count1[$2]++}{count2[$4]++}{count3[$3]++}\
END{\
print "\n"\
print "##########################################################################"\
print "There are: ", NR " Jobs"\
for(name in count1){ print name, count1[name]}\
print "\n"\
for(queqe in count2){ print queqe, count2[queqe]}\
print "\n"\
for(stt in count3){ print stt, count3[stt]}\
}' output >> output

And my desire is run it again per 15 minutes to get report. Someone told me use Wait but i've searched for it in man wait and can't find any
useful example. That's why i need yours help to solve this problem.
Thanks a lot.


问:
How to create a relationship between 2 nodes where the nodes' labels, properties and the relationship are variable using APOC
I'm having a really hard time querying Neo4j with Cypher and the APOC library. I've been recommended to use the APOC library a few days ago to create nodes with a label based on a variable. Creating these nodes works great, but a few days have past since and I still can't figure out how to create a relationship between these nodes.

The error messages I'm getting are the same as the ones I got before I started using APOC. The first character of the query is always seen as invalid input. Another one I have been getting is that the procedure call does not provide the required number of arguments.

I don't really understand the APOC documentation on how to create a relationship. I also tried CALL APOC.help('relationship') and saw that it's also possible to use apoc.merge. This can't be found in their documentation though. Furthermore I read about APOC's new summer release on Neo4J's blog, but I still really don't know how I can make this query work.

I've tried every possible tweak for the query I could think of, but the nodes just won't connect. I clearly don't know what I'm doing and missing out on something.

I really would like to be able to match 2 nodes and create a relationship between them. These nodes' labels and properties are variable since that's the way they were created. If possible, it would be great if the relationship type could be based on a variable too.

I'm working with NodeJS, the Neo4j driver and put the APOC Jar file succesfully in Neo4j's plugin folder.

Here's one of the failed queries to get an idea of what I'm trying to do:

```<code>('CALL apoc.create.relationship([{labelParamN1}], {name: {nameParamN1}}, {relationParam}, [{labelParamN2}], {name: {nameParamN2}})',
{labelParamN1: labelParamN1, nameParamN1: nameParamN1, labelParamN2: labelParamN2, nameParamN2: nameParamN2, relationParam: relation})
</code>```

Some help with this query would be really appreciated

答:
You first have to use MATCH to get the required nodes (n1 and n2), and then use the apoc.create.relationship method. Provided that you do want to add any properties on the relationships (and so you just pass {} for the third parameter), the following query should work:

```<code>MATCH (n1 {name: {nameParamN1}}), (n2 {name: {nameParamN2}})
CALL apoc.create.relationship(n1, {relationParam}, {}, n2)
YIELD rel
RETURN rel
</code>```

Body:
I'm having a really hard time querying Neo4j with Cypher and the APOC library. I've been recommended to use the APOC library a few days ago to create nodes with a label based on a variable. Creating these nodes works great, but a few days have past since and I still can't figure out how to create a relationship between these nodes.

The error messages I'm getting are the same as the ones I got before I started using APOC. The first character of the query is always seen as invalid input. Another one I have been getting is that the procedure call does not provide the required number of arguments.

I don't really understand the APOC documentation on how to create a relationship. I also tried CALL APOC.help('relationship') and saw that it's also possible to use apoc.merge. This can't be found in their documentation though. Furthermore I read about APOC's new summer release on Neo4J's blog, but I still really don't know how I can make this query work.

I've tried every possible tweak for the query I could think of, but the nodes just won't connect. I clearly don't know what I'm doing and missing out on something.

I really would like to be able to match 2 nodes and create a relationship between them. These nodes' labels and properties are variable since that's the way they were created. If possible, it would be great if the relationship type could be based on a variable too.

I'm working with NodeJS, the Neo4j driver and put the APOC Jar file succesfully in Neo4j's plugin folder.

Here's one of the failed queries to get an idea of what I'm trying to do:

('CALL apoc.create.relationship([{labelParamN1}], {name: {nameParamN1}}, {relationParam}, [{labelParamN2}], {name: {nameParamN2}})',
{labelParamN1: labelParamN1, nameParamN1: nameParamN1, labelParamN2: labelParamN2, nameParamN2: nameParamN2, relationParam: relation})

Some help with this query would be really appreciated

Body:
You first have to use MATCH to get the required nodes (n1 and n2), and then use the apoc.create.relationship method. Provided that you do want to add any properties on the relationships (and so you just pass {} for the third parameter), the following query should work:

MATCH (n1 {name: {nameParamN1}}), (n2 {name: {nameParamN2}})
CALL apoc.create.relationship(n1, {relationParam}, {}, n2)
YIELD rel
RETURN rel


问:
Making modular VBA function (MS Access)
I am writing up a simple multi-condition search form.
The Access VBA function set for the first toggle button looks like this:

```<code>Private Sub ToggleQ1_Click()
Select Case ToggleQ1.Value
    Case True
        CondQ1 = "AND"
        ToggleQ1.Caption = CondQ1
    Case False
        CondQ1 = "OR"
        ToggleQ1.Caption = CondQ1
End Select
End Sub
</code>```

ToggleQ1 = button's name

CondQ1 = variable to be used with a string to create conditional search.

It would likely be absurd to create 50 more of the same button code, differ only in its name (ex. "ToggleQ50" and "CondQ50")

Is there any way to make it modular and reusable?
Thank you very much in advance.

答:
Create another sub and send the clicked button to it. Similar to this:

```<code>Private Sub cmdTest01_Click()
    SetCaption cmdTest01
End Sub

Private Sub cmdTest02_Click()
    SetCaption cmdTest02
End Sub

Private Sub SetCaption(clickedButton As CommandButton)
    Dim CondQ1 As String

    Select Case clickedButton.Caption
        Case "Test01"
            CondQ1 = "AND"
            clickedButton.Caption = CondQ1
        Case "Test02"
            CondQ1 = "OR"
            clickedButton.Caption = CondQ1
     End Select
End Sub
</code>```

Case blocks can be simplified to

```<code>Case "Test01"
    clickedButton.Caption = "AND"
Case "Test02"
    clickedButton.Caption = "OR"
</code>```

Title: Making modular VBA function (MS Access)

Body:
I am writing up a simple multi-condition search form.
The Access VBA function set for the first toggle button looks like this:

Private Sub ToggleQ1_Click()
Select Case ToggleQ1.Value
    Case True
        CondQ1 = "AND"
        ToggleQ1.Caption = CondQ1
    Case False
        CondQ1 = "OR"
        ToggleQ1.Caption = CondQ1
End Select
End Sub

ToggleQ1 = button's name

CondQ1 = variable to be used with a string to create conditional search.

It would likely be absurd to create 50 more of the same button code, differ only in its name (ex. "ToggleQ50" and "CondQ50")

Is there any way to make it modular and reusable?
Thank you very much in advance.

Body:
Create another sub and send the clicked button to it. Similar to this:

Private Sub cmdTest01_Click()
    SetCaption cmdTest01
End Sub

Private Sub cmdTest02_Click()
    SetCaption cmdTest02
End Sub

Private Sub SetCaption(clickedButton As CommandButton)
    Dim CondQ1 As String

    Select Case clickedButton.Caption
        Case "Test01"
            CondQ1 = "AND"
            clickedButton.Caption = CondQ1
        Case "Test02"
            CondQ1 = "OR"
            clickedButton.Caption = CondQ1
     End Select
End Sub

Case blocks can be simplified to

Case "Test01"
    clickedButton.Caption = "AND"
Case "Test02"
    clickedButton.Caption = "OR"