Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

docs(blog): classification metrics on the backend #10501

Open
wants to merge 13 commits into
base: main
Choose a base branch
from

Conversation

IndexSeek
Copy link
Member

Description of changes

Adding a blog post breaking down how to perform binary classification metrics with Ibis. I did a fair amount of background explanation on these models and these metrics because many Ibis users may not be as familiar with these topics, but we can scale that back if needed and get more to the point.

@github-actions github-actions bot added the docs Documentation related issues or PRs label Nov 15, 2024
@deepyaman
Copy link
Contributor

Description of changes

Adding a blog post breaking down how to perform binary classification metrics with Ibis. I did a fair amount of background explanation on these models and these metrics because many Ibis users may not be as familiar with these topics, but we can scale that back if needed and get more to the point.

Seems like these would also be useful additions to IbisML! ibis_ml.metrics?

@cpcloud cpcloud added the docs-preview Add this label to trigger a docs preview label Nov 16, 2024
@ibis-docs-bot ibis-docs-bot bot removed the docs-preview Add this label to trigger a docs preview label Nov 16, 2024
@IndexSeek
Copy link
Member Author

Seems like these would also be useful additions to IbisML! ibis_ml.metrics?

I think so! I have given that a good bit of thought and I think it would be worth adding that capability with IbisML. I opened feat: ibis_ml.metrics #174 over there, so hopefully, we can discuss further and plan the approach.

Copy link
Contributor

@deepyaman deepyaman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Took a quick look. I personally like the detailed explanations; as you said, a lot of people may not have much ML exposure. I also think this is illustrative, but not necessarily efficient.

I'm guessing this should be a lot more efficient:

>>> tp = (t.actual * t.prediction).sum()
>>> tp
┌───┐
│ 4 │
└───┘
>>> fp = t.prediction.sum() - tp
>>> fp
┌───┐
│ 2 │
└───┘
>>> fn = t.actual.sum() - tp
>>> fn
┌───┐
│ 3 │
└───┘
>>> tn = t.actual.count() - tp - fp - fn
>>> tn
┌───┐
│ 3 │
└───┘

(I borrowed the logic from https://github.com/scikit-learn/scikit-learn/blob/a2448b5ce8778b76f8d8c6e7b0ef9b6cca9c7313/sklearn/metrics/_classification.py#L445, since I was too lazy to think it through myself.)

Since you do explicitly make a point about performance, maybe it makes sense to show the more efficient method after going through the illustrative labeling approach?

Edit: An alternative would be to just show the illustrative approach, add the efficient approach to IbisML, and call the IbisML function to demo the "efficient" path.

@IndexSeek
Copy link
Member Author

Thanks for the review and the feedback! I agree. The way you demonstrated calculating the true positives, false positives, etc., does seem much more efficient. It also demonstrates how we can break apart calculations and use them in other expressions with Ibis.

Since you do explicitly make a point about performance, maybe it makes sense to show the more efficient method after going through the illustrative labeling approach?

This is a great idea! The illustrative approach helps cement the concepts, and then the more efficient method would demonstrate assigning expressions as variables as using them in other expressions. Something that is far less convenient to do with pure SQL. I'm happy to incorporate this!

Edit: An alternative would be to just show the illustrative approach, add the efficient approach to IbisML, and call the IbisML function to demo the "efficient" path.

What if we added the above efficient approach to the article as it is now, I follow this up with another blog post on regression metrics. Then we have a third blog post to close out the series that throws back to the first two (e.g., we've previously reviewed and demonstrated how to calculate classification and regression metrics with Ibis, in this post, we'll demonstrate how we can perform these calculations out of the box with IbisML) so that we can tie it all together and create a nice mini series of blog posts.

@deepyaman
Copy link
Contributor

Edit: An alternative would be to just show the illustrative approach, add the efficient approach to IbisML, and call the IbisML function to demo the "efficient" path.

What if we added the above efficient approach to the article as it is now, I follow this up with another blog post on regression metrics. Then we have a third blog post to close out the series that throws back to the first two (e.g., we've previously reviewed and demonstrated how to calculate classification and regression metrics with Ibis, in this post, we'll demonstrate how we can perform these calculations out of the box with IbisML) so that we can tie it all together and create a nice mini series of blog posts.

Sounds good to me! From my perspective, part of seeing your posts is also an indicator of what, if anything, somebody may actually want to use Ibis for in the ML space. Happy to use the blogs as a leading indicator. :)

@IndexSeek
Copy link
Member Author

I just updated it to incorporate this approach. Thank you for sharing those snippets! Hopefully it flows well - I'm happy to adjust as necessary.

Comment on lines 194 to 199
t.select(
accuracy=accuracy_expr,
precision=precision_expr,
recall=recall_expr,
f1_score=f1_score_expr,
).limit(1)
Copy link
Member Author

@IndexSeek IndexSeek Nov 16, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a better way we could render these results? I was fiddling around with:

print(f"{accuracy_expr=}, {precision_expr=}, {recall_expr=}, {f1_score_expr=}")

But it wasn't rendering nicely.

image

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

.execute() should work (or .to_pyarrow().as_py() or some of the other .to_* export methods)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I ended up using to_pyarrow().as_py(). I suspect some readers may like to see that we can bring this to a Python object.

image

@deepyaman deepyaman added the docs-preview Add this label to trigger a docs preview label Nov 16, 2024
@ibis-docs-bot ibis-docs-bot bot removed the docs-preview Add this label to trigger a docs preview label Nov 16, 2024
Copy link
Contributor

@deepyaman deepyaman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added suggestions for the "efficient" paths, but I think for these there may be no meaningful difference if the computations are already warm on the backend? Probably something you could more easily test if you're interested; leave it up to you whether you want to use these shortcut formulas.

Copy link
Contributor

@deepyaman deepyaman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Some minor grammatical changes, but otherwise looks great to me!

---
title: "Classification metrics on the backend"
author: "Tyler White"
date: "2024-11-15"
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
date: "2024-11-15"
date: "2024-11-18"

I always forget to update the date, so leaving this out as a reminder to adjust this
when we are ready to merge. (Not saying it needs to be 2024-11-18 😄)

@IndexSeek
Copy link
Member Author

I'm ready to go with this one if we're good with it! (pending the date edit).

Thanks for your help and the thorough review @deepyaman, I think it greatly improves the post!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
docs Documentation related issues or PRs
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants