Python Label Expression; Using multiple if's to label fields > 0

6220
13
Jump to solution
03-02-2015 08:39 AM
MCAGIS
by
New Contributor II

I've written this code, and the expression checks out, but it only labels the first field. Can someone tell me why it doesn't run through the rest of the if's to create a stacked label with field >0?

 

def FindLabel ( [Light_Numb], [IN_FDN] , [IN_35_FT_METAL_POST] , [IN_35_5] , [IN_40_5] , [IN_6_FT_ARM] , [IN_12_FT_ARM] , [IN_18_FT_ARM] , [IN_X_ARM] , [IN_LED_87W_OH] , [IN_LED_101W_OH] , [IN_LED_110W_OH] , [IN_LED_260W_OH] , [IN_LED_87W_UG] , [IN_LED_101W_UG] , [IN_LED_110W_UG] , [IN_LED_260W_UG] , [IN_PC] , [IN_SC] , [CONC_WORK_REQ_SQ_FT]  😞

 

 

try:

    if [Light_Numb] > 0:

        return [Light_Numb]

    '\n'

    if [In_FDN] > 0:

        return 'In FDN', [IN_FDN]

    '\n'

    if [IN_35_FT_METAL_POST] > 0:

        return 'IN 35 FT METAL POST', [IN_35_FT_METAL_POST]

    '\n'

    if [IN_35_5] > 0:

        return 'IN 35-5', [IN_35_5]

    '\n'

    if [IN_40_5] > 0:

        return 'IN 40-5', [IN_40_5]

    '\n'

    if [IN_6_FT_ARM] > 0:

        return 'IN 6 FT ARM', [IN_6_FT_ARM]

    '\n'

    if [IN_12_FT_ARM] > 0:

        return 'IN 12 FT ARM', [IN_12_FT_ARM]

    '\n'

    if [IN_18_FT_ARM] > 0:

        return 'IN_18 FT ARM', [IN_18_FT_ARM]

    '\n'

    if [IN_X_ARM] > 0:

        return 'IN X ARM', [IN_X_ARM]

    '\n'

    if [IN_LED_87W_OH] > 0:

        return 'IN LED 87W', [IN_LED_87W_OH]

    '\n'

    if [IN_LED_87W_UG] > 0:

        return 'IN LED 87W', [IN_LED_87W_UG]

    '\n'

    if [IN_LED_101W_OH] > 0:

        return 'IN LED 101W', [IN_LED_101W_OH]

    '\n'

    if [IN_LED_101W_UG] > 0:

        return 'IN LED 101W', [IN_LED_101W_UG]

    '\n'

    if [IN_LED_110W_OH] > 0:

        return 'IN LED 110W', [IN_LED_110W_OH]

    '\n'

    if [IN_LED_110W_UG] > 0:

        return 'IN LED 110W', [IN_LED_110W_UG]

    '\n'

    if [IN_LED_260W_OH] > 0:

        return 'IN LED 260W', [IN_LED_260W_OH]

    '\n'

    if [IN_LED_260W_UG] > 0:

        return 'IN LED 260W', [IN_LED_260W_UG]

    '\n'

    if [IN_PC] > 0:

        return 'IN PC', [IN_PC]

    '\n'

    if [IN_SC] > 0:

        return 'IN SC', [IN_SC]

    '\n'

    if [CONC_WORK_REQ_SQ_FT] > 0:

        return 'CONC WORK REQ SQFT', [CONC_WORK_REQ_SQ_FT]

except:

return 'None'

0 Kudos
1 Solution

Accepted Solutions
XanderBakker
Esri Esteemed Contributor

... and the '\n'  for a new line is not going to work either. Could you try this:

def FindLabel([Light_Numb], [IN_FDN], [IN_35_FT_METAL_POST] ,[IN_35_5], [IN_40_5],
              [IN_6_FT_ARM], [IN_12_FT_ARM], [IN_18_FT_ARM], [IN_X_ARM], [IN_LED_87W_OH],
              [IN_LED_101W_OH], [IN_LED_110W_OH], [IN_LED_260W_OH], [IN_LED_87W_UG],
              [IN_LED_101W_UG], [IN_LED_110W_UG], [IN_LED_260W_UG], [IN_PC],
              [IN_SC] , [CONC_WORK_REQ_SQ_FT]):

    label = ""
    try:
        if [Light_Numb] > 0:
            label += "{0}\n".format([Light_Numb])
        if [In_FDN] > 0:
            label += "In FDN {0}\n".format([IN_FDN])
        if [IN_35_FT_METAL_POST] > 0:
            label += "IN 35 FT METAL POST {0}\n".format([IN_35_FT_METAL_POST])
        if [IN_35_5] > 0:
            label += "IN 35-5 {0}\n".format([IN_35_5])
        if [IN_40_5] > 0:
            label += "IN 40-5 {0}\n".format([IN_40_5])
        if [IN_6_FT_ARM] > 0:
            label += "IN 6 FT ARM {0}\n".format([IN_6_FT_ARM])
        if [IN_12_FT_ARM] > 0:
            label += "IN 12 FT ARM {0}\n".format([IN_12_FT_ARM])
        if [IN_18_FT_ARM] > 0:
            label += "IN_18 FT ARM {0}\n".format([IN_18_FT_ARM])
        if [IN_X_ARM] > 0:
            label += "IN X ARM {0}\n".format([IN_X_ARM])
        if [IN_LED_87W_OH] > 0:
            label += "IN LED 87W {0}\n".format([IN_LED_87W_OH])
        if [IN_LED_87W_UG] > 0:
            label += "IN LED 87W {0}\n".format([IN_LED_87W_UG])
        if [IN_LED_101W_OH] > 0:
            label += "IN LED 101W {0}\n".format([IN_LED_101W_OH])
        if [IN_LED_101W_UG] > 0:
            label += "IN LED 101W {0}\n".format([IN_LED_101W_UG])
        if [IN_LED_110W_OH] > 0:
            label += "IN LED 110W {0}\n".format([IN_LED_110W_OH])
        if [IN_LED_110W_UG] > 0:
            label += "IN LED 110W {0}\n".format([IN_LED_110W_UG])
        if [IN_LED_260W_OH] > 0:
            label += "IN LED 260W {0}\n".format([IN_LED_260W_OH])
        if [IN_LED_260W_UG] > 0:
            label += "IN LED 260W {0}\n".format([IN_LED_260W_UG])
        if [IN_PC] > 0:
            label += "IN PC {0}\n".format([IN_PC])
        if [IN_SC] > 0:
            label += "IN SC {0}\n".format([IN_SC])
        if [CONC_WORK_REQ_SQ_FT] > 0:
            label += "CONC WORK REQ SQFT {0}\n".format([CONC_WORK_REQ_SQ_FT])
        return label
    except:
        return 'None'

Please use syntax highlighting for your code (see: Posting Code blocks in the new GeoNet )

View solution in original post

13 Replies
JoshuaBixby
MVP Esteemed Contributor

It is because you are returning with each if statement.  Once the first if condition is met, the code will build that label and exit the function.

MCAGIS
by
New Contributor II

I tried to insert a 'While' statement above the if's?

eg...

While [Light_Numb] > 0:

then proceed with all of the if statements. it still only give me the first if statement in the label.

Any specific solutions?

0 Kudos
JoshuaBixby
MVP Esteemed Contributor

I see you made progress with Xander Bakker​'s code, glad he was able to help and provide some additional learning links.  Beyond what has already been said, I will just point out that Python functions with 15+ parameters are quite rare, even 10 is unusual.  And, they are all required arguments!  In cases like this, usually the code can benefit from being restructured.  If all of these arguments have to be passed, maybe just building a list or dictionary and passing it as a single argument would make sense.

XanderBakker
Esri Esteemed Contributor

... and the '\n'  for a new line is not going to work either. Could you try this:

def FindLabel([Light_Numb], [IN_FDN], [IN_35_FT_METAL_POST] ,[IN_35_5], [IN_40_5],
              [IN_6_FT_ARM], [IN_12_FT_ARM], [IN_18_FT_ARM], [IN_X_ARM], [IN_LED_87W_OH],
              [IN_LED_101W_OH], [IN_LED_110W_OH], [IN_LED_260W_OH], [IN_LED_87W_UG],
              [IN_LED_101W_UG], [IN_LED_110W_UG], [IN_LED_260W_UG], [IN_PC],
              [IN_SC] , [CONC_WORK_REQ_SQ_FT]):

    label = ""
    try:
        if [Light_Numb] > 0:
            label += "{0}\n".format([Light_Numb])
        if [In_FDN] > 0:
            label += "In FDN {0}\n".format([IN_FDN])
        if [IN_35_FT_METAL_POST] > 0:
            label += "IN 35 FT METAL POST {0}\n".format([IN_35_FT_METAL_POST])
        if [IN_35_5] > 0:
            label += "IN 35-5 {0}\n".format([IN_35_5])
        if [IN_40_5] > 0:
            label += "IN 40-5 {0}\n".format([IN_40_5])
        if [IN_6_FT_ARM] > 0:
            label += "IN 6 FT ARM {0}\n".format([IN_6_FT_ARM])
        if [IN_12_FT_ARM] > 0:
            label += "IN 12 FT ARM {0}\n".format([IN_12_FT_ARM])
        if [IN_18_FT_ARM] > 0:
            label += "IN_18 FT ARM {0}\n".format([IN_18_FT_ARM])
        if [IN_X_ARM] > 0:
            label += "IN X ARM {0}\n".format([IN_X_ARM])
        if [IN_LED_87W_OH] > 0:
            label += "IN LED 87W {0}\n".format([IN_LED_87W_OH])
        if [IN_LED_87W_UG] > 0:
            label += "IN LED 87W {0}\n".format([IN_LED_87W_UG])
        if [IN_LED_101W_OH] > 0:
            label += "IN LED 101W {0}\n".format([IN_LED_101W_OH])
        if [IN_LED_101W_UG] > 0:
            label += "IN LED 101W {0}\n".format([IN_LED_101W_UG])
        if [IN_LED_110W_OH] > 0:
            label += "IN LED 110W {0}\n".format([IN_LED_110W_OH])
        if [IN_LED_110W_UG] > 0:
            label += "IN LED 110W {0}\n".format([IN_LED_110W_UG])
        if [IN_LED_260W_OH] > 0:
            label += "IN LED 260W {0}\n".format([IN_LED_260W_OH])
        if [IN_LED_260W_UG] > 0:
            label += "IN LED 260W {0}\n".format([IN_LED_260W_UG])
        if [IN_PC] > 0:
            label += "IN PC {0}\n".format([IN_PC])
        if [IN_SC] > 0:
            label += "IN SC {0}\n".format([IN_SC])
        if [CONC_WORK_REQ_SQ_FT] > 0:
            label += "CONC WORK REQ SQFT {0}\n".format([CONC_WORK_REQ_SQ_FT])
        return label
    except:
        return 'None'

Please use syntax highlighting for your code (see: Posting Code blocks in the new GeoNet )

MCAGIS
by
New Contributor II

Ah, man that actually works pretty well. trying to transition from regular .py to arc.py is difficult. I need to learn the arc.py functions I guess....

Anyone have suggestions on the best way to do this? book, online class, etc...

Thanks Xander!

0 Kudos
XanderBakker
Esri Esteemed Contributor

I can point you to two threads were quite some suggestions are made for learning Python:

Seeking advice on how to go about learning Python

Learning Python

You can also have a look at my blog Some Python Snippets 

In case you know Python and want to learn arcpy, then the Help is a very values resource: ArcGIS Help (10.2, 10.2.1, and 10.2.2)

And also these posts are worth mentioning:

python - What are some resources for learning ArcPy? - Geographic Information Systems Stack Exchange

Seven easy ways to start learning Python and ArcPy | Support Services Blog  (point 6 and 7)

DavidFox
New Contributor III

I have a similar labeling problem and thought this code would help but it does not do what I thought it would. Here is my label expression:

def FindLabel ( [stand_code], [Avg_TPA_Pine], [Avg_TPA_Cyp], [Avg_TPA_Hdwd] 😞

     label = ""

     try:

          if [Avg_TPA_Pine] > 0:

               label += "TPA P: " + [Avg_TPA_Pine] + " / "

          if [Avg_TPA_Cyp] > 0:

               label += "TPA C: " + [Avg_TPA_Cyp] + " / "

          if [Avg_TPA_Hdwd] > 0:

               label += "TPA H: " + [Avg_TPA_Hdwd]

          return [stand_code]+ '\n'+ label

     except:

          return  [stand_code]

I thought this would add the data to a label only if the value of the field was > 0.

A typical label might look like:

SLn1937f

TPA P: 158.8 / TPA C: 14.1 / TPA H: 9.4

However, if any of the values on the second line are 0, they should not appear, like:

CYns

TPA C: 200

And a label with 0 values for all three fields should look like:

NT

Instead, this code creates labels that include the 0 values, like:

NT

TPA P: 0 / TPA C: 0 / TPA H: 0

What am I missing? Thanks,

Dave

0 Kudos
JoshuaBixby
MVP Esteemed Contributor

For starters, something is off with the code you posted here because having square brackets around your parameters in the function definition is invalid.  Also, do you mean to be turning all of your variables into lists before checking them?  For example;

>>> zero = 0
>>> [zero] > 0
True
>>>

The code, as written, is comparing a list with one element to an integer.  It is important to note the list itself is being compared, not the first element in the list.

Another issue could be how you are concatenating the strings.  Are you passing strings or numbers to this function?  If numbers, your string concatenations will generate a TypeError.

Try the following, it assumes the last 3 parameters are numbers.  If the last 3 are strings, some changes would have to be made:

def FindLabel ( stand_code, Avg_TPA_Pine, Avg_TPA_Cyp, Avg_TPA_Hdwd ):
    label = ""
    try:
          if Avg_TPA_Pine > 0:
              label += "TPA P: " + str(Avg_TPA_Pine) + " / "
          if Avg_TPA_Cyp > 0:
              label += "TPA C: " + str(Avg_TPA_Cyp) + " / "
          if Avg_TPA_Hdwd > 0:
              label += "TPA H: " + str(Avg_TPA_Hdwd)
          return str(stand_code) + '\n'+ label
    except:
          return  str(stand_code)
0 Kudos
DavidFox
New Contributor III

Thanks Joshua but your code returns multiple errors.

Mine was written using the label expression builder and produces labels that look like this with no errors:map_label_Capture.JPG

However, as you can see, the red underlined label portions contain zero values. I want that portion of the label (everything between the /  / ) to not show up if the value is zero. So, the NT label would show only that and the second line would not appear while the CYns label second line would only show TPA P: 40 / TPA H: 40 and the SLp1966f second line would show TPA P: 256  ... Hope that makes sense. Thanks for your time.

Dave

0 Kudos