Counting things

I’m trying to count the occurrences of a value in a data table. Specifically, For a given type of furniture (“lounge chair”), I want to know how many times it occurs in an entire furniture catalog. To do this i thought to use a pandas dataframe, but it seems I am buggering up the server call. To wit:

@anvil.server.callable
def get_furniture_type_count(typename):
  a = app_tables.furniture.search(furniture_type=typename)
  df = pd.Dataframe(a)
  count = df.groupby('furniture_type').count
  return count

the variable typename is being passed in from a label as I attempt to set the text property:

  def furniture_quants_show (self, **event_args):
    # This method is called when the Label is shown on the screen
    self.furniture_quants.text = anvil.server.call('get_furniture_type_count', self.item['furniture_type_name'])

I’m receiving the error

tables.TableError: Column ‘furniture_type’ can only be searched with a Row from ‘furniture_types’ table (not a string) in table ‘furniture’

any tips on how to smooth this out?

1 Like

I’m guessing furniture_type is a link to another table (of furniture types?). If so, you can’t perform a string search on that, it will only take a furniture_type object.

You would need to look up “lounge chair” in the furniture_types table to get the row object, then use that to search the furniture table and get your quantity count.

Does that make sense?

(edit) - you might be able to combine the two searches, but I can’t think how right now - brain dead…

Yes you are correct about the table structure. I was trying to do it all in one search but i kept getting dizzy. I’ll try it with an additional search as you suggest.

@anvil.server.callable
def get_furniture_type_count(typename):
  a = app_tables.furniture.search(furniture_type=app_tables.furniture_types.get(furniture_type_name=typename))
  df = pd.Dataframe(a)
  count = df.groupby('furniture_type').count
  return count

ok, so i’m getting closer but not quite. The new error is:
tables.TableError: Column ‘furniture_type’ can only be searched with a liveObjectArray (not a Row from ‘furniture_types’ table) in table ‘furniture’

which is very curious, as the previous error was:

tables.TableError: Column ‘furniture_type’ can only be searched with a Row from ‘furniture_types’ table (not a string) in table ‘furniture’

Do you fancy sharing your app so i can clone it (either here or PM)?
Might be able to help more if i can see it running.

For anyone else watching - being sorted in PM and will post a précis here when concluded for others to reference.

Basically :

a=app_tables.furniture.search(
    furniture_type=app_tables.furniture_types.get(
        furniture_type_name=typename
    )
)

furniture[‘furniture_type’] is a many-row link to furniture_type table and therefore cannot be directly compared to the row. Converting this link to a single row fixes the issue but not confirmed yet as to whether this solves the OP’s problem.

Also, Pandas is a bit of overkill (I think) - you can just do :

return len(a)

as “a” will be an array of results.

furniture[‘furniture_type’] is a many-row link to furniture_type table and therefore cannot be directly compared to the row

FYI, you can search within many-row links by passing a list, like so:

type_row = app_tables.furniture_type.get(name='Chair')
all_chairs = app_tables.furniture.search(type=[type_row])
number_of_chairs = len(all_chairs) # this is an efficient query; table iterators support a fast `len()`
2 Likes

I was hoping you’d jump in with a solution to that :slight_smile:

That did the trick. Thanks David for taking a look, and thanks Merydydd for the insight.

1 Like

Here’s the working server function:

@anvil.server.callable
def get_furniture_type_count(typename):
  type_row = app_tables.furniture_types.get(furniture_type_name=typename)
  all_furniture_of_type = app_tables.furniture.search(furniture_type=[type_row])
  count_of_furniture_items_of_type = len(all_furniture_of_type)  
  return count_of_furniture_items_of_type
3 Likes

Argh!

I’m trying to count things in a data table and create a bar chart to show the number of the different things counted.

I’ve been through the plot dashboard tutorial now, so I can plot a chart from a simple number in a data table.

But I can’t work out how to extend that to include the step of counting the number of times a given category of thing is appearing in the table on top of turning it into a chart

Is there a tutorial that covers that anywhere?

Also I see in this thread that @steven.rowland has put his def get_furniture_type_count function in the server module, but why put it in server and not client side code?

Thank you anvil gurus.

Please show a minimal code example and describe the setup of your datatable.

One common reason would be security/access. Folks often don’t want to give the client full access to the backend database.

Thank you.

Does it help if I share the app?

https://anvil.works/build#clone:CE3OFH5ZVVR6VQSX=VJ4ZJGWYT4OM7F5BDULBOBMZ

Partly yes; however, it would help if you describe exactly what you are trying to count. Perhaps give an example of the expected output so that folks don’t have much guess work in terms of what you are looking for.

Thank you. I’m trying to count the number of things that are ‘green’ and ‘orange’
Then to create a bar graph that shows the total counts of each.

By things I think you mean rows from the Fruit table.

Let’s start with the counting issue. My suggestion would be to compare the solution above by Meredydd (and the last post from the OP) and figure out how to modify it to fit your data tables (they appear to be quite similar). You are basically trying to use a row from the “color” table as a search query for the “fruit” table. I believe the above solutions are doing just that (but using different table names of course).

Good luck, and feel free to post your code here and any error you get.

3 posts were split to a new topic: Missing 1 required positional argument

A post was split to a new topic: Improving code for counting things