From a86c32c902f63a44a8ed80deaabb04e6c0ac2402 Mon Sep 17 00:00:00 2001 From: Ritu Singh Date: Tue, 24 Mar 2026 01:45:32 -0700 Subject: [PATCH 1/2] fixing typeerrors addresses Trusted-AI/AIF360/issues/560 Signed-off-by: Ritu Singh Signed-off-by: RituSinghme --- .../algorithms/preprocessing/optim_preproc.py | 2 +- aif360/datasets/regression_dataset.py | 3 +- aif360/datasets/standard_dataset.py | 8 +- aif360/metrics/binary_label_dataset_metric.py | 2 +- aif360/sklearn/detectors/facts/clean.py | 7 +- aif360/sklearn/postprocessing/__init__.py | 23 +- examples/demo_lfr.ipynb | 228 +++++------------- 7 files changed, 87 insertions(+), 186 deletions(-) diff --git a/aif360/algorithms/preprocessing/optim_preproc.py b/aif360/algorithms/preprocessing/optim_preproc.py index 7c00f296..7a1753e0 100644 --- a/aif360/algorithms/preprocessing/optim_preproc.py +++ b/aif360/algorithms/preprocessing/optim_preproc.py @@ -162,7 +162,7 @@ def transform(self, dataset, sep='=', transform_Y=True): if transform_Y: # randomized mapping when Y is requested to be transformed - dfP_withY = self.OpT.dfP.applymap(lambda x: 0 if x < 1e-8 else x) + dfP_withY = self.OpT.dfP.map(lambda x: 0 if x < 1e-8 else x) dfP_withY = dfP_withY.divide(dfP_withY.sum(axis=1), axis=0) df_transformed = _apply_randomized_mapping(df, dfP_withY, diff --git a/aif360/datasets/regression_dataset.py b/aif360/datasets/regression_dataset.py index 8a549df1..8f33daa0 100644 --- a/aif360/datasets/regression_dataset.py +++ b/aif360/datasets/regression_dataset.py @@ -81,13 +81,14 @@ def __init__(self, df, dep_var_name, protected_attribute_names, unprivileged_values = [0.] if callable(vals): df[attr] = df[attr].apply(vals) - elif np.issubdtype(df[attr].dtype, np.number): + elif pd.api.types.is_numeric_dtype(df[attr]): # this attribute is numeric; no remapping needed privileged_values = vals unprivileged_values = list(set(df[attr]).difference(vals)) else: # find all instances which match any of the attribute values priv = np.logical_or.reduce(np.equal.outer(vals, df[attr].to_numpy())) + df[attr] = df[attr].astype(object) df.loc[priv, attr] = privileged_values[0] df.loc[~priv, attr] = unprivileged_values[0] diff --git a/aif360/datasets/standard_dataset.py b/aif360/datasets/standard_dataset.py index d7c0eeb3..f106fac9 100644 --- a/aif360/datasets/standard_dataset.py +++ b/aif360/datasets/standard_dataset.py @@ -112,13 +112,14 @@ def __init__(self, df, label_name, favorable_classes, unprivileged_values = [0.] if callable(vals): df[attr] = df[attr].apply(vals) - elif np.issubdtype(df[attr].dtype, np.number): + elif pd.api.types.is_numeric_dtype(df[attr]): # this attribute is numeric; no remapping needed privileged_values = vals unprivileged_values = list(set(df[attr]).difference(vals)) else: # find all instances which match any of the attribute values priv = np.logical_or.reduce(np.equal.outer(vals, df[attr].to_numpy())) + df[attr] = df[attr].astype(object) df.loc[priv, attr] = privileged_values[0] df.loc[~priv, attr] = unprivileged_values[0] @@ -132,14 +133,15 @@ def __init__(self, df, label_name, favorable_classes, unfavorable_label = 0. if callable(favorable_classes): df[label_name] = df[label_name].apply(favorable_classes) - elif np.issubdtype(df[label_name], np.number) and len(set(df[label_name])) == 2: + elif pd.api.types.is_numeric_dtype(df[label_name]) and len(set(df[label_name])) == 2: # labels are already binary; don't change them favorable_label = favorable_classes[0] unfavorable_label = set(df[label_name]).difference(favorable_classes).pop() else: # find all instances which match any of the favorable classes - pos = np.logical_or.reduce(np.equal.outer(favorable_classes, + pos = np.logical_or.reduce(np.equal.outer(favorable_classes, df[label_name].to_numpy())) + df[label_name] = df[label_name].astype(object) df.loc[pos, label_name] = favorable_label df.loc[~pos, label_name] = unfavorable_label diff --git a/aif360/metrics/binary_label_dataset_metric.py b/aif360/metrics/binary_label_dataset_metric.py index b3b25df5..82f715a4 100644 --- a/aif360/metrics/binary_label_dataset_metric.py +++ b/aif360/metrics/binary_label_dataset_metric.py @@ -154,7 +154,7 @@ def consistency(self, n_neighbors=5): consistency += np.abs(y[i] - np.mean(y[indices[i]])) consistency = 1.0 - consistency/num_samples - return consistency + return np.asarray(consistency).item() def _smoothed_base_rates(self, labels, concentration=1.0): """Dirichlet-smoothed base rates for each intersecting group in the diff --git a/aif360/sklearn/detectors/facts/clean.py b/aif360/sklearn/detectors/facts/clean.py index 40bd529a..dbb2539d 100644 --- a/aif360/sklearn/detectors/facts/clean.py +++ b/aif360/sklearn/detectors/facts/clean.py @@ -26,7 +26,7 @@ def strip_str(x): return x.strip() else: return x - X = X.applymap(strip_str) + X = X.map(strip_str) X["relationship"] = X["relationship"].replace(["Husband", "Wife"], "Married") X["hours-per-week"] = pd.cut( x=X["hours-per-week"], @@ -81,9 +81,8 @@ def clean_compas(X: DataFrame) -> DataFrame: X = X.reset_index(drop=True) X = X.drop(columns=["age", "c_charge_desc"]) X["priors_count"] = pd.cut(X["priors_count"], [-0.1, 1, 5, 10, 15, 38]) - X.target.replace("Recidivated", 0, inplace=True) - X.target.replace("Survived", 1, inplace=True) - X["age_cat"].replace("Less than 25", "10-25", inplace=True) + X["target"] = X["target"].replace("Recidivated", 0).replace("Survived", 1) + X["age_cat"] = X["age_cat"].replace("Less than 25", "10-25") return X diff --git a/aif360/sklearn/postprocessing/__init__.py b/aif360/sklearn/postprocessing/__init__.py index b80719ea..18ee5c3a 100644 --- a/aif360/sklearn/postprocessing/__init__.py +++ b/aif360/sklearn/postprocessing/__init__.py @@ -13,6 +13,19 @@ from aif360.sklearn.postprocessing.reject_option_classification import RejectOptionClassifier, RejectOptionClassifierCV +def _get_requires_proba(postprocessor): + """Get requires_proba tag compatible with sklearn < 1.6 and >= 1.6. + + sklearn 1.6 removed _get_tags() from BaseEstimator; fall back to + _more_tags() which is still present. + """ + if hasattr(postprocessor, '_get_tags'): + return postprocessor._get_tags().get('requires_proba', False) + if hasattr(postprocessor, '_more_tags'): + return postprocessor._more_tags().get('requires_proba', False) + return False + + class PostProcessingMeta(BaseEstimator, MetaEstimatorMixin): """A meta-estimator which wraps a given estimator with a post-processing step. @@ -85,7 +98,7 @@ def fit(self, X, y, sample_weight=None, **fit_params): self.estimator_ = self.estimator if self.prefit else clone(self.estimator) try: - use_proba = self.postprocessor._get_tags()['requires_proba'] + use_proba = _get_requires_proba(self.postprocessor) except KeyError: raise TypeError("`postprocessor` (type: {}) does not have a " "'requires_proba' tag.".format(type(self.estimator))) @@ -145,7 +158,7 @@ def predict(self, X): Returns: numpy.ndarray: Predicted class label per sample. """ - use_proba = self.postprocessor_._get_tags()['requires_proba'] + use_proba = _get_requires_proba(self.postprocessor_) y_score = (self.estimator_.predict_proba(X) if use_proba else self.estimator_.predict(X)) y_score = pd.DataFrame(y_score, index=X.index).squeeze('columns') @@ -169,7 +182,7 @@ def predict_proba(self, X): in the model, where classes are ordered as they are in ``self.classes_``. """ - use_proba = self.postprocessor_._get_tags()['requires_proba'] + use_proba = _get_requires_proba(self.postprocessor_) y_score = (self.estimator_.predict_proba(X) if use_proba else self.estimator_.predict(X)) y_score = pd.DataFrame(y_score, index=X.index).squeeze('columns') @@ -193,7 +206,7 @@ def predict_log_proba(self, X): the model, where classes are ordered as they are in ``self.classes_``. """ - use_proba = self.postprocessor_._get_tags()['requires_proba'] + use_proba = _get_requires_proba(self.postprocessor_) y_score = (self.estimator_.predict_proba(X) if use_proba else self.estimator_.predict(X)) y_score = pd.DataFrame(y_score, index=X.index).squeeze('columns') @@ -216,7 +229,7 @@ def score(self, X, y, sample_weight=None): Returns: float: Score value. """ - use_proba = self.postprocessor_._get_tags()['requires_proba'] + use_proba = _get_requires_proba(self.postprocessor_) y_score = (self.estimator_.predict_proba(X) if use_proba else self.estimator_.predict(X)) y_score = pd.DataFrame(y_score, index=X.index).squeeze('columns') diff --git a/examples/demo_lfr.ipynb b/examples/demo_lfr.ipynb index 134a2729..327266b7 100644 --- a/examples/demo_lfr.ipynb +++ b/examples/demo_lfr.ipynb @@ -17,7 +17,18 @@ "cell_type": "code", "execution_count": 1, "metadata": {}, - "outputs": [], + "outputs": [ + { + "name": "stderr", + "output_type": "stream", + "text": [ + "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/inFairness/utils/ndcg.py:37: FutureWarning: We've integrated functorch into PyTorch. As the final step of the integration, `functorch.vmap` is deprecated as of PyTorch 2.0 and will be deleted in a future version of PyTorch >= 2.3. Please use `torch.vmap` instead; see the PyTorch 2.0 release notes and/or the `torch.func` migration guide for more details https://pytorch.org/docs/main/func.migrating.html\n", + " vect_normalized_discounted_cumulative_gain = vmap(\n", + "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/inFairness/utils/ndcg.py:48: FutureWarning: We've integrated functorch into PyTorch. As the final step of the integration, `functorch.vmap` is deprecated as of PyTorch 2.0 and will be deleted in a future version of PyTorch >= 2.3. Please use `torch.vmap` instead; see the PyTorch 2.0 release notes and/or the `torch.func` migration guide for more details https://pytorch.org/docs/main/func.migrating.html\n", + " monte_carlo_vect_ndcg = vmap(vect_normalized_discounted_cumulative_gain, in_dims=(0,))\n" + ] + } + ], "source": [ "%matplotlib inline\n", "# Load all necessary packages\n", @@ -55,121 +66,60 @@ "cell_type": "code", "execution_count": 2, "metadata": {}, - "outputs": [], - "source": [ - "# Get the dataset and split into train and test\n", - "dataset_orig = load_preproc_data_adult()\n", - "dataset_orig_train, dataset_orig_test = dataset_orig.split([0.7], shuffle=True)" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "#### Clean up training data" - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "metadata": {}, "outputs": [ - { - "data": { - "text/markdown": [ - "#### Training Dataset shape" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, { "name": "stdout", "output_type": "stream", "text": [ - "(34189, 18)\n" + "IOError: [Errno 2] No such file or directory: '/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/aif360/datasets/../data/raw/adult/adult.data'\n", + "To use this class, please download the following files:\n", + "\n", + "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.data\n", + "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.test\n", + "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.names\n", + "\n", + "and place them, as-is, in the folder:\n", + "\n", + "\t/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/aif360/data/raw/adult\n", + "\n" ] }, { - "data": { - "text/markdown": [ - "#### Favorable and unfavorable labels" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", - "output_type": "stream", - "text": [ - "1.0 0.0\n" + "ename": "SystemExit", + "evalue": "1", + "output_type": "error", + "traceback": [ + "An exception has occurred, use %tb to see the full traceback.\n", + "\u001b[31mSystemExit\u001b[39m\u001b[31m:\u001b[39m 1\n" ] }, { - "data": { - "text/markdown": [ - "#### Protected attribute names" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", + "name": "stderr", "output_type": "stream", "text": [ - "['sex', 'race']\n" - ] - }, - { - "data": { - "text/markdown": [ - "#### Privileged and unprivileged protected attribute values" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", - "output_type": "stream", - "text": [ - "[array([1.]), array([1.])] [array([0.]), array([0.])]\n" - ] - }, - { - "data": { - "text/markdown": [ - "#### Dataset feature names" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", - "output_type": "stream", - "text": [ - "['race', 'sex', 'Age (decade)=10', 'Age (decade)=20', 'Age (decade)=30', 'Age (decade)=40', 'Age (decade)=50', 'Age (decade)=60', 'Age (decade)=>=70', 'Education Years=6', 'Education Years=7', 'Education Years=8', 'Education Years=9', 'Education Years=10', 'Education Years=11', 'Education Years=12', 'Education Years=<6', 'Education Years=>12']\n" + "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/IPython/core/interactiveshell.py:3709: UserWarning: To exit: use 'exit', 'quit', or Ctrl-D.\n", + " warn(\"To exit: use 'exit', 'quit', or Ctrl-D.\", stacklevel=1)\n" ] } ], + "source": [ + "# Get the dataset and split into train and test\n", + "dataset_orig = load_preproc_data_adult()\n", + "dataset_orig_train, dataset_orig_test = dataset_orig.split([0.7], shuffle=True)" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "#### Clean up training data" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], "source": [ "# print out some labels, names, etc.\n", "display(Markdown(\"#### Training Dataset shape\"))\n", @@ -194,48 +144,9 @@ }, { "cell_type": "code", - "execution_count": 4, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "data": { - "text/markdown": [ - "#### Original training dataset" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Difference in mean outcomes between unprivileged and privileged groups = -0.193139\n" - ] - }, - { - "data": { - "text/markdown": [ - "#### Original test dataset" - ], - "text/plain": [ - "" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Difference in mean outcomes between unprivileged and privileged groups = -0.197697\n" - ] - } - ], + "outputs": [], "source": [ "# Metric for the original dataset\n", "privileged_groups = [{'sex': 1.0}]\n", @@ -262,7 +173,7 @@ }, { "cell_type": "code", - "execution_count": 5, + "execution_count": null, "metadata": {}, "outputs": [], "source": [ @@ -275,32 +186,7 @@ "cell_type": "code", "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "step: 0, loss: 1.0939550595829053, L_x: 2.531834521858599, L_y: 0.8200826015334493, L_z: 0.010344502931797964\n", - "step: 250, loss: 0.9162820270109503, L_x: 2.529109218043187, L_y: 0.6432961063010657, L_z: 0.010037499452782905\n", - "step: 500, loss: 0.8207071510514392, L_x: 2.5204911168067197, L_y: 0.5500397646035967, L_z: 0.00930913738358528\n", - "step: 750, loss: 0.8102771268166408, L_x: 2.511873834704061, L_y: 0.5427956868742799, L_z: 0.008147028235977415\n", - "step: 1000, loss: 0.7996570283329768, L_x: 2.480828451323288, L_y: 0.5399446552800813, L_z: 0.00581476396028337\n", - "step: 1250, loss: 0.7844631169970814, L_x: 2.4242508289183613, L_y: 0.5304307199052671, L_z: 0.005803657099989009\n", - "step: 1500, loss: 0.7653305722023572, L_x: 2.3297047767431986, L_y: 0.5176248867874912, L_z: 0.007367603870273078\n", - "step: 1750, loss: 0.7154304631442515, L_x: 2.085955877234543, L_y: 0.48081670080967953, L_z: 0.013009087305558827\n", - "step: 2000, loss: 0.6906420918886886, L_x: 1.896344106091722, L_y: 0.4646651544564373, L_z: 0.018171263411539594\n", - "step: 2250, loss: 0.6783680937630076, L_x: 1.7895665853948028, L_y: 0.4587714378849466, L_z: 0.020319998669290275\n", - "step: 2500, loss: 0.6725576747654705, L_x: 1.742061633693402, L_y: 0.4577729094336143, L_z: 0.020289300981257967\n", - "step: 2750, loss: 0.6694103860159343, L_x: 1.7548885984309939, L_y: 0.4545867175857845, L_z: 0.019667404293525217\n", - "step: 3000, loss: 0.6658207636894926, L_x: 1.7515234617350093, L_y: 0.4539151313299769, L_z: 0.018376643093007367\n", - "step: 3250, loss: 0.6481415219979564, L_x: 1.7252276686316934, L_y: 0.4491717858033674, L_z: 0.013223484665709846\n", - "step: 3500, loss: 0.645366243737316, L_x: 1.7196207136719521, L_y: 0.4482843307446003, L_z: 0.012559920812760247\n", - "step: 3750, loss: 0.6425278186287126, L_x: 1.7117758355776211, L_y: 0.4473063883366716, L_z: 0.012021923367139413\n", - "step: 4000, loss: 0.6419409673076768, L_x: 1.7092609385556714, L_y: 0.44744616781598634, L_z: 0.011784352818061686\n", - "step: 4250, loss: 0.6377801462539607, L_x: 1.6917081956472533, L_y: 0.4496335370425122, L_z: 0.009487894823361622\n" - ] - } - ], + "outputs": [], "source": [ "# Input recontruction quality - Ax\n", "# Fairness constraint - Az\n", @@ -451,7 +337,7 @@ ], "metadata": { "kernelspec": { - "display_name": "Python 3", + "display_name": "Python 3 (ipykernel)", "language": "python", "name": "python3" }, @@ -465,9 +351,9 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.6.10" + "version": "3.11.15" } }, "nbformat": 4, - "nbformat_minor": 2 + "nbformat_minor": 4 } From 74c767c2d0a48332cf754147f100234d61db320d Mon Sep 17 00:00:00 2001 From: Ritu Singh Date: Tue, 24 Mar 2026 02:11:03 -0700 Subject: [PATCH 2/2] rollback changes in notebook Signed-off-by: Ritu Singh Signed-off-by: RituSinghme --- examples/demo_lfr.ipynb | 228 ++++++++++++++++++++++++++++++---------- 1 file changed, 171 insertions(+), 57 deletions(-) diff --git a/examples/demo_lfr.ipynb b/examples/demo_lfr.ipynb index 327266b7..134a2729 100644 --- a/examples/demo_lfr.ipynb +++ b/examples/demo_lfr.ipynb @@ -17,18 +17,7 @@ "cell_type": "code", "execution_count": 1, "metadata": {}, - "outputs": [ - { - "name": "stderr", - "output_type": "stream", - "text": [ - "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/inFairness/utils/ndcg.py:37: FutureWarning: We've integrated functorch into PyTorch. As the final step of the integration, `functorch.vmap` is deprecated as of PyTorch 2.0 and will be deleted in a future version of PyTorch >= 2.3. Please use `torch.vmap` instead; see the PyTorch 2.0 release notes and/or the `torch.func` migration guide for more details https://pytorch.org/docs/main/func.migrating.html\n", - " vect_normalized_discounted_cumulative_gain = vmap(\n", - "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/inFairness/utils/ndcg.py:48: FutureWarning: We've integrated functorch into PyTorch. As the final step of the integration, `functorch.vmap` is deprecated as of PyTorch 2.0 and will be deleted in a future version of PyTorch >= 2.3. Please use `torch.vmap` instead; see the PyTorch 2.0 release notes and/or the `torch.func` migration guide for more details https://pytorch.org/docs/main/func.migrating.html\n", - " monte_carlo_vect_ndcg = vmap(vect_normalized_discounted_cumulative_gain, in_dims=(0,))\n" - ] - } - ], + "outputs": [], "source": [ "%matplotlib inline\n", "# Load all necessary packages\n", @@ -66,42 +55,7 @@ "cell_type": "code", "execution_count": 2, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "IOError: [Errno 2] No such file or directory: '/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/aif360/datasets/../data/raw/adult/adult.data'\n", - "To use this class, please download the following files:\n", - "\n", - "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.data\n", - "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.test\n", - "\thttps://archive.ics.uci.edu/ml/machine-learning-databases/adult/adult.names\n", - "\n", - "and place them, as-is, in the folder:\n", - "\n", - "\t/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/aif360/data/raw/adult\n", - "\n" - ] - }, - { - "ename": "SystemExit", - "evalue": "1", - "output_type": "error", - "traceback": [ - "An exception has occurred, use %tb to see the full traceback.\n", - "\u001b[31mSystemExit\u001b[39m\u001b[31m:\u001b[39m 1\n" - ] - }, - { - "name": "stderr", - "output_type": "stream", - "text": [ - "/opt/homebrew/Caskroom/miniconda/base/envs/aif360/lib/python3.11/site-packages/IPython/core/interactiveshell.py:3709: UserWarning: To exit: use 'exit', 'quit', or Ctrl-D.\n", - " warn(\"To exit: use 'exit', 'quit', or Ctrl-D.\", stacklevel=1)\n" - ] - } - ], + "outputs": [], "source": [ "# Get the dataset and split into train and test\n", "dataset_orig = load_preproc_data_adult()\n", @@ -117,9 +71,105 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 3, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "text/markdown": [ + "#### Training Dataset shape" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "(34189, 18)\n" + ] + }, + { + "data": { + "text/markdown": [ + "#### Favorable and unfavorable labels" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "1.0 0.0\n" + ] + }, + { + "data": { + "text/markdown": [ + "#### Protected attribute names" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "['sex', 'race']\n" + ] + }, + { + "data": { + "text/markdown": [ + "#### Privileged and unprivileged protected attribute values" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[array([1.]), array([1.])] [array([0.]), array([0.])]\n" + ] + }, + { + "data": { + "text/markdown": [ + "#### Dataset feature names" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "['race', 'sex', 'Age (decade)=10', 'Age (decade)=20', 'Age (decade)=30', 'Age (decade)=40', 'Age (decade)=50', 'Age (decade)=60', 'Age (decade)=>=70', 'Education Years=6', 'Education Years=7', 'Education Years=8', 'Education Years=9', 'Education Years=10', 'Education Years=11', 'Education Years=12', 'Education Years=<6', 'Education Years=>12']\n" + ] + } + ], "source": [ "# print out some labels, names, etc.\n", "display(Markdown(\"#### Training Dataset shape\"))\n", @@ -144,9 +194,48 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 4, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "text/markdown": [ + "#### Original training dataset" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Difference in mean outcomes between unprivileged and privileged groups = -0.193139\n" + ] + }, + { + "data": { + "text/markdown": [ + "#### Original test dataset" + ], + "text/plain": [ + "" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Difference in mean outcomes between unprivileged and privileged groups = -0.197697\n" + ] + } + ], "source": [ "# Metric for the original dataset\n", "privileged_groups = [{'sex': 1.0}]\n", @@ -173,7 +262,7 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 5, "metadata": {}, "outputs": [], "source": [ @@ -186,7 +275,32 @@ "cell_type": "code", "execution_count": null, "metadata": {}, - "outputs": [], + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "step: 0, loss: 1.0939550595829053, L_x: 2.531834521858599, L_y: 0.8200826015334493, L_z: 0.010344502931797964\n", + "step: 250, loss: 0.9162820270109503, L_x: 2.529109218043187, L_y: 0.6432961063010657, L_z: 0.010037499452782905\n", + "step: 500, loss: 0.8207071510514392, L_x: 2.5204911168067197, L_y: 0.5500397646035967, L_z: 0.00930913738358528\n", + "step: 750, loss: 0.8102771268166408, L_x: 2.511873834704061, L_y: 0.5427956868742799, L_z: 0.008147028235977415\n", + "step: 1000, loss: 0.7996570283329768, L_x: 2.480828451323288, L_y: 0.5399446552800813, L_z: 0.00581476396028337\n", + "step: 1250, loss: 0.7844631169970814, L_x: 2.4242508289183613, L_y: 0.5304307199052671, L_z: 0.005803657099989009\n", + "step: 1500, loss: 0.7653305722023572, L_x: 2.3297047767431986, L_y: 0.5176248867874912, L_z: 0.007367603870273078\n", + "step: 1750, loss: 0.7154304631442515, L_x: 2.085955877234543, L_y: 0.48081670080967953, L_z: 0.013009087305558827\n", + "step: 2000, loss: 0.6906420918886886, L_x: 1.896344106091722, L_y: 0.4646651544564373, L_z: 0.018171263411539594\n", + "step: 2250, loss: 0.6783680937630076, L_x: 1.7895665853948028, L_y: 0.4587714378849466, L_z: 0.020319998669290275\n", + "step: 2500, loss: 0.6725576747654705, L_x: 1.742061633693402, L_y: 0.4577729094336143, L_z: 0.020289300981257967\n", + "step: 2750, loss: 0.6694103860159343, L_x: 1.7548885984309939, L_y: 0.4545867175857845, L_z: 0.019667404293525217\n", + "step: 3000, loss: 0.6658207636894926, L_x: 1.7515234617350093, L_y: 0.4539151313299769, L_z: 0.018376643093007367\n", + "step: 3250, loss: 0.6481415219979564, L_x: 1.7252276686316934, L_y: 0.4491717858033674, L_z: 0.013223484665709846\n", + "step: 3500, loss: 0.645366243737316, L_x: 1.7196207136719521, L_y: 0.4482843307446003, L_z: 0.012559920812760247\n", + "step: 3750, loss: 0.6425278186287126, L_x: 1.7117758355776211, L_y: 0.4473063883366716, L_z: 0.012021923367139413\n", + "step: 4000, loss: 0.6419409673076768, L_x: 1.7092609385556714, L_y: 0.44744616781598634, L_z: 0.011784352818061686\n", + "step: 4250, loss: 0.6377801462539607, L_x: 1.6917081956472533, L_y: 0.4496335370425122, L_z: 0.009487894823361622\n" + ] + } + ], "source": [ "# Input recontruction quality - Ax\n", "# Fairness constraint - Az\n", @@ -337,7 +451,7 @@ ], "metadata": { "kernelspec": { - "display_name": "Python 3 (ipykernel)", + "display_name": "Python 3", "language": "python", "name": "python3" }, @@ -351,9 +465,9 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.11.15" + "version": "3.6.10" } }, "nbformat": 4, - "nbformat_minor": 4 + "nbformat_minor": 2 }