Search code examples
pythonarrayslower-boundupperbound

Python: set lower- and upperbounds, remove them from array, and calculate the mean of new array


enter image description here

I need help to figure this out! I am pretty new to coding python. I have set in the print statement my upper and lower bounds to be 25 and 15, i have then tried to define 2 lines, that removes the number that exceeds the upperbound of is lower than the lowerbound everytime i run the code, i get the error:

"return umr_any(a, axis, dtype, out, keepdims)

TypeError: only integer scalar arrays can be converted to a scalar index"

I know there probably is a easier way to solve it, which I would love to know! but I also want this code to work, since I feel like I can learn a lot from it! thank you in advance!

here is the code:

import math 
import numpy as np
    
def fermentationRate(measuredRate, lowerBound, upperBound):
        def remove_values_from_list1(measuredRate, lowerBound):
            return [value for value in measuredRate if value < lowerBound]
    
        def remove_values_from_list2(measuredRate, upperbound):
            return [value for value in measuredRate if value > upperBound]
        x = np.array([measuredRate]) 
        for i in range(len(measuredRate)):
            if (x.any(x[i]) < lowerBound) and (x.any(x[i]) > upperBound):
                measuredRate = remove_values_from_list1(measuredrate,lowerBound)
                measuredRate = remove_values_from_list2(measuredrate,upperBound)
                averageRate = np.mean(measuredRate)
            else:
                averageRate = np.mean(measuredRate)
        return averageRate
    print(fermentationRate(np.array([20.1, 19.3, 1.1, 18.2, 19.7, 121.1, 20.3, 20.0]), 15, 25))

Solution

  • Since measuredRate is a numpy array, you don't need to iterate over it to find the locations that fulfil some condition.

    def fermentationRate(measuredRate, lowerBound, upperBound):
        # Create logical arrays containing True or False for both conditions
        condition1 = measuredRate >= lowerBound 
        condition2 = measuredRate <= upperBound 
        # logical_and the two: select the row if both conditions are true
        select_row = np.logical_and(condition1, condition2)
        filtered_array = measuredRate[select_row]
        return filtered_array.mean()
    

    Once you've understood this, it can be condensed down to a single line, although it's much less readable:

    def fermentationRate(measuredRate, lowerBound, upperBound):
        return measuredRate[
                   np.logical_and(measuredRate >= lowerBound, 
                                  measuredRate <= upperBound)
               ].mean()