├── .DS_Store ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── images ├── .DS_Store ├── AutoEncoder.png ├── Autoencoder_structure.png ├── function.png ├── image-01.png ├── image-02.png ├── image-03.png ├── image-04.png ├── image-05.png ├── image-06.png ├── image-07.png ├── image-08.png ├── image-09.png ├── image-10.png ├── image-11.png ├── image-12.png ├── image-13.png └── image-14.png └── notebooks ├── AutoEncoders.ipynb ├── NeuralNetOverSampling.ipynb ├── sagemaker_fraud_detection_xgb.ipynb └── train_nn.py /.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/.DS_Store -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | ## Code of Conduct 2 | This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct). 3 | For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact 4 | opensource-codeofconduct@amazon.com with any additional questions or comments. 5 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines 2 | 3 | Thank you for your interest in contributing to our project. Whether it's a bug report, new feature, correction, or additional 4 | documentation, we greatly value feedback and contributions from our community. 5 | 6 | Please read through this document before submitting any issues or pull requests to ensure we have all the necessary 7 | information to effectively respond to your bug report or contribution. 8 | 9 | 10 | ## Reporting Bugs/Feature Requests 11 | 12 | We welcome you to use the GitHub issue tracker to report bugs or suggest features. 13 | 14 | When filing an issue, please check existing open, or recently closed, issues to make sure somebody else hasn't already 15 | reported the issue. Please try to include as much information as you can. Details like these are incredibly useful: 16 | 17 | * A reproducible test case or series of steps 18 | * The version of our code being used 19 | * Any modifications you've made relevant to the bug 20 | * Anything unusual about your environment or deployment 21 | 22 | 23 | ## Contributing via Pull Requests 24 | Contributions via pull requests are much appreciated. Before sending us a pull request, please ensure that: 25 | 26 | 1. You are working against the latest source on the *master* branch. 27 | 2. You check existing open, and recently merged, pull requests to make sure someone else hasn't addressed the problem already. 28 | 3. You open an issue to discuss any significant work - we would hate for your time to be wasted. 29 | 30 | To send us a pull request, please: 31 | 32 | 1. Fork the repository. 33 | 2. Modify the source; please focus on the specific change you are contributing. If you also reformat all the code, it will be hard for us to focus on your change. 34 | 3. Ensure local tests pass. 35 | 4. Commit to your fork using clear commit messages. 36 | 5. Send us a pull request, answering any default questions in the pull request interface. 37 | 6. Pay attention to any automated CI failures reported in the pull request, and stay involved in the conversation. 38 | 39 | GitHub provides additional document on [forking a repository](https://help.github.com/articles/fork-a-repo/) and 40 | [creating a pull request](https://help.github.com/articles/creating-a-pull-request/). 41 | 42 | 43 | ## Finding contributions to work on 44 | Looking at the existing issues is a great way to find something to contribute on. As our projects, by default, use the default GitHub issue labels (enhancement/bug/duplicate/help wanted/invalid/question/wontfix), looking at any 'help wanted' issues is a great place to start. 45 | 46 | 47 | ## Code of Conduct 48 | This project has adopted the [Amazon Open Source Code of Conduct](https://aws.github.io/code-of-conduct). 49 | For more information see the [Code of Conduct FAQ](https://aws.github.io/code-of-conduct-faq) or contact 50 | opensource-codeofconduct@amazon.com with any additional questions or comments. 51 | 52 | 53 | ## Security issue notifications 54 | If you discover a potential security issue in this project we ask that you notify AWS/Amazon Security via our [vulnerability reporting page](http://aws.amazon.com/security/vulnerability-reporting/). Please do **not** create a public github issue. 55 | 56 | 57 | ## Licensing 58 | 59 | See the [LICENSE](LICENSE) file for our project's licensing. We will ask you to confirm the licensing of your contribution. 60 | 61 | We may ask you to sign a [Contributor License Agreement (CLA)](http://en.wikipedia.org/wiki/Contributor_License_Agreement) for larger changes. 62 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved. 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of 4 | this software and associated documentation files (the "Software"), to deal in 5 | the Software without restriction, including without limitation the rights to 6 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 7 | the Software, and to permit persons to whom the Software is furnished to do so. 8 | 9 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 10 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 11 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 12 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 13 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 14 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 15 | 16 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## Sagemaker Fraud Detection Workshop 2 | 3 | ### Lab description 4 | 5 | This lab demonstrates three different ML algorithms used for identifying fraudelent transactions on the same dataset: 6 | - SageMaker XGBoost 7 | - AutoEncoders 8 | - Neural Networks 9 | 10 | ### Steps for launching the workshop environment using EVENT ENGINE 11 | Note: these steps were tested on Chrome browser using Mac OS 12 | #### open a browser and navigate to https://dashboard.eventengine.run/login 13 | #### Enter a 12-character "hash" provided to you by workshop organizer. 14 | #### Click on "Accpet Terms & Login" 15 | ![Navigate to Sagemaker Service](/images/image-01.png) 16 | 17 | #### Click on "AWS Console" 18 | ![Navigate to Sagemaker Service](/images/image-02.png) 19 | 20 | #### Please, log off from any other AWS accounts you are currently logged into 21 | 22 | #### Click on "Open AWS Console" 23 | ![Navigate to Sagemaker Service](images/image-03.png) 24 | 25 | #### You should see a screen like this. 26 | #### We now need select the correct Identity Role for the workshop 27 | #### Type "IAM" into the search bar and click on IAM 28 | (Identity and Access Management). 29 | ![Navigate to Sagemaker Service](/images/image-04.png) 30 | 31 | #### Click on "Roles" 32 | ![Navigate to Sagemaker Service](/images/image-05.png) 33 | 34 | #### Scroll down past "Create Role" and Click on "TeamRole" 35 | ![Navigate to Sagemaker Service](/images/image-06.png) 36 | 37 | #### Copy "Role ARN" by selecting the copy icon on the right 38 | #### You may want to temporariliy paste this role ARN into a notepad 39 | #### Once you copied TeamRole ARN, click on "Services" in the upper left corner 40 | ![Navigate to Sagemaker Service](/images/image-07.png) 41 | 42 | #### Enter "SageMaker" in the search bar and click on it 43 | ![Navigate to Sagemaker Service](/images/image-08.png) 44 | 45 | #### You should see a screen like this. 46 | #### Click on the orange button "Create Notebook Instance" 47 | ![Navigate to Sagemaker Service](/images/image-09.png) 48 | 49 | #### On the next webpage, 50 | #### - Give your notebook a name (no underscores, please) 51 | #### - Under Notebook instance type, select "ml.c5.2xlarge" 52 | #### - Under "Permission and encryption" select "Enter a custom IAM role ARN"; 53 | #### - Paste your TeamRole ARN in the cell below labled "Custom IAM role ARN" 54 | #### Note: your TeamRole ARN will have different AWS account number than what you see here 55 | #### - Scroll down to the bottom of the page and click on "Create Notebook instance" 56 | ![Navigate to Sagemaker Service](/images/image-10.png) 57 | 58 | #### You should see your notebook being created. In a couple of minutes, its status will change 59 | #### from "Pending" to "In Service", at which point, please click on "Open Jupyter" 60 | ![Navigate to Sagemaker Service](/images/image-11.png) 61 | 62 | #### In Jupyter Notebook console, please, click on 'New' -> 'Terminal' on the right-hand side 63 | ![Navigate to Sagemaker Service](/images/image-12.png) 64 | 65 | #### A new Chrome browser tab will open displaying a command prompt terminal 66 | #### In the terminal tap, please, issue these two commands: 67 | #### $ cd SageMaker 68 | #### $ git clone https://github.com/aws-samples/amazon-sagemaker-fraud-detection 69 | #### You should see output similar to this: 70 | ![Navigate to Sagemaker Service](/images/image-13.png) 71 | 72 | #### You may now close the browser tab with command prompt terminal, 73 | #### return to Jupyter console and navigate the created folder structure to 74 | #### amazon-sagemaker-fraud-detection -> notebooks 75 | #### launch and run each one of the three Jupyter notebooks 76 | ![Navigate to Sagemaker Service](/images/image-14.png) 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | #### Open SageMaker Console by clicking on "Services" and searching for Sagemaker 89 | ![Navigate to Sagemaker Service](/images/image-08.png) 90 | 91 | ## License 92 | 93 | This library is licensed under the MIT-0 License. See the LICENSE file. 94 | 95 | -------------------------------------------------------------------------------- /images/.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/.DS_Store -------------------------------------------------------------------------------- /images/AutoEncoder.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/AutoEncoder.png -------------------------------------------------------------------------------- /images/Autoencoder_structure.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/Autoencoder_structure.png -------------------------------------------------------------------------------- /images/function.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/function.png -------------------------------------------------------------------------------- /images/image-01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-01.png -------------------------------------------------------------------------------- /images/image-02.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-02.png -------------------------------------------------------------------------------- /images/image-03.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-03.png -------------------------------------------------------------------------------- /images/image-04.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-04.png -------------------------------------------------------------------------------- /images/image-05.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-05.png -------------------------------------------------------------------------------- /images/image-06.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-06.png -------------------------------------------------------------------------------- /images/image-07.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-07.png -------------------------------------------------------------------------------- /images/image-08.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-08.png -------------------------------------------------------------------------------- /images/image-09.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-09.png -------------------------------------------------------------------------------- /images/image-10.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-10.png -------------------------------------------------------------------------------- /images/image-11.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-11.png -------------------------------------------------------------------------------- /images/image-12.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-12.png -------------------------------------------------------------------------------- /images/image-13.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-13.png -------------------------------------------------------------------------------- /images/image-14.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aws-samples/amazon-sagemaker-fraud-detection/66c88ab1f2b63686d052fe2febb9324b7847607d/images/image-14.png -------------------------------------------------------------------------------- /notebooks/NeuralNetOverSampling.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Fraud Detection Using Neural Network - A Supervised Deep Learning Method" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "## Introduction\n", 15 | "In this lab, we are going to use the Neural Network to perform fraud detection. We are going to use the same dataset i.e. credit card data set. \n", 16 | "\n", 17 | "From previous labs we know that our dataset is highly imbalanced. The class column corresponds to whether or not a transaction is fradulent. We see that the majority of data is non-fraudulant with only $492$ ($.173\\%$) of the data corresponding to fraudulant examples.\n", 18 | "\n", 19 | "For unbalanced data sets like ours where the positive (fraudulent) examples occur much less frequently than the negative (legitimate) examples, we may try “over-sampling” the minority dataset by generating synthetic data (read about SMOTE in Data Mining for Imbalanced Datasets: An Overview (https://link.springer.com/chapter/10.1007%2F0-387-25465-X_40) or undersampling the majority class by using ensemble methods (see http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.68.6858&rep=rep1&type=pdfor).\n", 20 | "\n", 21 | "Let's start by installing one of the liabraries for SMOTE technique." 22 | ] 23 | }, 24 | { 25 | "cell_type": "code", 26 | "execution_count": null, 27 | "metadata": {}, 28 | "outputs": [], 29 | "source": [ 30 | "!pip install -U imbalanced-learn" 31 | ] 32 | }, 33 | { 34 | "cell_type": "code", 35 | "execution_count": 2, 36 | "metadata": {}, 37 | "outputs": [], 38 | "source": [ 39 | "# creating directory structure\n", 40 | "!mkdir ../data\n", 41 | "!mkdir ../model\n", 42 | "!mkdir ../logs" 43 | ] 44 | }, 45 | { 46 | "cell_type": "code", 47 | "execution_count": 3, 48 | "metadata": {}, 49 | "outputs": [ 50 | { 51 | "name": "stderr", 52 | "output_type": "stream", 53 | "text": [ 54 | "Using TensorFlow backend.\n" 55 | ] 56 | } 57 | ], 58 | "source": [ 59 | "# first neural network with keras tutorial\n", 60 | "from numpy import loadtxt\n", 61 | "from keras.models import Sequential\n", 62 | "from keras.layers import Dense\n", 63 | "import pandas as pd\n", 64 | "import numpy as np\n", 65 | "from imblearn.over_sampling import SMOTE, ADASYN\n", 66 | "from sagemaker.tensorflow import TensorFlow\n", 67 | "from collections import Counter\n", 68 | "import matplotlib.pyplot as plt\n", 69 | "import seaborn as sns" 70 | ] 71 | }, 72 | { 73 | "cell_type": "markdown", 74 | "metadata": {}, 75 | "source": [ 76 | "## Downloading data" 77 | ] 78 | }, 79 | { 80 | "cell_type": "code", 81 | "execution_count": null, 82 | "metadata": {}, 83 | "outputs": [], 84 | "source": [ 85 | "!curl https://s3-us-west-2.amazonaws.com/sagemaker-e2e-solutions/fraud-detection/creditcardfraud.zip -o ../data/creditcardfraud.zip" 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 5, 91 | "metadata": {}, 92 | "outputs": [ 93 | { 94 | "name": "stdout", 95 | "output_type": "stream", 96 | "text": [ 97 | "Archive: ../data/creditcardfraud.zip\n", 98 | " inflating: ../data/creditcard.csv \n" 99 | ] 100 | } 101 | ], 102 | "source": [ 103 | "!unzip -o ../data/creditcardfraud.zip -d ../data/" 104 | ] 105 | }, 106 | { 107 | "cell_type": "markdown", 108 | "metadata": {}, 109 | "source": [ 110 | "## Load and Visualize" 111 | ] 112 | }, 113 | { 114 | "cell_type": "code", 115 | "execution_count": 6, 116 | "metadata": {}, 117 | "outputs": [], 118 | "source": [ 119 | "data = pd.read_csv('../data/creditcard.csv', delimiter=',')" 120 | ] 121 | }, 122 | { 123 | "cell_type": "code", 124 | "execution_count": 7, 125 | "metadata": {}, 126 | "outputs": [ 127 | { 128 | "data": { 129 | "text/html": [ 130 | "
\n", 131 | "\n", 144 | "\n", 145 | " \n", 146 | " \n", 147 | " \n", 148 | " \n", 149 | " \n", 150 | " \n", 151 | " \n", 152 | " \n", 153 | " \n", 154 | " \n", 155 | " \n", 156 | " \n", 157 | " \n", 158 | " \n", 159 | " \n", 160 | " \n", 161 | " \n", 162 | " \n", 163 | " \n", 164 | " \n", 165 | " \n", 166 | " \n", 167 | " \n", 168 | " \n", 169 | " \n", 170 | " \n", 171 | " \n", 172 | " \n", 173 | " \n", 174 | " \n", 175 | " \n", 176 | " \n", 177 | " \n", 178 | " \n", 179 | " \n", 180 | " \n", 181 | " \n", 182 | " \n", 183 | " \n", 184 | " \n", 185 | " \n", 186 | " \n", 187 | " \n", 188 | " \n", 189 | " \n", 190 | " \n", 191 | " \n", 192 | " \n", 193 | " \n", 194 | " \n", 195 | " \n", 196 | " \n", 197 | " \n", 198 | " \n", 199 | " \n", 200 | " \n", 201 | " \n", 202 | " \n", 203 | " \n", 204 | " \n", 205 | " \n", 206 | " \n", 207 | " \n", 208 | " \n", 209 | " \n", 210 | " \n", 211 | " \n", 212 | " \n", 213 | " \n", 214 | " \n", 215 | " \n", 216 | " \n", 217 | " \n", 218 | " \n", 219 | " \n", 220 | " \n", 221 | " \n", 222 | " \n", 223 | " \n", 224 | " \n", 225 | " \n", 226 | " \n", 227 | " \n", 228 | " \n", 229 | " \n", 230 | " \n", 231 | " \n", 232 | " \n", 233 | " \n", 234 | " \n", 235 | " \n", 236 | " \n", 237 | " \n", 238 | " \n", 239 | " \n", 240 | " \n", 241 | " \n", 242 | " \n", 243 | " \n", 244 | " \n", 245 | " \n", 246 | " \n", 247 | " \n", 248 | " \n", 249 | " \n", 250 | " \n", 251 | " \n", 252 | " \n", 253 | " \n", 254 | " \n", 255 | " \n", 256 | " \n", 257 | " \n", 258 | " \n", 259 | " \n", 260 | " \n", 261 | " \n", 262 | " \n", 263 | " \n", 264 | " \n", 265 | " \n", 266 | " \n", 267 | " \n", 268 | " \n", 269 | " \n", 270 | " \n", 271 | " \n", 272 | " \n", 273 | " \n", 274 | " \n", 275 | " \n", 276 | " \n", 277 | " \n", 278 | " \n", 279 | " \n", 280 | " \n", 281 | " \n", 282 | " \n", 283 | " \n", 284 | " \n", 285 | " \n", 286 | " \n", 287 | " \n", 288 | " \n", 289 | " \n", 290 | " \n", 291 | " \n", 292 | " \n", 293 | " \n", 294 | " \n", 295 | " \n", 296 | " \n", 297 | " \n", 298 | " \n", 299 | " \n", 300 | " \n", 301 | " \n", 302 | " \n", 303 | " \n", 304 | " \n", 305 | " \n", 306 | " \n", 307 | " \n", 308 | " \n", 309 | " \n", 310 | " \n", 311 | " \n", 312 | " \n", 313 | " \n", 314 | " \n", 315 | " \n", 316 | " \n", 317 | " \n", 318 | " \n", 319 | " \n", 320 | " \n", 321 | " \n", 322 | " \n", 323 | " \n", 324 | " \n", 325 | " \n", 326 | " \n", 327 | " \n", 328 | " \n", 329 | " \n", 330 | " \n", 331 | " \n", 332 | " \n", 333 | " \n", 334 | " \n", 335 | " \n", 336 | " \n", 337 | " \n", 338 | " \n", 339 | " \n", 340 | " \n", 341 | " \n", 342 | " \n", 343 | " \n", 344 | " \n", 345 | " \n", 346 | " \n", 347 | " \n", 348 | " \n", 349 | " \n", 350 | " \n", 351 | " \n", 352 | " \n", 353 | " \n", 354 | " \n", 355 | " \n", 356 | " \n", 357 | " \n", 358 | " \n", 359 | " \n", 360 | " \n", 361 | " \n", 362 | " \n", 363 | " \n", 364 | " \n", 365 | " \n", 366 | " \n", 367 | " \n", 368 | " \n", 369 | " \n", 370 | " \n", 371 | " \n", 372 | " \n", 373 | " \n", 374 | " \n", 375 | " \n", 376 | " \n", 377 | " \n", 378 | " \n", 379 | " \n", 380 | " \n", 381 | " \n", 382 | " \n", 383 | " \n", 384 | " \n", 385 | " \n", 386 | " \n", 387 | " \n", 388 | " \n", 389 | " \n", 390 | " \n", 391 | " \n", 392 | " \n", 393 | " \n", 394 | " \n", 395 | " \n", 396 | " \n", 397 | " \n", 398 | " \n", 399 | " \n", 400 | " \n", 401 | " \n", 402 | " \n", 403 | " \n", 404 | " \n", 405 | " \n", 406 | " \n", 407 | " \n", 408 | " \n", 409 | " \n", 410 | " \n", 411 | " \n", 412 | " \n", 413 | "
TimeV1V2V3V4V5V6V7V8V9...V21V22V23V24V25V26V27V28AmountClass
00.0-1.359807-0.0727812.5363471.378155-0.3383210.4623880.2395990.0986980.363787...-0.0183070.277838-0.1104740.0669280.128539-0.1891150.133558-0.021053149.620
10.01.1918570.2661510.1664800.4481540.060018-0.082361-0.0788030.085102-0.255425...-0.225775-0.6386720.101288-0.3398460.1671700.125895-0.0089830.0147242.690
21.0-1.358354-1.3401631.7732090.379780-0.5031981.8004990.7914610.247676-1.514654...0.2479980.7716790.909412-0.689281-0.327642-0.139097-0.055353-0.059752378.660
31.0-0.966272-0.1852261.792993-0.863291-0.0103091.2472030.2376090.377436-1.387024...-0.1083000.005274-0.190321-1.1755750.647376-0.2219290.0627230.061458123.500
42.0-1.1582330.8777371.5487180.403034-0.4071930.0959210.592941-0.2705330.817739...-0.0094310.798278-0.1374580.141267-0.2060100.5022920.2194220.21515369.990
52.0-0.4259660.9605231.141109-0.1682520.420987-0.0297280.4762010.260314-0.568671...-0.208254-0.559825-0.026398-0.371427-0.2327940.1059150.2538440.0810803.670
64.01.2296580.1410040.0453711.2026130.1918810.272708-0.0051590.0812130.464960...-0.167716-0.270710-0.154104-0.7800550.750137-0.2572370.0345070.0051684.990
77.0-0.6442691.4179641.074380-0.4921990.9489340.4281181.120631-3.8078640.615375...1.943465-1.0154550.057504-0.649709-0.415267-0.051634-1.206921-1.08533940.800
87.0-0.8942860.286157-0.113192-0.2715262.6695993.7218180.3701450.851084-0.392048...-0.073425-0.268092-0.2042331.0115920.373205-0.3841570.0117470.14240493.200
99.0-0.3382621.1195931.044367-0.2221870.499361-0.2467610.6515830.069539-0.736727...-0.246914-0.633753-0.120794-0.385050-0.0697330.0941990.2462190.0830763.680
\n", 414 | "

10 rows × 31 columns

\n", 415 | "
" 416 | ], 417 | "text/plain": [ 418 | " Time V1 V2 V3 V4 V5 V6 V7 \\\n", 419 | "0 0.0 -1.359807 -0.072781 2.536347 1.378155 -0.338321 0.462388 0.239599 \n", 420 | "1 0.0 1.191857 0.266151 0.166480 0.448154 0.060018 -0.082361 -0.078803 \n", 421 | "2 1.0 -1.358354 -1.340163 1.773209 0.379780 -0.503198 1.800499 0.791461 \n", 422 | "3 1.0 -0.966272 -0.185226 1.792993 -0.863291 -0.010309 1.247203 0.237609 \n", 423 | "4 2.0 -1.158233 0.877737 1.548718 0.403034 -0.407193 0.095921 0.592941 \n", 424 | "5 2.0 -0.425966 0.960523 1.141109 -0.168252 0.420987 -0.029728 0.476201 \n", 425 | "6 4.0 1.229658 0.141004 0.045371 1.202613 0.191881 0.272708 -0.005159 \n", 426 | "7 7.0 -0.644269 1.417964 1.074380 -0.492199 0.948934 0.428118 1.120631 \n", 427 | "8 7.0 -0.894286 0.286157 -0.113192 -0.271526 2.669599 3.721818 0.370145 \n", 428 | "9 9.0 -0.338262 1.119593 1.044367 -0.222187 0.499361 -0.246761 0.651583 \n", 429 | "\n", 430 | " V8 V9 ... V21 V22 V23 V24 V25 \\\n", 431 | "0 0.098698 0.363787 ... -0.018307 0.277838 -0.110474 0.066928 0.128539 \n", 432 | "1 0.085102 -0.255425 ... -0.225775 -0.638672 0.101288 -0.339846 0.167170 \n", 433 | "2 0.247676 -1.514654 ... 0.247998 0.771679 0.909412 -0.689281 -0.327642 \n", 434 | "3 0.377436 -1.387024 ... -0.108300 0.005274 -0.190321 -1.175575 0.647376 \n", 435 | "4 -0.270533 0.817739 ... -0.009431 0.798278 -0.137458 0.141267 -0.206010 \n", 436 | "5 0.260314 -0.568671 ... -0.208254 -0.559825 -0.026398 -0.371427 -0.232794 \n", 437 | "6 0.081213 0.464960 ... -0.167716 -0.270710 -0.154104 -0.780055 0.750137 \n", 438 | "7 -3.807864 0.615375 ... 1.943465 -1.015455 0.057504 -0.649709 -0.415267 \n", 439 | "8 0.851084 -0.392048 ... -0.073425 -0.268092 -0.204233 1.011592 0.373205 \n", 440 | "9 0.069539 -0.736727 ... -0.246914 -0.633753 -0.120794 -0.385050 -0.069733 \n", 441 | "\n", 442 | " V26 V27 V28 Amount Class \n", 443 | "0 -0.189115 0.133558 -0.021053 149.62 0 \n", 444 | "1 0.125895 -0.008983 0.014724 2.69 0 \n", 445 | "2 -0.139097 -0.055353 -0.059752 378.66 0 \n", 446 | "3 -0.221929 0.062723 0.061458 123.50 0 \n", 447 | "4 0.502292 0.219422 0.215153 69.99 0 \n", 448 | "5 0.105915 0.253844 0.081080 3.67 0 \n", 449 | "6 -0.257237 0.034507 0.005168 4.99 0 \n", 450 | "7 -0.051634 -1.206921 -1.085339 40.80 0 \n", 451 | "8 -0.384157 0.011747 0.142404 93.20 0 \n", 452 | "9 0.094199 0.246219 0.083076 3.68 0 \n", 453 | "\n", 454 | "[10 rows x 31 columns]" 455 | ] 456 | }, 457 | "execution_count": 7, 458 | "metadata": {}, 459 | "output_type": "execute_result" 460 | } 461 | ], 462 | "source": [ 463 | "data.head(10)" 464 | ] 465 | }, 466 | { 467 | "cell_type": "code", 468 | "execution_count": 8, 469 | "metadata": {}, 470 | "outputs": [ 471 | { 472 | "data": { 473 | "text/plain": [ 474 | "Text(0, 0.5, 'Frequency')" 475 | ] 476 | }, 477 | "execution_count": 8, 478 | "metadata": {}, 479 | "output_type": "execute_result" 480 | }, 481 | { 482 | "data": { 483 | "image/png": "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\n", 484 | "text/plain": [ 485 | "
" 486 | ] 487 | }, 488 | "metadata": {}, 489 | "output_type": "display_data" 490 | } 491 | ], 492 | "source": [ 493 | "labels = ['normal','fraud']\n", 494 | "classes = pd.value_counts(data['Class'], sort = True)\n", 495 | "classes.plot(kind = 'bar', rot=0)\n", 496 | "plt.title(\"Transaction class distribution\")\n", 497 | "plt.xticks(range(2), labels)\n", 498 | "plt.xlabel(\"Class\")\n", 499 | "plt.ylabel(\"Frequency\")" 500 | ] 501 | }, 502 | { 503 | "cell_type": "markdown", 504 | "metadata": {}, 505 | "source": [ 506 | "As we learned in previous labs, that features like 'Time', and 'Amount' are not that relevant. So let's drop these fields." 507 | ] 508 | }, 509 | { 510 | "cell_type": "code", 511 | "execution_count": 9, 512 | "metadata": {}, 513 | "outputs": [], 514 | "source": [ 515 | "data = data.drop(['Time','Amount'],axis=1)" 516 | ] 517 | }, 518 | { 519 | "cell_type": "markdown", 520 | "metadata": {}, 521 | "source": [ 522 | "## Split dateset into Train, Validation, and Test" 523 | ] 524 | }, 525 | { 526 | "cell_type": "code", 527 | "execution_count": 10, 528 | "metadata": {}, 529 | "outputs": [], 530 | "source": [ 531 | "import boto3\n", 532 | "import os\n", 533 | "import sagemaker\n", 534 | "from sklearn.model_selection import train_test_split\n", 535 | "\n", 536 | "session = sagemaker.Session()\n", 537 | "\n", 538 | "bucket = session.default_bucket()\n", 539 | "sagemaker_iam_role = sagemaker.get_execution_role()\n", 540 | "\n", 541 | "prefix = 'sagemaker/NeuralNetwork-fraud'\n", 542 | "\n", 543 | "RANDOM_SEED = 314 #used to help randomly select the data points\n", 544 | "TEST_PCT = 0.2 # 20% of the data\n", 545 | "\n", 546 | "train_data, test_data = train_test_split(data, test_size=TEST_PCT,random_state=RANDOM_SEED)\n", 547 | "validation_data, test_data = train_test_split(test_data, test_size=0.5,random_state=RANDOM_SEED)" 548 | ] 549 | }, 550 | { 551 | "cell_type": "markdown", 552 | "metadata": {}, 553 | "source": [ 554 | "## Balacing our Training dataset" 555 | ] 556 | }, 557 | { 558 | "cell_type": "code", 559 | "execution_count": 11, 560 | "metadata": {}, 561 | "outputs": [ 562 | { 563 | "name": "stdout", 564 | "output_type": "stream", 565 | "text": [ 566 | "(227845, 28)\n", 567 | "(227845, 1)\n" 568 | ] 569 | }, 570 | { 571 | "name": "stderr", 572 | "output_type": "stream", 573 | "text": [ 574 | "/home/ec2-user/anaconda3/envs/tensorflow_p36/lib/python3.6/site-packages/sklearn/utils/validation.py:724: DataConversionWarning: A column-vector y was passed when a 1d array was expected. Please change the shape of y to (n_samples, ), for example using ravel().\n", 575 | " y = column_or_1d(y, warn=True)\n" 576 | ] 577 | }, 578 | { 579 | "name": "stdout", 580 | "output_type": "stream", 581 | "text": [ 582 | "(454936, 28)\n", 583 | "(454936, 1)\n" 584 | ] 585 | }, 586 | { 587 | "data": { 588 | "text/plain": [ 589 | "(454936, 29)" 590 | ] 591 | }, 592 | "execution_count": 11, 593 | "metadata": {}, 594 | "output_type": "execute_result" 595 | } 596 | ], 597 | "source": [ 598 | "X = train_data.iloc[:, 0:28]\n", 599 | "y = train_data.iloc[:,28:29]\n", 600 | "print(X.shape)\n", 601 | "print(y.shape)\n", 602 | "\n", 603 | "X_resampled, y_resampled = SMOTE().fit_resample(X, y)\n", 604 | "y_resampled = y_resampled.reshape((y_resampled.shape[0],1))\n", 605 | "\n", 606 | "X = X_resampled\n", 607 | "y = y_resampled\n", 608 | "\n", 609 | "print(X.shape)\n", 610 | "print(y.shape)\n", 611 | "train_data = np.concatenate((X, y),axis=1)\n", 612 | "train_data = pd.DataFrame(train_data)\n", 613 | "train_data.shape" 614 | ] 615 | }, 616 | { 617 | "cell_type": "code", 618 | "execution_count": 12, 619 | "metadata": {}, 620 | "outputs": [ 621 | { 622 | "data": { 623 | "text/html": [ 624 | "
\n", 625 | "\n", 638 | "\n", 639 | " \n", 640 | " \n", 641 | " \n", 642 | " \n", 643 | " \n", 644 | " \n", 645 | " \n", 646 | " \n", 647 | " \n", 648 | " \n", 649 | " \n", 650 | " \n", 651 | " \n", 652 | " \n", 653 | " \n", 654 | " \n", 655 | " \n", 656 | " \n", 657 | " \n", 658 | " \n", 659 | " \n", 660 | " \n", 661 | " \n", 662 | " \n", 663 | " \n", 664 | " \n", 665 | " \n", 666 | " \n", 667 | " \n", 668 | " \n", 669 | " \n", 670 | " \n", 671 | " \n", 672 | " \n", 673 | " \n", 674 | " \n", 675 | " \n", 676 | " \n", 677 | " \n", 678 | " \n", 679 | " \n", 680 | " \n", 681 | " \n", 682 | " \n", 683 | " \n", 684 | " \n", 685 | " \n", 686 | " \n", 687 | " \n", 688 | " \n", 689 | " \n", 690 | " \n", 691 | " \n", 692 | " \n", 693 | " \n", 694 | " \n", 695 | " \n", 696 | " \n", 697 | " \n", 698 | " \n", 699 | " \n", 700 | " \n", 701 | " \n", 702 | " \n", 703 | " \n", 704 | " \n", 705 | " \n", 706 | " \n", 707 | " \n", 708 | " \n", 709 | " \n", 710 | " \n", 711 | " \n", 712 | " \n", 713 | " \n", 714 | " \n", 715 | " \n", 716 | " \n", 717 | " \n", 718 | " \n", 719 | " \n", 720 | " \n", 721 | " \n", 722 | " \n", 723 | " \n", 724 | " \n", 725 | " \n", 726 | " \n", 727 | " \n", 728 | " \n", 729 | " \n", 730 | " \n", 731 | " \n", 732 | " \n", 733 | " \n", 734 | " \n", 735 | " \n", 736 | " \n", 737 | " \n", 738 | " \n", 739 | " \n", 740 | " \n", 741 | " \n", 742 | " \n", 743 | " \n", 744 | " \n", 745 | " \n", 746 | " \n", 747 | " \n", 748 | " \n", 749 | " \n", 750 | " \n", 751 | " \n", 752 | " \n", 753 | " \n", 754 | " \n", 755 | " \n", 756 | " \n", 757 | " \n", 758 | " \n", 759 | " \n", 760 | " \n", 761 | " \n", 762 | " \n", 763 | " \n", 764 | " \n", 765 | " \n", 766 | " \n", 767 | " \n", 768 | " \n", 769 | " \n", 770 | " \n", 771 | " \n", 772 | " \n", 773 | " \n", 774 | " \n", 775 | " \n", 776 | " \n", 777 | " \n", 778 | " \n", 779 | " \n", 780 | " \n", 781 | " \n", 782 | " \n", 783 | " \n", 784 | " \n", 785 | " \n", 786 | " \n", 787 | " \n", 788 | " \n", 789 | " \n", 790 | " \n", 791 | " \n", 792 | " \n", 793 | " \n", 794 | " \n", 795 | " \n", 796 | " \n", 797 | " \n", 798 | " \n", 799 | " \n", 800 | " \n", 801 | " \n", 802 | " \n", 803 | " \n", 804 | " \n", 805 | " \n", 806 | " \n", 807 | " \n", 808 | " \n", 809 | " \n", 810 | " \n", 811 | " \n", 812 | " \n", 813 | " \n", 814 | " \n", 815 | " \n", 816 | " \n", 817 | " \n", 818 | " \n", 819 | " \n", 820 | " \n", 821 | " \n", 822 | " \n", 823 | " \n", 824 | " \n", 825 | " \n", 826 | " \n", 827 | " \n", 828 | " \n", 829 | " \n", 830 | " \n", 831 | " \n", 832 | " \n", 833 | " \n", 834 | " \n", 835 | " \n", 836 | " \n", 837 | " \n", 838 | " \n", 839 | " \n", 840 | " \n", 841 | " \n", 842 | " \n", 843 | " \n", 844 | " \n", 845 | " \n", 846 | " \n", 847 | " \n", 848 | " \n", 849 | " \n", 850 | " \n", 851 | " \n", 852 | " \n", 853 | " \n", 854 | " \n", 855 | " \n", 856 | " \n", 857 | " \n", 858 | " \n", 859 | " \n", 860 | " \n", 861 | " \n", 862 | " \n", 863 | " \n", 864 | " \n", 865 | " \n", 866 | " \n", 867 | " \n", 868 | " \n", 869 | " \n", 870 | " \n", 871 | " \n", 872 | " \n", 873 | " \n", 874 | " \n", 875 | " \n", 876 | " \n", 877 | " \n", 878 | " \n", 879 | " \n", 880 | " \n", 881 | " \n", 882 | " \n", 883 | " \n", 884 | " \n", 885 | " \n", 886 | " \n", 887 | " \n", 888 | " \n", 889 | " \n", 890 | " \n", 891 | " \n", 892 | " \n", 893 | " \n", 894 | " \n", 895 | " \n", 896 | " \n", 897 | " \n", 898 | " \n", 899 | " \n", 900 | " \n", 901 | " \n", 902 | " \n", 903 | " \n", 904 | " \n", 905 | " \n", 906 | " \n", 907 | "
0123456789...19202122232425262728
00.2605380.644354-0.649921-0.0534630.883230-0.7579730.787879-0.1420560.291431-0.926765...-0.1265910.1246000.572313-0.245022-0.698144-0.3753060.7152180.0813760.1082980.0
1-1.3822660.1121620.5417461.459137-1.3201200.8815051.2748780.692477-0.523981-0.419198...0.6838670.2461740.1604480.774357-0.064849-0.023380-0.2424200.1588460.1535500.0
21.998524-0.228993-0.2768570.572004-0.3057670.025961-0.706267-0.0688672.603357-0.577862...-0.1847250.0432190.6573040.1504400.592132-0.064754-0.2776140.020307-0.0362670.0
30.736055-0.4231050.2802551.521043-0.739431-0.9827840.463617-0.284605-0.061795-0.048532...0.3465340.2405330.182956-0.2855090.7274830.538996-0.326837-0.0278060.0680510.0
42.063104-0.064287-0.9551700.639229-0.229669-1.213497-0.025961-0.3170862.089984-0.246140...-0.379353-0.459128-1.0266460.373861-0.062467-0.3817830.162610-0.108893-0.0699740.0
51.938746-1.348070-0.571826-0.898448-1.164698-0.275187-0.9977560.074171-0.0383860.851980...0.1260710.041904-0.1518100.264565-0.440844-0.564571-0.486713-0.012370-0.0387350.0
6-0.7668211.1688860.9516800.7173841.039082-0.3466631.765473-0.569001-0.5787340.621377...0.109518-0.0406730.372062-0.7058670.0107091.003730-0.266130-0.277632-0.3681660.0
71.2956940.4004210.0983590.558956-0.036970-0.7465470.129645-0.215352-0.053382-0.305466...-0.012401-0.313920-0.8622300.053621-0.1709140.3154380.125078-0.0183830.0270280.0
81.2464540.038172-0.059950-0.096151-0.195872-0.8124500.183660-0.112738-0.1998240.046081...-0.061652-0.411634-1.3484990.148395-0.0002300.0844800.625746-0.113259-0.0082120.0
92.0167740.007711-3.2980510.1250373.0765083.0375940.1991250.576568-0.3066990.383016...-0.1667500.1315680.3283180.0075290.7018160.502323-0.465696-0.016936-0.0663470.0
\n", 908 | "

10 rows × 29 columns

\n", 909 | "
" 910 | ], 911 | "text/plain": [ 912 | " 0 1 2 3 4 5 6 \\\n", 913 | "0 0.260538 0.644354 -0.649921 -0.053463 0.883230 -0.757973 0.787879 \n", 914 | "1 -1.382266 0.112162 0.541746 1.459137 -1.320120 0.881505 1.274878 \n", 915 | "2 1.998524 -0.228993 -0.276857 0.572004 -0.305767 0.025961 -0.706267 \n", 916 | "3 0.736055 -0.423105 0.280255 1.521043 -0.739431 -0.982784 0.463617 \n", 917 | "4 2.063104 -0.064287 -0.955170 0.639229 -0.229669 -1.213497 -0.025961 \n", 918 | "5 1.938746 -1.348070 -0.571826 -0.898448 -1.164698 -0.275187 -0.997756 \n", 919 | "6 -0.766821 1.168886 0.951680 0.717384 1.039082 -0.346663 1.765473 \n", 920 | "7 1.295694 0.400421 0.098359 0.558956 -0.036970 -0.746547 0.129645 \n", 921 | "8 1.246454 0.038172 -0.059950 -0.096151 -0.195872 -0.812450 0.183660 \n", 922 | "9 2.016774 0.007711 -3.298051 0.125037 3.076508 3.037594 0.199125 \n", 923 | "\n", 924 | " 7 8 9 ... 19 20 21 22 \\\n", 925 | "0 -0.142056 0.291431 -0.926765 ... -0.126591 0.124600 0.572313 -0.245022 \n", 926 | "1 0.692477 -0.523981 -0.419198 ... 0.683867 0.246174 0.160448 0.774357 \n", 927 | "2 -0.068867 2.603357 -0.577862 ... -0.184725 0.043219 0.657304 0.150440 \n", 928 | "3 -0.284605 -0.061795 -0.048532 ... 0.346534 0.240533 0.182956 -0.285509 \n", 929 | "4 -0.317086 2.089984 -0.246140 ... -0.379353 -0.459128 -1.026646 0.373861 \n", 930 | "5 0.074171 -0.038386 0.851980 ... 0.126071 0.041904 -0.151810 0.264565 \n", 931 | "6 -0.569001 -0.578734 0.621377 ... 0.109518 -0.040673 0.372062 -0.705867 \n", 932 | "7 -0.215352 -0.053382 -0.305466 ... -0.012401 -0.313920 -0.862230 0.053621 \n", 933 | "8 -0.112738 -0.199824 0.046081 ... -0.061652 -0.411634 -1.348499 0.148395 \n", 934 | "9 0.576568 -0.306699 0.383016 ... -0.166750 0.131568 0.328318 0.007529 \n", 935 | "\n", 936 | " 23 24 25 26 27 28 \n", 937 | "0 -0.698144 -0.375306 0.715218 0.081376 0.108298 0.0 \n", 938 | "1 -0.064849 -0.023380 -0.242420 0.158846 0.153550 0.0 \n", 939 | "2 0.592132 -0.064754 -0.277614 0.020307 -0.036267 0.0 \n", 940 | "3 0.727483 0.538996 -0.326837 -0.027806 0.068051 0.0 \n", 941 | "4 -0.062467 -0.381783 0.162610 -0.108893 -0.069974 0.0 \n", 942 | "5 -0.440844 -0.564571 -0.486713 -0.012370 -0.038735 0.0 \n", 943 | "6 0.010709 1.003730 -0.266130 -0.277632 -0.368166 0.0 \n", 944 | "7 -0.170914 0.315438 0.125078 -0.018383 0.027028 0.0 \n", 945 | "8 -0.000230 0.084480 0.625746 -0.113259 -0.008212 0.0 \n", 946 | "9 0.701816 0.502323 -0.465696 -0.016936 -0.066347 0.0 \n", 947 | "\n", 948 | "[10 rows x 29 columns]" 949 | ] 950 | }, 951 | "execution_count": 12, 952 | "metadata": {}, 953 | "output_type": "execute_result" 954 | } 955 | ], 956 | "source": [ 957 | "train_data.head(10)" 958 | ] 959 | }, 960 | { 961 | "cell_type": "code", 962 | "execution_count": 13, 963 | "metadata": {}, 964 | "outputs": [ 965 | { 966 | "data": { 967 | "text/plain": [ 968 | "Text(0, 0.5, 'Frequency')" 969 | ] 970 | }, 971 | "execution_count": 13, 972 | "metadata": {}, 973 | "output_type": "execute_result" 974 | }, 975 | { 976 | "data": { 977 | "image/png": "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\n", 978 | "text/plain": [ 979 | "
" 980 | ] 981 | }, 982 | "metadata": {}, 983 | "output_type": "display_data" 984 | } 985 | ], 986 | "source": [ 987 | "labels = ['normal','fraud']\n", 988 | "classes = pd.value_counts(train_data.iloc[:,28], sort = True)\n", 989 | "classes.plot(kind = 'bar', rot=0)\n", 990 | "plt.title(\"Transaction class distribution\")\n", 991 | "plt.xticks(range(2), labels)\n", 992 | "plt.xlabel(\"Class\")\n", 993 | "plt.ylabel(\"Frequency\")" 994 | ] 995 | }, 996 | { 997 | "cell_type": "markdown", 998 | "metadata": {}, 999 | "source": [ 1000 | "After balancing the dataset between fraud and non-fraud, we have equal number of records for both the categories in our training set." 1001 | ] 1002 | }, 1003 | { 1004 | "cell_type": "markdown", 1005 | "metadata": {}, 1006 | "source": [ 1007 | "## Uploading our dataset to S3" 1008 | ] 1009 | }, 1010 | { 1011 | "cell_type": "code", 1012 | "execution_count": 14, 1013 | "metadata": {}, 1014 | "outputs": [ 1015 | { 1016 | "name": "stdout", 1017 | "output_type": "stream", 1018 | "text": [ 1019 | "Training artifacts will be uploaded to: s3://sagemaker-us-east-1-343208833149/sagemaker/NeuralNetwork-fraud/output\n" 1020 | ] 1021 | } 1022 | ], 1023 | "source": [ 1024 | "train_data.to_csv('train.csv', header=False, index=False)\n", 1025 | "validation_data.to_csv('validation.csv', header=False, index=False)\n", 1026 | "test_data.to_csv('test.csv', header=False, index=False)\n", 1027 | "\n", 1028 | "\n", 1029 | "boto3.Session().resource('s3').Bucket(bucket).Object(os.path.join(prefix, 'train/train.csv')) \\\n", 1030 | " .upload_file('train.csv')\n", 1031 | "boto3.Session().resource('s3').Bucket(bucket).Object(os.path.join(prefix, 'validation/validation.csv')) \\\n", 1032 | " .upload_file('validation.csv')\n", 1033 | "boto3.Session().resource('s3').Bucket(bucket).Object(os.path.join(prefix, 'test/test.csv')) \\\n", 1034 | " .upload_file('test.csv')\n", 1035 | "\n", 1036 | "s3_train_data = 's3://{}/{}/train/train.csv'.format(bucket, prefix)\n", 1037 | "s3_validation_data = 's3://{}/{}/validation/validation.csv'.format(bucket, prefix)\n", 1038 | "\n", 1039 | "\n", 1040 | "output_location = 's3://{}/{}/output'.format(bucket, prefix)\n", 1041 | "\n", 1042 | "print('Training artifacts will be uploaded to: {}'.format(output_location))" 1043 | ] 1044 | }, 1045 | { 1046 | "cell_type": "markdown", 1047 | "metadata": {}, 1048 | "source": [ 1049 | "## Set Up and Launch Training" 1050 | ] 1051 | }, 1052 | { 1053 | "cell_type": "code", 1054 | "execution_count": 15, 1055 | "metadata": {}, 1056 | "outputs": [], 1057 | "source": [ 1058 | "role = sagemaker.get_execution_role()" 1059 | ] 1060 | }, 1061 | { 1062 | "cell_type": "code", 1063 | "execution_count": 16, 1064 | "metadata": {}, 1065 | "outputs": [], 1066 | "source": [ 1067 | "epochs = 50\n", 1068 | "batchsize = 1000\n", 1069 | "key = \"data\"\n", 1070 | "key_output = \"output\" # Path from the bucket's root to the dataset\n", 1071 | "train_instance_type='ml.m4.xlarge' # The type of EC2 instance which will be used for training\n", 1072 | "deploy_instance_type='ml.m4.xlarge' # The type of EC2 instance which will be used for deployment\n", 1073 | "hyperparameters={\n", 1074 | " \"learning_rate\": 1e-4,\n", 1075 | " \"decay\": 1e-6,\n", 1076 | " \"epochs\": epochs, \n", 1077 | " \"batch_size\": batchsize\n", 1078 | "}" 1079 | ] 1080 | }, 1081 | { 1082 | "cell_type": "code", 1083 | "execution_count": 17, 1084 | "metadata": {}, 1085 | "outputs": [], 1086 | "source": [ 1087 | "inputs = {'training': s3_train_data, 'validation': s3_validation_data}" 1088 | ] 1089 | }, 1090 | { 1091 | "cell_type": "code", 1092 | "execution_count": 18, 1093 | "metadata": {}, 1094 | "outputs": [], 1095 | "source": [ 1096 | "model_dir = '/opt/ml/model'" 1097 | ] 1098 | }, 1099 | { 1100 | "cell_type": "code", 1101 | "execution_count": null, 1102 | "metadata": { 1103 | "scrolled": false 1104 | }, 1105 | "outputs": [], 1106 | "source": [ 1107 | "my_estimator = TensorFlow(entry_point='train_nn.py',\n", 1108 | " role=role,\n", 1109 | " model_dir=model_dir,\n", 1110 | " framework_version='1.13', \n", 1111 | " train_instance_count=1,\n", 1112 | " train_instance_type=train_instance_type,\n", 1113 | " #train_instance_type='local',\n", 1114 | " py_version='py3',\n", 1115 | " script_mode=True,\n", 1116 | " base_job_name='Neural-Net-Fraud-Detection',\n", 1117 | " hyperparameters=hyperparameters\n", 1118 | " )\n", 1119 | "my_estimator.fit(inputs=inputs,logs=True)" 1120 | ] 1121 | }, 1122 | { 1123 | "cell_type": "markdown", 1124 | "metadata": {}, 1125 | "source": [ 1126 | "## Deploy our Trained Model on SageMaker Instances" 1127 | ] 1128 | }, 1129 | { 1130 | "cell_type": "markdown", 1131 | "metadata": {}, 1132 | "source": [ 1133 | "Note: Deployment process may take from 5-10mins !" 1134 | ] 1135 | }, 1136 | { 1137 | "cell_type": "code", 1138 | "execution_count": 20, 1139 | "metadata": { 1140 | "scrolled": true 1141 | }, 1142 | "outputs": [ 1143 | { 1144 | "name": "stdout", 1145 | "output_type": "stream", 1146 | "text": [ 1147 | "---------------------------------------------------------------------------------------------------!" 1148 | ] 1149 | } 1150 | ], 1151 | "source": [ 1152 | "my_estimator.name = 'deployed-neural-net-prediction'\n", 1153 | "my_predictor = my_estimator.deploy(initial_instance_count = 1, instance_type = deploy_instance_type)" 1154 | ] 1155 | }, 1156 | { 1157 | "cell_type": "markdown", 1158 | "metadata": {}, 1159 | "source": [ 1160 | "## Prediction on Test Dataset" 1161 | ] 1162 | }, 1163 | { 1164 | "cell_type": "code", 1165 | "execution_count": 21, 1166 | "metadata": {}, 1167 | "outputs": [], 1168 | "source": [ 1169 | "from sagemaker.predictor import csv_serializer \n", 1170 | "\n", 1171 | "my_predictor.content_type = 'text/csv'\n", 1172 | "my_predictor.serializer = csv_serializer\n", 1173 | "my_predictor.deserializer = None" 1174 | ] 1175 | }, 1176 | { 1177 | "cell_type": "code", 1178 | "execution_count": 22, 1179 | "metadata": {}, 1180 | "outputs": [], 1181 | "source": [ 1182 | "import json" 1183 | ] 1184 | }, 1185 | { 1186 | "cell_type": "code", 1187 | "execution_count": 23, 1188 | "metadata": {}, 1189 | "outputs": [ 1190 | { 1191 | "name": "stdout", 1192 | "output_type": "stream", 1193 | "text": [ 1194 | "No of rows to predict = 28481\n" 1195 | ] 1196 | } 1197 | ], 1198 | "source": [ 1199 | "print('No of rows to predict =',len(test_data))" 1200 | ] 1201 | }, 1202 | { 1203 | "cell_type": "code", 1204 | "execution_count": 24, 1205 | "metadata": {}, 1206 | "outputs": [], 1207 | "source": [ 1208 | "y_true = test_data.iloc[:,28:29]" 1209 | ] 1210 | }, 1211 | { 1212 | "cell_type": "code", 1213 | "execution_count": 25, 1214 | "metadata": {}, 1215 | "outputs": [ 1216 | { 1217 | "name": "stderr", 1218 | "output_type": "stream", 1219 | "text": [ 1220 | "/home/ec2-user/anaconda3/envs/tensorflow_p36/lib/python3.6/site-packages/ipykernel/__main__.py:12: FutureWarning: Method .as_matrix will be removed in a future version. Use .values instead.\n" 1221 | ] 1222 | } 1223 | ], 1224 | "source": [ 1225 | "def predict(data, rows=500):\n", 1226 | " split_array = np.array_split(data, int(data.shape[0] / float(rows) + 1))\n", 1227 | " predictions = []\n", 1228 | " for array in split_array:\n", 1229 | " x = my_predictor.predict(array).decode('utf-8')\n", 1230 | " x = json.loads(x)\n", 1231 | " x = np.array(x[\"predictions\"])\n", 1232 | " y = len(x)\n", 1233 | " predictions = np.append(predictions,x)\n", 1234 | " return predictions\n", 1235 | "\n", 1236 | "result_out = predict(test_data.as_matrix()[:,0:28])" 1237 | ] 1238 | }, 1239 | { 1240 | "cell_type": "code", 1241 | "execution_count": 26, 1242 | "metadata": {}, 1243 | "outputs": [], 1244 | "source": [ 1245 | "y_pred = (result_out>0.5)" 1246 | ] 1247 | }, 1248 | { 1249 | "cell_type": "code", 1250 | "execution_count": 27, 1251 | "metadata": {}, 1252 | "outputs": [], 1253 | "source": [ 1254 | "y_true = test_data.iloc[:,28:29]" 1255 | ] 1256 | }, 1257 | { 1258 | "cell_type": "code", 1259 | "execution_count": 28, 1260 | "metadata": {}, 1261 | "outputs": [ 1262 | { 1263 | "name": "stdout", 1264 | "output_type": "stream", 1265 | "text": [ 1266 | "No. of rows predicted = 28481\n" 1267 | ] 1268 | } 1269 | ], 1270 | "source": [ 1271 | "print('No. of rows predicted =',len(y_pred))" 1272 | ] 1273 | }, 1274 | { 1275 | "cell_type": "markdown", 1276 | "metadata": {}, 1277 | "source": [ 1278 | "## Analyzing our Results" 1279 | ] 1280 | }, 1281 | { 1282 | "cell_type": "code", 1283 | "execution_count": 29, 1284 | "metadata": {}, 1285 | "outputs": [ 1286 | { 1287 | "name": "stdout", 1288 | "output_type": "stream", 1289 | "text": [ 1290 | "Number of frauds: 46\n", 1291 | "Number of non-frauds: 28435\n", 1292 | "Percentage of fradulent data: 0.16151118289385907\n" 1293 | ] 1294 | } 1295 | ], 1296 | "source": [ 1297 | "test_nonfrauds, test_frauds = test_data.groupby('Class').size()\n", 1298 | "print('Number of frauds: ', test_frauds)\n", 1299 | "print('Number of non-frauds: ', test_nonfrauds)\n", 1300 | "print('Percentage of fradulent data:', 100.*test_frauds/(test_frauds + test_nonfrauds))" 1301 | ] 1302 | }, 1303 | { 1304 | "cell_type": "code", 1305 | "execution_count": 30, 1306 | "metadata": {}, 1307 | "outputs": [ 1308 | { 1309 | "data": { 1310 | "image/png": "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\n", 1311 | "text/plain": [ 1312 | "
" 1313 | ] 1314 | }, 1315 | "metadata": {}, 1316 | "output_type": "display_data" 1317 | } 1318 | ], 1319 | "source": [ 1320 | "from sklearn.metrics import confusion_matrix, precision_recall_curve\n", 1321 | "import seaborn as sns\n", 1322 | "import matplotlib.pyplot as plt\n", 1323 | "LABELS = [\"Normal\",\"Fraud\"]\n", 1324 | "conf_matrix = confusion_matrix(y_true=y_true, y_pred=y_pred)\n", 1325 | "tn, fp, fn, tp = conf_matrix.ravel() \n", 1326 | "plt.figure(figsize=(12, 12))\n", 1327 | "sns.heatmap(conf_matrix, xticklabels=LABELS, yticklabels=LABELS, annot=True, fmt=\"d\");\n", 1328 | "plt.title(\"Confusion matrix\")\n", 1329 | "plt.ylabel('True class')\n", 1330 | "plt.xlabel('Predicted class')\n", 1331 | "plt.show()" 1332 | ] 1333 | }, 1334 | { 1335 | "cell_type": "code", 1336 | "execution_count": 33, 1337 | "metadata": {}, 1338 | "outputs": [ 1339 | { 1340 | "name": "stdout", 1341 | "output_type": "stream", 1342 | "text": [ 1343 | " precision recall f1-score support\n", 1344 | "\n", 1345 | " 0 1.00 1.00 1.00 28435\n", 1346 | " 1 0.61 0.76 0.68 46\n", 1347 | "\n", 1348 | " accuracy 1.00 28481\n", 1349 | " macro avg 0.81 0.88 0.84 28481\n", 1350 | "weighted avg 1.00 1.00 1.00 28481\n", 1351 | "\n" 1352 | ] 1353 | } 1354 | ], 1355 | "source": [ 1356 | "from sklearn.metrics import classification_report\n", 1357 | "print(classification_report(y_true, y_pred))" 1358 | ] 1359 | }, 1360 | { 1361 | "cell_type": "code", 1362 | "execution_count": 36, 1363 | "metadata": {}, 1364 | "outputs": [], 1365 | "source": [ 1366 | "from sklearn.metrics import precision_score,accuracy_score, recall_score\n", 1367 | "accuracy = accuracy_score(y_true=y_true, y_pred=y_pred)\n", 1368 | "precision = precision_score(y_true=y_true, y_pred=y_pred)\n", 1369 | "recall = recall_score(y_true=y_true, y_pred=y_pred)" 1370 | ] 1371 | }, 1372 | { 1373 | "cell_type": "code", 1374 | "execution_count": 37, 1375 | "metadata": {}, 1376 | "outputs": [ 1377 | { 1378 | "name": "stdout", 1379 | "output_type": "stream", 1380 | "text": [ 1381 | "\n", 1382 | "Accuracy Score: 1.0\n", 1383 | "\n", 1384 | "Precision Score: 0.61\n", 1385 | "\n", 1386 | "Recall Score: 0.76\n" 1387 | ] 1388 | } 1389 | ], 1390 | "source": [ 1391 | "print (\"\")\n", 1392 | "print (\"Accuracy Score: \", round(accuracy, 2))\n", 1393 | "print (\"\")\n", 1394 | "print (\"Precision Score: \", round(precision, 2))\n", 1395 | "print (\"\")\n", 1396 | "print (\"Recall Score: \", round(recall, 2))" 1397 | ] 1398 | }, 1399 | { 1400 | "cell_type": "markdown", 1401 | "metadata": {}, 1402 | "source": [ 1403 | "## Data Acknowledgements\n", 1404 | "The dataset used to demonstrated the fraud detection solution has been collected and analysed during a research collaboration of Worldline and the Machine Learning Group (http://mlg.ulb.ac.be) of ULB (Université Libre de Bruxelles) on big data mining and fraud detection. More details on current and past projects on related topics are available on https://www.researchgate.net/project/Fraud-detection-5 and the page of the DefeatFraud project We cite the following works:\n", 1405 | "\n", 1406 | "- Andrea Dal Pozzolo, Olivier Caelen, Reid A. Johnson and Gianluca Bontempi. Calibrating Probability with Undersampling for Unbalanced Classification. In Symposium on Computational Intelligence and Data Mining (CIDM), IEEE, 2015\n", 1407 | "- Dal Pozzolo, Andrea; Caelen, Olivier; Le Borgne, Yann-Ael; Waterschoot, Serge; Bontempi, Gianluca. Learned lessons in credit card fraud detection from a practitioner perspective, Expert systems with applications,41,10,4915-4928,2014, Pergamon\n", 1408 | "- Dal Pozzolo, Andrea; Boracchi, Giacomo; Caelen, Olivier; Alippi, Cesare; Bontempi, Gianluca. Credit card fraud detection: a realistic modeling and a novel learning strategy, IEEE transactions on neural networks and learning systems,29,8,3784-3797,2018,IEEE\n", 1409 | "- Dal Pozzolo, Andrea Adaptive Machine learning for credit card fraud detection ULB MLG PhD thesis (supervised by G. Bontempi)\n", 1410 | "- Carcillo, Fabrizio; Dal Pozzolo, Andrea; Le Borgne, Yann-Aël; Caelen, Olivier; Mazzer, Yannis; Bontempi, Gianluca. Scarff: a scalable framework for streaming credit card fraud detection with Spark, Information fusion,41, 182-194,2018,Elsevier\n", 1411 | "- Carcillo, Fabrizio; Le Borgne, Yann-Aël; Caelen, Olivier; Bontempi, Gianluca. Streaming active learning strategies for real-life credit card fraud detection: assessment and visualization, International Journal of Data Science and Analytics, 5,4,285-300,2018,Springer International Publishing" 1412 | ] 1413 | } 1414 | ], 1415 | "metadata": { 1416 | "kernelspec": { 1417 | "display_name": "conda_tensorflow_p36", 1418 | "language": "python", 1419 | "name": "conda_tensorflow_p36" 1420 | }, 1421 | "language_info": { 1422 | "codemirror_mode": { 1423 | "name": "ipython", 1424 | "version": 3 1425 | }, 1426 | "file_extension": ".py", 1427 | "mimetype": "text/x-python", 1428 | "name": "python", 1429 | "nbconvert_exporter": "python", 1430 | "pygments_lexer": "ipython3", 1431 | "version": "3.6.5" 1432 | } 1433 | }, 1434 | "nbformat": 4, 1435 | "nbformat_minor": 2 1436 | } 1437 | -------------------------------------------------------------------------------- /notebooks/sagemaker_fraud_detection_xgb.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Credit card fraud detector" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "## Investigate and process the data" 15 | ] 16 | }, 17 | { 18 | "cell_type": "markdown", 19 | "metadata": {}, 20 | "source": [ 21 | "Let's start by downloading and reading in the credit card fraud data set." 22 | ] 23 | }, 24 | { 25 | "cell_type": "code", 26 | "execution_count": null, 27 | "metadata": {}, 28 | "outputs": [], 29 | "source": [ 30 | "%%bash\n", 31 | "wget https://s3-us-west-2.amazonaws.com/sagemaker-e2e-solutions/fraud-detection/creditcardfraud.zip\n", 32 | "unzip creditcardfraud.zip" 33 | ] 34 | }, 35 | { 36 | "cell_type": "code", 37 | "execution_count": 26, 38 | "metadata": {}, 39 | "outputs": [], 40 | "source": [ 41 | "import numpy as np \n", 42 | "import pandas as pd\n", 43 | "import matplotlib.pyplot as plt\n", 44 | "\n", 45 | "data = pd.read_csv('creditcard.csv', delimiter=',')" 46 | ] 47 | }, 48 | { 49 | "cell_type": "markdown", 50 | "metadata": {}, 51 | "source": [ 52 | "Let's take a peek at our data (we only show a subset of the columns in the table):" 53 | ] 54 | }, 55 | { 56 | "cell_type": "code", 57 | "execution_count": 27, 58 | "metadata": {}, 59 | "outputs": [ 60 | { 61 | "name": "stdout", 62 | "output_type": "stream", 63 | "text": [ 64 | "Index(['Time', 'V1', 'V2', 'V3', 'V4', 'V5', 'V6', 'V7', 'V8', 'V9', 'V10',\n", 65 | " 'V11', 'V12', 'V13', 'V14', 'V15', 'V16', 'V17', 'V18', 'V19', 'V20',\n", 66 | " 'V21', 'V22', 'V23', 'V24', 'V25', 'V26', 'V27', 'V28', 'Amount',\n", 67 | " 'Class'],\n", 68 | " dtype='object')\n" 69 | ] 70 | }, 71 | { 72 | "data": { 73 | "text/html": [ 74 | "
\n", 75 | "\n", 88 | "\n", 89 | " \n", 90 | " \n", 91 | " \n", 92 | " \n", 93 | " \n", 94 | " \n", 95 | " \n", 96 | " \n", 97 | " \n", 98 | " \n", 99 | " \n", 100 | " \n", 101 | " \n", 102 | " \n", 103 | " \n", 104 | " \n", 105 | " \n", 106 | " \n", 107 | " \n", 108 | " \n", 109 | " \n", 110 | " \n", 111 | " \n", 112 | " \n", 113 | " \n", 114 | " \n", 115 | " \n", 116 | " \n", 117 | " \n", 118 | " \n", 119 | " \n", 120 | " \n", 121 | " \n", 122 | " \n", 123 | " \n", 124 | " \n", 125 | " \n", 126 | " \n", 127 | " \n", 128 | " \n", 129 | " \n", 130 | " \n", 131 | " \n", 132 | " \n", 133 | " \n", 134 | " \n", 135 | " \n", 136 | " \n", 137 | " \n", 138 | " \n", 139 | " \n", 140 | " \n", 141 | " \n", 142 | " \n", 143 | " \n", 144 | " \n", 145 | " \n", 146 | " \n", 147 | " \n", 148 | " \n", 149 | " \n", 150 | " \n", 151 | " \n", 152 | " \n", 153 | " \n", 154 | " \n", 155 | " \n", 156 | " \n", 157 | " \n", 158 | " \n", 159 | " \n", 160 | " \n", 161 | " \n", 162 | " \n", 163 | " \n", 164 | " \n", 165 | " \n", 166 | " \n", 167 | " \n", 168 | " \n", 169 | " \n", 170 | " \n", 171 | " \n", 172 | " \n", 173 | " \n", 174 | " \n", 175 | " \n", 176 | " \n", 177 | " \n", 178 | " \n", 179 | " \n", 180 | " \n", 181 | " \n", 182 | " \n", 183 | " \n", 184 | " \n", 185 | " \n", 186 | " \n", 187 | " \n", 188 | " \n", 189 | " \n", 190 | " \n", 191 | " \n", 192 | " \n", 193 | " \n", 194 | " \n", 195 | " \n", 196 | " \n", 197 | " \n", 198 | " \n", 199 | " \n", 200 | " \n", 201 | " \n", 202 | " \n", 203 | " \n", 204 | " \n", 205 | " \n", 206 | " \n", 207 | " \n", 208 | " \n", 209 | " \n", 210 | " \n", 211 | " \n", 212 | " \n", 213 | " \n", 214 | " \n", 215 | " \n", 216 | " \n", 217 | " \n", 218 | " \n", 219 | " \n", 220 | " \n", 221 | " \n", 222 | " \n", 223 | " \n", 224 | " \n", 225 | " \n", 226 | " \n", 227 | " \n", 228 | " \n", 229 | " \n", 230 | " \n", 231 | " \n", 232 | " \n", 233 | " \n", 234 | " \n", 235 | " \n", 236 | " \n", 237 | " \n", 238 | " \n", 239 | " \n", 240 | " \n", 241 | " \n", 242 | " \n", 243 | " \n", 244 | " \n", 245 | " \n", 246 | " \n", 247 | " \n", 248 | " \n", 249 | " \n", 250 | " \n", 251 | " \n", 252 | " \n", 253 | " \n", 254 | " \n", 255 | " \n", 256 | " \n", 257 | " \n", 258 | " \n", 259 | " \n", 260 | " \n", 261 | " \n", 262 | " \n", 263 | " \n", 264 | " \n", 265 | " \n", 266 | " \n", 267 | " \n", 268 | " \n", 269 | " \n", 270 | " \n", 271 | " \n", 272 | " \n", 273 | " \n", 274 | " \n", 275 | " \n", 276 | " \n", 277 | " \n", 278 | " \n", 279 | " \n", 280 | " \n", 281 | " \n", 282 | " \n", 283 | " \n", 284 | " \n", 285 | " \n", 286 | " \n", 287 | " \n", 288 | " \n", 289 | " \n", 290 | " \n", 291 | " \n", 292 | " \n", 293 | " \n", 294 | " \n", 295 | " \n", 296 | " \n", 297 | " \n", 298 | " \n", 299 | " \n", 300 | " \n", 301 | " \n", 302 | " \n", 303 | " \n", 304 | " \n", 305 | " \n", 306 | " \n", 307 | " \n", 308 | " \n", 309 | " \n", 310 | " \n", 311 | " \n", 312 | " \n", 313 | " \n", 314 | " \n", 315 | " \n", 316 | " \n", 317 | " \n", 318 | " \n", 319 | " \n", 320 | " \n", 321 | " \n", 322 | " \n", 323 | " \n", 324 | " \n", 325 | " \n", 326 | " \n", 327 | " \n", 328 | " \n", 329 | " \n", 330 | " \n", 331 | " \n", 332 | " \n", 333 | " \n", 334 | " \n", 335 | " \n", 336 | " \n", 337 | " \n", 338 | " \n", 339 | " \n", 340 | " \n", 341 | " \n", 342 | " \n", 343 | " \n", 344 | " \n", 345 | " \n", 346 | " \n", 347 | " \n", 348 | " \n", 349 | " \n", 350 | " \n", 351 | " \n", 352 | " \n", 353 | " \n", 354 | " \n", 355 | " \n", 356 | " \n", 357 | "
TimeV1V2V3V4V5V6V7V8V9...V21V22V23V24V25V26V27V28AmountClass
00.0-1.359807-0.0727812.5363471.378155-0.3383210.4623880.2395990.0986980.363787...-0.0183070.277838-0.1104740.0669280.128539-0.1891150.133558-0.021053149.620
10.01.1918570.2661510.1664800.4481540.060018-0.082361-0.0788030.085102-0.255425...-0.225775-0.6386720.101288-0.3398460.1671700.125895-0.0089830.0147242.690
21.0-1.358354-1.3401631.7732090.379780-0.5031981.8004990.7914610.247676-1.514654...0.2479980.7716790.909412-0.689281-0.327642-0.139097-0.055353-0.059752378.660
31.0-0.966272-0.1852261.792993-0.863291-0.0103091.2472030.2376090.377436-1.387024...-0.1083000.005274-0.190321-1.1755750.647376-0.2219290.0627230.061458123.500
42.0-1.1582330.8777371.5487180.403034-0.4071930.0959210.592941-0.2705330.817739...-0.0094310.798278-0.1374580.141267-0.2060100.5022920.2194220.21515369.990
52.0-0.4259660.9605231.141109-0.1682520.420987-0.0297280.4762010.260314-0.568671...-0.208254-0.559825-0.026398-0.371427-0.2327940.1059150.2538440.0810803.670
64.01.2296580.1410040.0453711.2026130.1918810.272708-0.0051590.0812130.464960...-0.167716-0.270710-0.154104-0.7800550.750137-0.2572370.0345070.0051684.990
77.0-0.6442691.4179641.074380-0.4921990.9489340.4281181.120631-3.8078640.615375...1.943465-1.0154550.057504-0.649709-0.415267-0.051634-1.206921-1.08533940.800
87.0-0.8942860.286157-0.113192-0.2715262.6695993.7218180.3701450.851084-0.392048...-0.073425-0.268092-0.2042331.0115920.373205-0.3841570.0117470.14240493.200
99.0-0.3382621.1195931.044367-0.2221870.499361-0.2467610.6515830.069539-0.736727...-0.246914-0.633753-0.120794-0.385050-0.0697330.0941990.2462190.0830763.680
\n", 358 | "

10 rows × 31 columns

\n", 359 | "
" 360 | ], 361 | "text/plain": [ 362 | " Time V1 V2 V3 V4 V5 V6 V7 \\\n", 363 | "0 0.0 -1.359807 -0.072781 2.536347 1.378155 -0.338321 0.462388 0.239599 \n", 364 | "1 0.0 1.191857 0.266151 0.166480 0.448154 0.060018 -0.082361 -0.078803 \n", 365 | "2 1.0 -1.358354 -1.340163 1.773209 0.379780 -0.503198 1.800499 0.791461 \n", 366 | "3 1.0 -0.966272 -0.185226 1.792993 -0.863291 -0.010309 1.247203 0.237609 \n", 367 | "4 2.0 -1.158233 0.877737 1.548718 0.403034 -0.407193 0.095921 0.592941 \n", 368 | "5 2.0 -0.425966 0.960523 1.141109 -0.168252 0.420987 -0.029728 0.476201 \n", 369 | "6 4.0 1.229658 0.141004 0.045371 1.202613 0.191881 0.272708 -0.005159 \n", 370 | "7 7.0 -0.644269 1.417964 1.074380 -0.492199 0.948934 0.428118 1.120631 \n", 371 | "8 7.0 -0.894286 0.286157 -0.113192 -0.271526 2.669599 3.721818 0.370145 \n", 372 | "9 9.0 -0.338262 1.119593 1.044367 -0.222187 0.499361 -0.246761 0.651583 \n", 373 | "\n", 374 | " V8 V9 ... V21 V22 V23 V24 V25 \\\n", 375 | "0 0.098698 0.363787 ... -0.018307 0.277838 -0.110474 0.066928 0.128539 \n", 376 | "1 0.085102 -0.255425 ... -0.225775 -0.638672 0.101288 -0.339846 0.167170 \n", 377 | "2 0.247676 -1.514654 ... 0.247998 0.771679 0.909412 -0.689281 -0.327642 \n", 378 | "3 0.377436 -1.387024 ... -0.108300 0.005274 -0.190321 -1.175575 0.647376 \n", 379 | "4 -0.270533 0.817739 ... -0.009431 0.798278 -0.137458 0.141267 -0.206010 \n", 380 | "5 0.260314 -0.568671 ... -0.208254 -0.559825 -0.026398 -0.371427 -0.232794 \n", 381 | "6 0.081213 0.464960 ... -0.167716 -0.270710 -0.154104 -0.780055 0.750137 \n", 382 | "7 -3.807864 0.615375 ... 1.943465 -1.015455 0.057504 -0.649709 -0.415267 \n", 383 | "8 0.851084 -0.392048 ... -0.073425 -0.268092 -0.204233 1.011592 0.373205 \n", 384 | "9 0.069539 -0.736727 ... -0.246914 -0.633753 -0.120794 -0.385050 -0.069733 \n", 385 | "\n", 386 | " V26 V27 V28 Amount Class \n", 387 | "0 -0.189115 0.133558 -0.021053 149.62 0 \n", 388 | "1 0.125895 -0.008983 0.014724 2.69 0 \n", 389 | "2 -0.139097 -0.055353 -0.059752 378.66 0 \n", 390 | "3 -0.221929 0.062723 0.061458 123.50 0 \n", 391 | "4 0.502292 0.219422 0.215153 69.99 0 \n", 392 | "5 0.105915 0.253844 0.081080 3.67 0 \n", 393 | "6 -0.257237 0.034507 0.005168 4.99 0 \n", 394 | "7 -0.051634 -1.206921 -1.085339 40.80 0 \n", 395 | "8 -0.384157 0.011747 0.142404 93.20 0 \n", 396 | "9 0.094199 0.246219 0.083076 3.68 0 \n", 397 | "\n", 398 | "[10 rows x 31 columns]" 399 | ] 400 | }, 401 | "execution_count": 27, 402 | "metadata": {}, 403 | "output_type": "execute_result" 404 | } 405 | ], 406 | "source": [ 407 | "print(data.columns)\n", 408 | "data[['Time', 'V1', 'V2', 'V27', 'V28', 'Amount', 'Class']].describe()\n", 409 | "data.head(10)" 410 | ] 411 | }, 412 | { 413 | "cell_type": "markdown", 414 | "metadata": {}, 415 | "source": [ 416 | "The class column corresponds to whether or not a transaction is fradulent. We see that the majority of data is non-fraudulant with only $492$ ($.173\\%$) of the data corresponding to fraudulant examples." 417 | ] 418 | }, 419 | { 420 | "cell_type": "code", 421 | "execution_count": 28, 422 | "metadata": {}, 423 | "outputs": [ 424 | { 425 | "name": "stdout", 426 | "output_type": "stream", 427 | "text": [ 428 | "Number of frauds: 492\n", 429 | "Number of non-frauds: 284315\n", 430 | "Percentage of fradulent data: 0.1727485630620034\n" 431 | ] 432 | } 433 | ], 434 | "source": [ 435 | "nonfrauds, frauds = data.groupby('Class').size()\n", 436 | "print('Number of frauds: ', frauds)\n", 437 | "print('Number of non-frauds: ', nonfrauds)\n", 438 | "print('Percentage of fradulent data:', 100.*frauds/(frauds + nonfrauds))" 439 | ] 440 | }, 441 | { 442 | "cell_type": "markdown", 443 | "metadata": {}, 444 | "source": [ 445 | "This dataset has 28 columns, $V_i$ for $i=1..28$ of anonymized features along with columns for time, amount, and class. We already know that the columns $V_i$ have been normalized to have $0$ mean and unit standard deviation as the result of a PCA. You can read more about PCA here:. \n", 446 | "\n", 447 | "Tip: For our dataset this amount of preprocessing will give us reasonable accuracy, but it's important to note that there are more preprocessing steps one can use to improve accuracy . For unbalanced data sets like ours where the positive (fraudulent) examples occur much less frequently than the negative (legitimate) examples, we may try “over-sampling” the minority dataset by generating synthetic data (read about SMOTE in Data Mining for Imbalanced Datasets: An Overview (https://link.springer.com/chapter/10.1007%2F0-387-25465-X_40) or undersampling the majority class by using ensemble methods (see http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.68.6858&rep=rep1&type=pdfor)." 448 | ] 449 | }, 450 | { 451 | "cell_type": "code", 452 | "execution_count": 29, 453 | "metadata": {}, 454 | "outputs": [], 455 | "source": [ 456 | "feature_columns = data.columns[:-1]\n", 457 | "label_column = data.columns[-1]\n", 458 | "\n", 459 | "features = data[feature_columns].values.astype('float32')\n", 460 | "labels = (data[label_column].values).astype('float32')" 461 | ] 462 | }, 463 | { 464 | "cell_type": "markdown", 465 | "metadata": {}, 466 | "source": [ 467 | "Let's do some analysis and discuss different ways we can preprocess our data. Let's discuss the way in which this data was preprocessed." 468 | ] 469 | }, 470 | { 471 | "cell_type": "markdown", 472 | "metadata": {}, 473 | "source": [ 474 | "## SageMaker XGB" 475 | ] 476 | }, 477 | { 478 | "cell_type": "markdown", 479 | "metadata": {}, 480 | "source": [ 481 | "### Prepare Data and Upload to S3" 482 | ] 483 | }, 484 | { 485 | "cell_type": "markdown", 486 | "metadata": {}, 487 | "source": [ 488 | "The Amazon common libraries provide utilities to convert NumPy n-dimensional arrays into a the Record-IO format which SageMaker uses for a concise representation of features and labels. The Record-IO format is implemented via protocol buffer so the serialization is very efficient." 489 | ] 490 | }, 491 | { 492 | "cell_type": "code", 493 | "execution_count": 30, 494 | "metadata": {}, 495 | "outputs": [ 496 | { 497 | "data": { 498 | "text/html": [ 499 | "
\n", 500 | "\n", 513 | "\n", 514 | " \n", 515 | " \n", 516 | " \n", 517 | " \n", 518 | " \n", 519 | " \n", 520 | " \n", 521 | " \n", 522 | " \n", 523 | " \n", 524 | " \n", 525 | " \n", 526 | " \n", 527 | " \n", 528 | " \n", 529 | " \n", 530 | " \n", 531 | " \n", 532 | " \n", 533 | " \n", 534 | " \n", 535 | " \n", 536 | " \n", 537 | " \n", 538 | " \n", 539 | " \n", 540 | " \n", 541 | " \n", 542 | " \n", 543 | " \n", 544 | " \n", 545 | " \n", 546 | " \n", 547 | " \n", 548 | " \n", 549 | " \n", 550 | " \n", 551 | " \n", 552 | " \n", 553 | " \n", 554 | " \n", 555 | " \n", 556 | " \n", 557 | " \n", 558 | " \n", 559 | " \n", 560 | " \n", 561 | " \n", 562 | " \n", 563 | " \n", 564 | " \n", 565 | " \n", 566 | " \n", 567 | " \n", 568 | " \n", 569 | " \n", 570 | " \n", 571 | " \n", 572 | " \n", 573 | " \n", 574 | " \n", 575 | " \n", 576 | " \n", 577 | " \n", 578 | " \n", 579 | " \n", 580 | " \n", 581 | " \n", 582 | " \n", 583 | " \n", 584 | " \n", 585 | " \n", 586 | " \n", 587 | " \n", 588 | " \n", 589 | " \n", 590 | " \n", 591 | " \n", 592 | " \n", 593 | " \n", 594 | " \n", 595 | " \n", 596 | " \n", 597 | " \n", 598 | " \n", 599 | " \n", 600 | " \n", 601 | " \n", 602 | " \n", 603 | " \n", 604 | " \n", 605 | " \n", 606 | " \n", 607 | " \n", 608 | " \n", 609 | " \n", 610 | " \n", 611 | " \n", 612 | " \n", 613 | " \n", 614 | " \n", 615 | " \n", 616 | " \n", 617 | " \n", 618 | " \n", 619 | " \n", 620 | " \n", 621 | " \n", 622 | " \n", 623 | " \n", 624 | " \n", 625 | " \n", 626 | " \n", 627 | " \n", 628 | " \n", 629 | " \n", 630 | " \n", 631 | " \n", 632 | " \n", 633 | " \n", 634 | " \n", 635 | " \n", 636 | " \n", 637 | " \n", 638 | " \n", 639 | " \n", 640 | " \n", 641 | " \n", 642 | " \n", 643 | " \n", 644 | " \n", 645 | " \n", 646 | " \n", 647 | " \n", 648 | " \n", 649 | " \n", 650 | " \n", 651 | " \n", 652 | " \n", 653 | " \n", 654 | " \n", 655 | " \n", 656 | " \n", 657 | " \n", 658 | " \n", 659 | " \n", 660 | " \n", 661 | " \n", 662 | "
ClassTimeV1V2V3V4V5V6V7V8...V20V21V22V23V24V25V26V27V28Amount
000.0-1.359807-0.0727812.5363471.378155-0.3383210.4623880.2395990.098698...0.251412-0.0183070.277838-0.1104740.0669280.128539-0.1891150.133558-0.021053149.62
100.01.1918570.2661510.1664800.4481540.060018-0.082361-0.0788030.085102...-0.069083-0.225775-0.6386720.101288-0.3398460.1671700.125895-0.0089830.0147242.69
201.0-1.358354-1.3401631.7732090.379780-0.5031981.8004990.7914610.247676...0.5249800.2479980.7716790.909412-0.689281-0.327642-0.139097-0.055353-0.059752378.66
301.0-0.966272-0.1852261.792993-0.863291-0.0103091.2472030.2376090.377436...-0.208038-0.1083000.005274-0.190321-1.1755750.647376-0.2219290.0627230.061458123.50
402.0-1.1582330.8777371.5487180.403034-0.4071930.0959210.592941-0.270533...0.408542-0.0094310.798278-0.1374580.141267-0.2060100.5022920.2194220.21515369.99
\n", 663 | "

5 rows × 31 columns

\n", 664 | "
" 665 | ], 666 | "text/plain": [ 667 | " Class Time V1 V2 V3 V4 V5 V6 \\\n", 668 | "0 0 0.0 -1.359807 -0.072781 2.536347 1.378155 -0.338321 0.462388 \n", 669 | "1 0 0.0 1.191857 0.266151 0.166480 0.448154 0.060018 -0.082361 \n", 670 | "2 0 1.0 -1.358354 -1.340163 1.773209 0.379780 -0.503198 1.800499 \n", 671 | "3 0 1.0 -0.966272 -0.185226 1.792993 -0.863291 -0.010309 1.247203 \n", 672 | "4 0 2.0 -1.158233 0.877737 1.548718 0.403034 -0.407193 0.095921 \n", 673 | "\n", 674 | " V7 V8 ... V20 V21 V22 V23 V24 \\\n", 675 | "0 0.239599 0.098698 ... 0.251412 -0.018307 0.277838 -0.110474 0.066928 \n", 676 | "1 -0.078803 0.085102 ... -0.069083 -0.225775 -0.638672 0.101288 -0.339846 \n", 677 | "2 0.791461 0.247676 ... 0.524980 0.247998 0.771679 0.909412 -0.689281 \n", 678 | "3 0.237609 0.377436 ... -0.208038 -0.108300 0.005274 -0.190321 -1.175575 \n", 679 | "4 0.592941 -0.270533 ... 0.408542 -0.009431 0.798278 -0.137458 0.141267 \n", 680 | "\n", 681 | " V25 V26 V27 V28 Amount \n", 682 | "0 0.128539 -0.189115 0.133558 -0.021053 149.62 \n", 683 | "1 0.167170 0.125895 -0.008983 0.014724 2.69 \n", 684 | "2 -0.327642 -0.139097 -0.055353 -0.059752 378.66 \n", 685 | "3 0.647376 -0.221929 0.062723 0.061458 123.50 \n", 686 | "4 -0.206010 0.502292 0.219422 0.215153 69.99 \n", 687 | "\n", 688 | "[5 rows x 31 columns]" 689 | ] 690 | }, 691 | "execution_count": 30, 692 | "metadata": {}, 693 | "output_type": "execute_result" 694 | } 695 | ], 696 | "source": [ 697 | "model_data = data\n", 698 | "model_data.head()\n", 699 | "model_data = pd.concat([model_data['Class'], model_data.drop(['Class'], axis=1)], axis=1)\n", 700 | "model_data.head()\n" 701 | ] 702 | }, 703 | { 704 | "cell_type": "markdown", 705 | "metadata": {}, 706 | "source": [ 707 | "### Now we upload the data to S3 using boto3." 708 | ] 709 | }, 710 | { 711 | "cell_type": "code", 712 | "execution_count": 32, 713 | "metadata": {}, 714 | "outputs": [ 715 | { 716 | "name": "stdout", 717 | "output_type": "stream", 718 | "text": [ 719 | "Uploaded training data location: s3://sagemaker-us-east-1-282128611277/sagemaker/DEMO-xgboost-fraud/train/train.csv\n", 720 | "Uploaded training data location: s3://sagemaker-us-east-1-282128611277/sagemaker/DEMO-xgboost-fraud/validation/validation.csv\n", 721 | "Training artifacts will be uploaded to: s3://sagemaker-us-east-1-282128611277/sagemaker/DEMO-xgboost-fraud/output\n" 722 | ] 723 | } 724 | ], 725 | "source": [ 726 | "import boto3\n", 727 | "import os\n", 728 | "import sagemaker\n", 729 | "\n", 730 | "session = sagemaker.Session()\n", 731 | "\n", 732 | "bucket = session.default_bucket()\n", 733 | "sagemaker_iam_role = sagemaker.get_execution_role()\n", 734 | "\n", 735 | "prefix = 'sagemaker/DEMO-xgboost-fraud'\n", 736 | "\n", 737 | "train_data, validation_data, test_data = np.split(model_data.sample(frac=1, random_state=1729), \n", 738 | " [int(0.7 * len(model_data)), int(0.9 * len(model_data))])\n", 739 | "train_data.to_csv('train.csv', header=False, index=False)\n", 740 | "validation_data.to_csv('validation.csv', header=False, index=False)\n", 741 | "\n", 742 | "\n", 743 | "boto3.Session().resource('s3').Bucket(bucket).Object(os.path.join(prefix, 'train/train.csv')) \\\n", 744 | " .upload_file('train.csv')\n", 745 | "boto3.Session().resource('s3').Bucket(bucket).Object(os.path.join(prefix, 'validation/validation.csv')) \\\n", 746 | " .upload_file('validation.csv')\n", 747 | "s3_train_data = 's3://{}/{}/train/train.csv'.format(bucket, prefix)\n", 748 | "s3_validation_data = 's3://{}/{}/validation/validation.csv'.format(bucket, prefix)\n", 749 | "print('Uploaded training data location: {}'.format(s3_train_data))\n", 750 | "print('Uploaded training data location: {}'.format(s3_validation_data))\n", 751 | "\n", 752 | "output_location = 's3://{}/{}/output'.format(bucket, prefix)\n", 753 | "print('Training artifacts will be uploaded to: {}'.format(output_location))" 754 | ] 755 | }, 756 | { 757 | "cell_type": "markdown", 758 | "metadata": {}, 759 | "source": [ 760 | "---\n", 761 | "## Train\n", 762 | "\n", 763 | "Moving onto training, first we'll need to specify the locations of the XGBoost algorithm containers.\n", 764 | "To specify the Linear Learner algorithm, we use a utility function to obtain it's URI. A complete list of build-in algorithms is found here: https://docs.aws.amazon.com/sagemaker/latest/dg/algos.html" 765 | ] 766 | }, 767 | { 768 | "cell_type": "code", 769 | "execution_count": 33, 770 | "metadata": {}, 771 | "outputs": [ 772 | { 773 | "name": "stderr", 774 | "output_type": "stream", 775 | "text": [ 776 | "WARNING:root:There is a more up to date SageMaker XGBoost image.To use the newer image, please set 'repo_version'='0.90-1. For example:\n", 777 | "\tget_image_uri(region, 'xgboost', '0.90-1').\n" 778 | ] 779 | } 780 | ], 781 | "source": [ 782 | "from sagemaker.amazon.amazon_estimator import get_image_uri\n", 783 | "container = get_image_uri(boto3.Session().region_name, 'xgboost')" 784 | ] 785 | }, 786 | { 787 | "cell_type": "markdown", 788 | "metadata": {}, 789 | "source": [ 790 | "Then, because we're training with the CSV file format, we'll create s3_inputs that our training function can use as a pointer to the files in S3." 791 | ] 792 | }, 793 | { 794 | "cell_type": "code", 795 | "execution_count": 34, 796 | "metadata": {}, 797 | "outputs": [], 798 | "source": [ 799 | "s3_input_train = sagemaker.s3_input(s3_data='s3://{}/{}/train'.format(bucket, prefix), content_type='csv')\n", 800 | "s3_input_validation = sagemaker.s3_input(s3_data='s3://{}/{}/validation/'.format(bucket, prefix), content_type='csv')" 801 | ] 802 | }, 803 | { 804 | "cell_type": "markdown", 805 | "metadata": {}, 806 | "source": [ 807 | "Now, we can specify a few parameters like what type of training instances we'd like to use and how many, as well as our XGBoost hyperparameters. A few key hyperparameters are:\n", 808 | "- `max_depth` controls how deep each tree within the algorithm can be built. Deeper trees can lead to better fit, but are more computationally expensive and can lead to overfitting. There is typically some trade-off in model performance that needs to be explored between a large number of shallow trees and a smaller number of deeper trees.\n", 809 | "- `subsample` controls sampling of the training data. This technique can help reduce overfitting, but setting it too low can also starve the model of data.\n", 810 | "- `num_round` controls the number of boosting rounds. This is essentially the subsequent models that are trained using the residuals of previous iterations. Again, more rounds should produce a better fit on the training data, but can be computationally expensive or lead to overfitting.\n", 811 | "- `eta` controls how aggressive each round of boosting is. Larger values lead to more conservative boosting.\n", 812 | "- `gamma` controls how aggressively trees are grown. Larger values lead to more conservative models.\n", 813 | "\n", 814 | "More detail on XGBoost's hyperparmeters can be found on their GitHub [page](https://github.com/dmlc/xgboost/blob/master/doc/parameter.md)." 815 | ] 816 | }, 817 | { 818 | "cell_type": "markdown", 819 | "metadata": {}, 820 | "source": [ 821 | "SageMaker abstracts training with Estimators. We can pass container, and all parameters to the estimator, as well as the hyperparameters for the linear learner and fit the estimator to the data in S3.\n", 822 | "Note: For IP protection reasons, SageMaker built-in algorithms, such as XGBoost, can't be run locally, i.e. on the same instance where this Jupyter Notebook code is running. " 823 | ] 824 | }, 825 | { 826 | "cell_type": "code", 827 | "execution_count": 35, 828 | "metadata": {}, 829 | "outputs": [], 830 | "source": [ 831 | "xgb = sagemaker.estimator.Estimator(container,\n", 832 | " role=sagemaker_iam_role, \n", 833 | " train_instance_count=1, \n", 834 | " train_instance_type='ml.m4.xlarge',\n", 835 | " output_path=output_location,\n", 836 | " sagemaker_session=session)\n", 837 | "xgb.set_hyperparameters(max_depth=5,\n", 838 | " eta=0.2,\n", 839 | " gamma=4,\n", 840 | " min_child_weight=6,\n", 841 | " subsample=0.8,\n", 842 | " silent=0,\n", 843 | " objective='binary:logistic',\n", 844 | " num_round=100)" 845 | ] 846 | }, 847 | { 848 | "cell_type": "code", 849 | "execution_count": null, 850 | "metadata": {}, 851 | "outputs": [], 852 | "source": [ 853 | "xgb.fit({'train': s3_input_train, 'validation': s3_input_validation}) " 854 | ] 855 | }, 856 | { 857 | "cell_type": "markdown", 858 | "metadata": {}, 859 | "source": [ 860 | "### Host XGBoost Model" 861 | ] 862 | }, 863 | { 864 | "cell_type": "markdown", 865 | "metadata": {}, 866 | "source": [ 867 | "Now we deploy the estimator to and endpoint." 868 | ] 869 | }, 870 | { 871 | "cell_type": "code", 872 | "execution_count": 38, 873 | "metadata": {}, 874 | "outputs": [ 875 | { 876 | "name": "stderr", 877 | "output_type": "stream", 878 | "text": [ 879 | "WARNING:sagemaker:Using already existing model: xgboost-2019-12-03-21-58-34-726\n" 880 | ] 881 | }, 882 | { 883 | "name": "stdout", 884 | "output_type": "stream", 885 | "text": [ 886 | "---------------------------------------------------------------------------------------------------------------!" 887 | ] 888 | } 889 | ], 890 | "source": [ 891 | "xgb.name = 'deployed-xgboost-fraud-prediction'\n", 892 | "xgb_predictor = xgb.deploy(initial_instance_count = 1, instance_type = 'ml.m4.xlarge',\n", 893 | " endpoint_name='deployed-xgboost-fraud-prediction')" 894 | ] 895 | }, 896 | { 897 | "cell_type": "markdown", 898 | "metadata": {}, 899 | "source": [ 900 | "### Evaluate\n", 901 | "\n", 902 | "Now that we have a hosted endpoint running, we can make real-time predictions from our model very easily, \n", 903 | "simply by making an http POST request. But first, we'll need to setup serializers and deserializers for passing our `test_data` NumPy arrays to the model behind the endpoint." 904 | ] 905 | }, 906 | { 907 | "cell_type": "code", 908 | "execution_count": 39, 909 | "metadata": {}, 910 | "outputs": [], 911 | "source": [ 912 | "from sagemaker.predictor import csv_serializer \n", 913 | "\n", 914 | "xgb_predictor.content_type = 'text/csv'\n", 915 | "xgb_predictor.serializer = csv_serializer\n", 916 | "xgb_predictor.deserializer = None" 917 | ] 918 | }, 919 | { 920 | "cell_type": "markdown", 921 | "metadata": {}, 922 | "source": [ 923 | "Now, we'll use a simple function to:\n", 924 | "1. Loop over our test dataset\n", 925 | "1. Split it into mini-batches of rows \n", 926 | "1. Convert those mini-batchs to CSV string payloads\n", 927 | "1. Retrieve mini-batch predictions by invoking the XGBoost endpoint\n", 928 | "1. Collect predictions and convert from the CSV output our model provides into a NumPy array" 929 | ] 930 | }, 931 | { 932 | "cell_type": "code", 933 | "execution_count": 40, 934 | "metadata": {}, 935 | "outputs": [ 936 | { 937 | "name": "stderr", 938 | "output_type": "stream", 939 | "text": [ 940 | "/home/ec2-user/anaconda3/envs/mxnet_p36/lib/python3.6/site-packages/ipykernel/__main__.py:9: FutureWarning: Method .as_matrix will be removed in a future version. Use .values instead.\n" 941 | ] 942 | } 943 | ], 944 | "source": [ 945 | "def predict(data, rows=500):\n", 946 | " split_array = np.array_split(data, int(data.shape[0] / float(rows) + 1))\n", 947 | " predictions = ''\n", 948 | " for array in split_array:\n", 949 | " predictions = ','.join([predictions, xgb_predictor.predict(array).decode('utf-8')])\n", 950 | "\n", 951 | " return np.fromstring(predictions[1:], sep=',')\n", 952 | "\n", 953 | "predictions = predict(test_data.as_matrix()[:, 1:])" 954 | ] 955 | }, 956 | { 957 | "cell_type": "markdown", 958 | "metadata": {}, 959 | "source": [ 960 | "There are many ways to compare the performance of a machine learning model, but let's start by simply by comparing actual to predicted values. In this case, we're simply predicting whether the customer churned (1) or not (0), which produces a simple confusion matrix." 961 | ] 962 | }, 963 | { 964 | "cell_type": "code", 965 | "execution_count": 41, 966 | "metadata": {}, 967 | "outputs": [ 968 | { 969 | "name": "stdout", 970 | "output_type": "stream", 971 | "text": [ 972 | "Number of frauds: 54\n", 973 | "Number of non-frauds: 28427\n", 974 | "Percentage of fradulent data: 0.1896000842667041\n" 975 | ] 976 | } 977 | ], 978 | "source": [ 979 | "test_nonfrauds, test_frauds = test_data.groupby('Class').size()\n", 980 | "print('Number of frauds: ', test_frauds)\n", 981 | "print('Number of non-frauds: ', test_nonfrauds)\n", 982 | "print('Percentage of fradulent data:', 100.*test_frauds/(test_frauds + test_nonfrauds))" 983 | ] 984 | }, 985 | { 986 | "cell_type": "code", 987 | "execution_count": 42, 988 | "metadata": {}, 989 | "outputs": [ 990 | { 991 | "data": { 992 | "text/html": [ 993 | "
\n", 994 | "\n", 1007 | "\n", 1008 | " \n", 1009 | " \n", 1010 | " \n", 1011 | " \n", 1012 | " \n", 1013 | " \n", 1014 | " \n", 1015 | " \n", 1016 | " \n", 1017 | " \n", 1018 | " \n", 1019 | " \n", 1020 | " \n", 1021 | " \n", 1022 | " \n", 1023 | " \n", 1024 | " \n", 1025 | " \n", 1026 | " \n", 1027 | " \n", 1028 | " \n", 1029 | " \n", 1030 | " \n", 1031 | " \n", 1032 | "
predictions0.01.0
actual
0284261
11440
\n", 1033 | "
" 1034 | ], 1035 | "text/plain": [ 1036 | "predictions 0.0 1.0\n", 1037 | "actual \n", 1038 | "0 28426 1\n", 1039 | "1 14 40" 1040 | ] 1041 | }, 1042 | "execution_count": 42, 1043 | "metadata": {}, 1044 | "output_type": "execute_result" 1045 | } 1046 | ], 1047 | "source": [ 1048 | "pd.crosstab(index=test_data.iloc[:, 0], columns=np.round(predictions), rownames=['actual'], colnames=['predictions'])" 1049 | ] 1050 | }, 1051 | { 1052 | "cell_type": "code", 1053 | "execution_count": 43, 1054 | "metadata": {}, 1055 | "outputs": [ 1056 | { 1057 | "name": "stdout", 1058 | "output_type": "stream", 1059 | "text": [ 1060 | "precision: 0.98\n", 1061 | "recall: 0.74\n" 1062 | ] 1063 | } 1064 | ], 1065 | "source": [ 1066 | "#precision: tp / (tp + fp)\n", 1067 | "#recall: tp / (tp + fn)\n", 1068 | "from sklearn.metrics import precision_recall_fscore_support\n", 1069 | "results = precision_recall_fscore_support(test_data.iloc[:, 0],\n", 1070 | " np.round(predictions))\n", 1071 | "print('precision: ', round(results[0][1], 2))\n", 1072 | "print('recall: ', round(results[1][1], 2))" 1073 | ] 1074 | }, 1075 | { 1076 | "cell_type": "markdown", 1077 | "metadata": {}, 1078 | "source": [ 1079 | "Note, due to randomized elements of the algorithm, you results may differ slightly.\n", 1080 | "\n", 1081 | "Of the 54 fraudsters, we've correctly predicted 40 of them (true positives). And, we incorrectly predicted 1 case of fraud (false positive). There are also 14 cases of fraud that the model classified as benign transaction (false negatives) - which can get really expensive.\n", 1082 | "\n", 1083 | "An important point here is that because of the np.round() function above we are using a simple threshold (or cutoff) of 0.5. Our predictions from xgboost come out as continuous values between 0 and 1 and we force them into the binary classes that we began with. So, we should consider adjusting this cutoff. That will almost certainly increase the number of false positives, but it can also be expected to increase the number of true positives and reduce the number of false negatives.\n", 1084 | "\n", 1085 | "To get a rough intuition here, let's look at the continuous values of our predictions." 1086 | ] 1087 | }, 1088 | { 1089 | "cell_type": "code", 1090 | "execution_count": 44, 1091 | "metadata": {}, 1092 | "outputs": [ 1093 | { 1094 | "data": { 1095 | "image/png": "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\n", 1096 | "text/plain": [ 1097 | "
" 1098 | ] 1099 | }, 1100 | "metadata": {}, 1101 | "output_type": "display_data" 1102 | } 1103 | ], 1104 | "source": [ 1105 | "plt.hist(predictions)\n", 1106 | "plt.show()" 1107 | ] 1108 | }, 1109 | { 1110 | "cell_type": "markdown", 1111 | "metadata": {}, 1112 | "source": [ 1113 | "By varying the cutoff threshold, we can trade false positives for false negatives. " 1114 | ] 1115 | }, 1116 | { 1117 | "cell_type": "code", 1118 | "execution_count": 45, 1119 | "metadata": {}, 1120 | "outputs": [ 1121 | { 1122 | "data": { 1123 | "text/html": [ 1124 | "
\n", 1125 | "\n", 1138 | "\n", 1139 | " \n", 1140 | " \n", 1141 | " \n", 1142 | " \n", 1143 | " \n", 1144 | " \n", 1145 | " \n", 1146 | " \n", 1147 | " \n", 1148 | " \n", 1149 | " \n", 1150 | " \n", 1151 | " \n", 1152 | " \n", 1153 | " \n", 1154 | " \n", 1155 | " \n", 1156 | " \n", 1157 | " \n", 1158 | " \n", 1159 | " \n", 1160 | " \n", 1161 | " \n", 1162 | " \n", 1163 | "
col_001
Class
02841116
1747
\n", 1164 | "
" 1165 | ], 1166 | "text/plain": [ 1167 | "col_0 0 1\n", 1168 | "Class \n", 1169 | "0 28411 16\n", 1170 | "1 7 47" 1171 | ] 1172 | }, 1173 | "execution_count": 45, 1174 | "metadata": {}, 1175 | "output_type": "execute_result" 1176 | } 1177 | ], 1178 | "source": [ 1179 | "pd.crosstab(index=test_data.iloc[:, 0], columns=np.where(predictions > 0.04, 1, 0))" 1180 | ] 1181 | }, 1182 | { 1183 | "cell_type": "code", 1184 | "execution_count": 46, 1185 | "metadata": {}, 1186 | "outputs": [ 1187 | { 1188 | "name": "stdout", 1189 | "output_type": "stream", 1190 | "text": [ 1191 | "precision: 0.75\n", 1192 | "recall: 0.87\n" 1193 | ] 1194 | } 1195 | ], 1196 | "source": [ 1197 | "results = precision_recall_fscore_support(test_data.iloc[:, 0],\n", 1198 | " np.where(predictions > 0.04, 1, 0))\n", 1199 | "print('precision: ', round(results[0][1], 2))\n", 1200 | "print('recall: ', round(results[1][1], 2))" 1201 | ] 1202 | }, 1203 | { 1204 | "cell_type": "code", 1205 | "execution_count": 47, 1206 | "metadata": {}, 1207 | "outputs": [ 1208 | { 1209 | "data": { 1210 | "image/png": "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\n", 1211 | "text/plain": [ 1212 | "
" 1213 | ] 1214 | }, 1215 | "metadata": {}, 1216 | "output_type": "display_data" 1217 | } 1218 | ], 1219 | "source": [ 1220 | "plt.hist(predictions)\n", 1221 | "plt.show()" 1222 | ] 1223 | }, 1224 | { 1225 | "cell_type": "markdown", 1226 | "metadata": {}, 1227 | "source": [ 1228 | "### Relative cost of errors\n", 1229 | "\n", 1230 | "Any practical binary classification problem is likely to produce a similarly sensitive cutoff. \n", 1231 | "If we put an ML model into production, there are costs associated with the model erroneously assigning false positives and false negatives. Because the choice of the cutoff affects all four of these statistics, we need to consider the relative costs to the business for each of these four outcomes for each prediction.\n", 1232 | "\n", 1233 | "#### Assigning costs\n", 1234 | "\n", 1235 | "What are the costs for our problem fraud detection? The costs, of course, depend on the specific actions that the business takes. Let's make some assumptions here.\n", 1236 | "\n", 1237 | "First, assign the cost of \\$0.00 to both the true negatives (correctly recognized benign transactions) and true positives (correctly recognized fraudulent transactions). Our model essentially correctly identified both situations. One can assign a benefit (i.e. negative cost) to correctly detected fraud, but we are not going to do this here.\n", 1238 | "\n", 1239 | "False negatives are the most problematic, because they represent a fraudulent transactions that slipped through our model. Based on some Internet research (see sources below), we assign a cost of \\$450.00 for each one. This is the cost of false negatives.\n", 1240 | "\n", 1241 | "Finally, False positives are the genuine transactions that our model would block as fraud. This would result in an annoyed customer that might possibly close the credit card account and move to another bank. We assume that it costs a \\$500.00 sign-on bonus to obtain a cr. card customer and that \\5 percent of annoyed customers would defect. \n", 1242 | "\n", 1243 | "Source:\n", 1244 | "\n", 1245 | "https://www.creditcards.com/credit-card-news/credit-card-security-id-theft-fraud-statistics-1276.php\n", 1246 | "https://wallethub.com/edu/cc/credit-debit-card-fraud-statistics/25725/\n" 1247 | ] 1248 | }, 1249 | { 1250 | "cell_type": "markdown", 1251 | "metadata": {}, 1252 | "source": [ 1253 | "#### Finding the optimal cutoff\n", 1254 | "\n", 1255 | "It’s clear that false negatives are substantially more costly than false positives. We should be minimizing a cost function that looks like this:\n", 1256 | "\n", 1257 | "```txt\n", 1258 | "$450 * FN(C) + $0 * TN(C) + 0.05*$500 * FP(C) + $0 * TP(C)\n", 1259 | "```\n", 1260 | "\n", 1261 | "FN(C) means that the false negative percentage is a function of the cutoff, C, and similar for TN, FP, and TP. We need to find the cutoff, C, where the result of the expression is smallest.\n", 1262 | "\n", 1263 | "A straightforward way to do this, is to simply run a simulation over a large number of possible cutoffs. We test 100 possible values in the for loop below." 1264 | ] 1265 | }, 1266 | { 1267 | "cell_type": "code", 1268 | "execution_count": 48, 1269 | "metadata": {}, 1270 | "outputs": [ 1271 | { 1272 | "data": { 1273 | "image/png": "iVBORw0KGgoAAAANSUhEUgAAAYcAAAD8CAYAAACcjGjIAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAADl0RVh0U29mdHdhcmUAbWF0cGxvdGxpYiB2ZXJzaW9uIDMuMC4zLCBodHRwOi8vbWF0cGxvdGxpYi5vcmcvnQurowAAIABJREFUeJzt3Xt0nXWd7/H3N0nTNOklTRNKL2nT0hZOAbllShFREQ8UnKGsEbWoQ9UeOUsBzxk8jnJmzsKFMkvHcVSOClOlUhilVLzQEQRBUTj0AsFeKAXa0CbdKb3k0qRN0ub6PX/sJ3SbpE26d/Z+9t75vNbKyt6/57ef/f21aT59nt/veba5OyIiIrFywi5ARETSj8JBREQGUDiIiMgACgcRERlA4SAiIgMoHEREZACFg4iIDKBwEBGRARQOIiIyQF7YBcSrtLTUKyoqwi5DRCSjvPLKKw3uXjZUv4wNh4qKCqqqqsIuQ0Qko5hZ7XD66bSSiIgMMGQ4mNkqMztkZtv7td9uZm+Y2Wtm9i8x7XeaWbWZvWlm18S0Lwnaqs3sKzHtc8xsU9D+qJnlj9TgREQkPsM5cngQWBLbYGZXAkuBC9z9XOBfg/aFwDLg3OA1PzSzXDPLBX4AXAssBG4K+gJ8E/iOu88DDgMrEh2UiIgkZshwcPfngaZ+zZ8DvuHuHUGfQ0H7UmCNu3e4+x6gGlgUfFW7+2537wTWAEvNzIAPAI8Fr18N3JDgmEREJEHxzjksAK4ITgf9ycz+KmifAURi+tUFbSdrnwI0u3t3v/ZBmdktZlZlZlX19fVxli4iIkOJNxzygBJgMfAlYG1wFJBU7r7S3SvdvbKsbMiVWCIiEqd4l7LWAb/06MfIvWRmvUApsA8oj+k3M2jjJO2NQLGZ5QVHD7H9RUQkJPEeOfwauBLAzBYA+UADsA5YZmZjzWwOMB94CXgZmB+sTMonOmm9LgiX54Abg/0uBx6PdzAiItnspT1NfPfZnRzv6kn6ew1nKesjwAbgbDOrM7MVwCpgbrC8dQ2w3KNeA9YCO4CngFvdvSc4KrgNeBp4HVgb9AX4MnCHmVUTnYN4YGSHKCKSHda/1cB3n91Fbk7Sz+IPfVrJ3W86yaZPnqT/PcA9g7Q/CTw5SPtuoquZRETkFBpbOykuHMOY3ORfv6wrpEVEMkRTWydTilJznbDCQUQkQzS0djClaGxK3kvhICKSIRrbOpkyXkcOIiISo7G1Q+EgIiIndPf0cri9S6eVRETkhKb2TgBKdeQgIiJ9mtqi4VCiIwcREenT2BoNB805iIjIOxpaOwCdVhIRkRjvHDnotJKIiPRpbOsgN8eYNG5MSt5P4SAikgGa2jopKconJwU33QOFg4hIRmhoTd19lUDhICKSEVJ5dTQoHEREMkJjW2fKJqNB4SAikhEaW1N30z1QOIiIpL3jXT20dnRTOl5HDiIiEjhx6wwdOYiISODEBXAKBxERCTS0RW+dMUWnlUREpE/fkUOq7qsECgcRkbTX2KojBxER6aeprZP8vByK8nNT9p5DhoOZrTKzQ2a2fZBtXzQzN7PS4LmZ2b1mVm1m28zs4pi+y81sV/C1PKb9EjN7NXjNvWaWmhuHiIhkiIbWTkqL8knlr8fhHDk8CCzp32hm5cDVwN6Y5muB+cHXLcB9Qd8S4C7gUmARcJeZTQ5ecx/w2ZjXDXgvEZHRrLGtI6WnlGAY4eDuzwNNg2z6DvAPgMe0LQUe8qiNQLGZTQOuAZ5x9yZ3Pww8AywJtk10943u7sBDwA2JDUlEJLuk+upoiHPOwcyWAvvcfWu/TTOASMzzuqDtVO11g7SLiEigsbUjpfdVAsg73ReYWSHwv4meUkopM7uF6OkqZs2aleq3FxFJOXeP3nQvA44czgLmAFvNrAaYCfzZzM4E9gHlMX1nBm2nap85SPug3H2lu1e6e2VZWVkcpYuIZJa2zh46untTenU0xBEO7v6qu5/h7hXuXkH0VNDF7n4AWAfcHKxaWgy0uPt+4GngajObHExEXw08HWw7YmaLg1VKNwOPj9DYREQyXhjXOMDwlrI+AmwAzjazOjNbcYruTwK7gWrgR8DnAdy9Cfga8HLwdXfQRtDnx8Fr3gJ+G99QRESyT0PffZVSfFppyDkHd79piO0VMY8duPUk/VYBqwZprwLOG6oOEZHRqO/IoTTFE9K6QlpEJI313a47EyakRUQkRRpD+CwHUDiIiKS1+qMdjB+bR8GY1N1XCRQOIiJpLdLUzszJ41L+vgoHEZE0VtPYRsWUopS/r8JBRCRN9fQ6kaZjzC4tTPl7KxxERNLU283H6Ozp1ZGDiIicUNvYDqBwEBGRE/Y0tgFQodNKIiLSp7ahjbF5OUydUJDy91Y4iIikqZrGdiqmFJGTk/pPT1Y4iIikqZrGNmZPSf0pJVA4iIikpZ5eZ29jO3NKUz8ZDQoHEZG0dODIcTp7epkdwkolUDiIiKSlmoZgpZJOK4mISJ+ad5ax6shBREQCtY3t5OflcObE1C9jBYWDiEha2tPQxuySwlCWsYLCQUQkLdU2toV2SgkUDiIiaae316ltbA9tMhoUDiIiaefAkeN0dIe3jBUUDiIiaadvpVJYF8CBwkFEJO3UNERv1R3WrTNgGOFgZqvM7JCZbY9p+5aZvWFm28zsV2ZWHLPtTjOrNrM3zeyamPYlQVu1mX0lpn2OmW0K2h81s/yRHKCISCZo7ejmjQNHeOPAEbZGmsnPzWHapNR/dnSf4Rw5PAgs6df2DHCeu78L2AncCWBmC4FlwLnBa35oZrlmlgv8ALgWWAjcFPQF+CbwHXefBxwGViQ0IhGRDPTZ1VUs+e4LLPnuCzxaFWFuWRG5IS1jBcgbqoO7P29mFf3afhfzdCNwY/B4KbDG3TuAPWZWDSwKtlW7+24AM1sDLDWz14EPAB8P+qwGvgrcF89gREQy1esHjvD+s8v4WGU5AOdMmxhqPUOGwzB8Bng0eDyDaFj0qQvaACL92i8FpgDN7t49SH8RkVGhub2T5vYuLj+rlGvPnxZ2OUCCE9Jm9o9AN/DTkSlnyPe7xcyqzKyqvr4+FW8pIpJ0NY3hT0D3F3c4mNmngL8GPuHuHjTvA8pjus0M2k7W3ggUm1lev/ZBuftKd69098qysrJ4SxcRSSu1abB0tb+4wsHMlgD/AFzv7u0xm9YBy8xsrJnNAeYDLwEvA/ODlUn5RCet1wWh8hwn5iyWA4/HNxQRkcy0p6ENMygvyaAjBzN7BNgAnG1mdWa2Avg+MAF4xsy2mNn9AO7+GrAW2AE8Bdzq7j3BnMJtwNPA68DaoC/Al4E7gsnrKcADIzpCEZE0V9vYzvRJ4ygYkxt2Ke8YzmqlmwZpPukvcHe/B7hnkPYngScHad/NiRVNIiKjTpifFX0yukJaRCRkNQ1tod5HaTAKBxGRELW0d3G4vYs5pTpyEBGRQG1TdKWSjhxEROQdexqCz4pWOIiISJ/aNLwADhQOIiKhqmlsY9qkgrRaxgoKBxGRUNU0tKXdKSVQOIiIhKq2sZ2KNFupBAoHEZHQHDneRWNbZ9qtVAKFg4hIaGqDjwPVaSUREXlHTXA3Vp1WEhGRd/Tdqnt2iY4cREQksKehnTMnFjAuP72WsYLCQUQkNLVpeDfWPgoHEZEQuDtv1bem1ae/xVI4iIiEINJ0jMPtXZw/c1LYpQxK4SAiEoLNkcMAXFheHHIlg1M4iIiEYGukhYIxOZw9dULYpQxK4SAiEoItkcOcP2MSebnp+Ws4PasSEcliXT29bH/7CBfMTM9TSqBwEBFJuTf2H6Wzu5cLZykcREQksCWYjNaRg4iIvGNLpIXS8fnMnDwu7FJOSuEgIpJiWyKHuWBmMWYWdiknNWQ4mNkqMztkZttj2krM7Bkz2xV8nxy0m5nda2bVZrbNzC6Oec3yoP8uM1se036Jmb0avOZeS+c/LRGRBB053sVb9W1pe31Dn+EcOTwILOnX9hXg9+4+H/h98BzgWmB+8HULcB9EwwS4C7gUWATc1RcoQZ/Pxryu/3uJiGSNbZEWAC7I9HBw9+eBpn7NS4HVwePVwA0x7Q951Eag2MymAdcAz7h7k7sfBp4BlgTbJrr7Rnd34KGYfYmIZJ2tdc1Aek9GQ/xzDlPdfX/w+AAwNXg8A4jE9KsL2k7VXjdI+6DM7BYzqzKzqvr6+jhLFxEJz+a9zcwtLWJS4ZiwSzmlhCekg//x+wjUMpz3Wunule5eWVZWloq3FBEZMe7O1rrmtJ9vgPjD4WBwSojg+6GgfR9QHtNvZtB2qvaZg7SLiGSdt1uOU3+0I+3nGyD+cFgH9K04Wg48HtN+c7BqaTHQEpx+ehq42swmBxPRVwNPB9uOmNniYJXSzTH7EhHJKlsj0fmGTDhyyBuqg5k9ArwfKDWzOqKrjr4BrDWzFUAt8NGg+5PAdUA10A58GsDdm8zsa8DLQb+73b1vkvvzRFdEjQN+G3yJiGSdLZFm8nNzOGdaet6JNdaQ4eDuN51k01WD9HXg1pPsZxWwapD2KuC8oeoQEcl0WyLNLJw+kbF56feZ0f3pCmkRkRTo7unl1bqWjDilBAoHEZGU2HWolWNdPQoHERE5YUsGTUaDwkFEJCW2RpopLhzD7CmFYZcyLAoHEZEU2BJpTvs7scZSOIiIJFlbRzc7Dx7NmFNKoHAQEUm6V/e10OuZM98ACgcRkaTrm4zOhNtm9FE4iIgk2dZIM7NKCikpyg+7lGFTOIiIJNmWSGbciTWWwkFEJIlqGtrY33Jc4SAiIif8x8Za8nKMD71rWtilnBaFg4hIkrR3drO2KsKS885k6sSCsMs5LQoHEZEk+dXmfRw53s2n3l0RdimnTeEgIpIE7s7q9TWcO30il8yeHHY5p03hICKSBBt2N7LzYCvL312RMbfMiKVwEBFJgtXra5hcOIbrL5gedilxUTiIiIywfc3HeGbHQZYtmkXBmPT/1LfBKBxEREbYwxtqAfjk4tkhVxI/hYOIyAg63tXDmpf3cvXCM5lRPC7scuKmcBARGUHrtrxNc3sXyzNw+WoshYOIyAhxdx5cX8PZUyeweG5J2OUkROEgIjJCqmoPs2P/kYxdvhoroXAws783s9fMbLuZPWJmBWY2x8w2mVm1mT1qZvlB37HB8+pge0XMfu4M2t80s2sSG5KISDgeXF/DxII8brgoM5evxsqL94VmNgP4ArDQ3Y+Z2VpgGXAd8B13X2Nm9wMrgPuC74fdfZ6ZLQO+CXzMzBYGrzsXmA48a2YL3L0noZGJiCTg+Z31/Gln/bD797rz9PYDfPryCgrz4/7VmjYSHUEeMM7MuoBCYD/wAeDjwfbVwFeJhsPS4DHAY8D3LXrctRRY4+4dwB4zqwYWARsSrE1EJC4d3T3csXYLR451k583/BMsZRPGZvxEdJ+4w8Hd95nZvwJ7gWPA74BXgGZ37w661QEzgsczgEjw2m4zawGmBO0bY3Yd+xoRkZR7Ytt+Glo7eXjFIq6YXxZ2OaGIe87BzCYT/V//HKKng4qAJSNU18ne8xYzqzKzqvr64R/uiYicjtXrazirrIj3zCsNu5TQJDIh/UFgj7vXu3sX8EvgcqDYzPqOSGYC+4LH+4BygGD7JKAxtn2Q1/wFd1/p7pXuXllWNjrTXESSa/Pew2yta8mKFUeJSCQc9gKLzawwmDu4CtgBPAfcGPRZDjwePF4XPCfY/gd396B9WbCaaQ4wH3gpgbpEROK2en0N48fm8bcXzwy7lFAlMuewycweA/4MdAObgZXAE8AaM/t60PZA8JIHgIeDCecmoiuUcPfXgpVOO4L93KqVSiIShkNHj/PEq/v5xKWzGT8281ccJSKh0bv7XcBd/Zp3E11t1L/vceAjJ9nPPcA9idQiInIq2+qaOXKs+5R9nnptP109zs2XZe4N80bK6I5GERkVqmqauPH+4a2Ov/LsMuaWjU9yRelP4SAiWe8nL0avXF55cyW5OaeeZD77zAkpqiq9KRxEJKvtbznGU68d4DOXV7B47pSwy8kYuvGeiGS1n27cS687f7e4IuxSMorCQUSy1vGuHh55aS9XnXMGs6YUhl1ORlE4iEjWemLbfhrbOrPmfkeppDkHEQnF718/SGNb56DbSgrzKS8ppLxkXNx3OHV3Vm/QbTDipXAQkZSrqmlixeqqYfUdk2sYp38bC8fp6nHuXnruqL4NRrwUDiKScj8JPhTn8dvew5jcv/zF7Q6NbZ1EmtrZ29ROa8epL1w7lcIxuXy0snzojjKAwkFEUupAy3Ge2h5dWjqntGjQPuUlhVxYXpziyiSWJqRFJKV+uqlWS0szgMJBRFKmo7uHn23S0tJMoHAQkZT5zVYtLc0UmnMQSVPHOnto64x/MjYdaWlp5lA4iKShlmNdvO9bz9Hc3hV2KSNOS0szg8JBJA39vCpCc3sXX7rmbCYWZM8/07F5udxw0Yywy5BhyJ6fOpEs0dvrPLyxlktmT+bWK+eFXY6MUpqQFkkzf9x5iNrGdk3aSqgUDiJp5sH1tUydOJZrzzsz7FJkFFM4iKSRt+pbeX5nPZ+4dDZjcvXPU8Kjnz6RNPLwhlryc3O4adGssEuRUU4T0iJxuPs/d/ByTdOI73fnwaN86F3TKJswdsT3LXI6FA4ip2nnwaOsenEP582YyBkTCkZ039MmFXDbB7RCScKncBA5TavX15Cfl8NDn7mUkqL8sMsRSYqE5hzMrNjMHjOzN8zsdTO7zMxKzOwZM9sVfJ8c9DUzu9fMqs1sm5ldHLOf5UH/XWa2PNFBiSRLy7EufvnnfSy9YLqCQbJaohPS3wOecvdzgAuA14GvAL939/nA74PnANcC84OvW4D7AMysBLgLuBRYBNzVFygi6ebnVRGOdfXoGgTJenGHg5lNAt4LPADg7p3u3gwsBVYH3VYDNwSPlwIPedRGoNjMpgHXAM+4e5O7HwaeAZbEW5dIsvRduVw5ezLnzZgUdjkiSZXIkcMcoB74iZltNrMfm1kRMNXd9wd9DgBTg8czgEjM6+uCtpO1D2Bmt5hZlZlV1dfXJ1C6yOnTlcsymiQyIZ0HXAzc7u6bzOx7nDiFBIC7u5l5IgX2299KYCVAZWXliO1XstebB47yxKv7h+44DM/uOMjUiWNZoiuXZRRIJBzqgDp33xQ8f4xoOBw0s2nuvj84bXQo2L4PiP2k75lB2z7g/f3a/5hAXSLv+PIvtrEl0jwi+zKD//OhhbpyWUaFuMPB3Q+YWcTMznb3N4GrgB3B13LgG8H3x4OXrANuM7M1RCefW4IAeRr455hJ6KuBO+OtS6TP1kgzWyLN3PU3C/n05XPCLkckoyR6ncPtwE/NLB/YDXya6DzGWjNbAdQCHw36PglcB1QD7UFf3L3JzL4GvBz0u9vdR/7SUxl1Vq+voSg/lxsvmRl2KSIZJ6FwcPctQOUgm64apK8Dt55kP6uAVYnUIhKrobWD32zbz7JF5UwoGBN2OSIZRydPJSs9smkvnT293HxZRdiliGQkhYNkna6eXv5jUy1XzC9l3hnjwy5HJCPp3kqSFRpbO9jb1A7AK7WHOXikg3tuOD/kqkQyl8JBMl5vr/OR+zewu6HtnbZZJYVcec4ZIVYlktkUDpLx/rjzELsb2rjjvy7g/JnR21osmDqB3BwLuTKRzKVwkIzX95nLn3v/WbpATWSE6F+SZDR95rJIcuhfk2Q0feaySHIoHCRjtXZ089grdfrMZZEk0JyDJOTVuhYih9sH3TahII9ZJYVMLx6XlFM+v3iljtaObt1CWyQJFA4St+NdPXz4/vV0dveesl+OwcRxYxjptUNtHT1cUF7MheXFI7xnEVE4SNxee7uFzu5evrb0XBbNmfIX2xynub2LSFM7kaZ2mo91jfj7G/Bh3VRPJCkUDhK3LZEWAK4590zOmFgwaJ/Fc6cM2i4i6U0T0hK3LZFmpk8qOGkwiEjmUjhI3LZGmrlwls73i2SjURUO7s7Og0d57e2WsEvJeH03urtgpsJBJBuNqnAwM/7b6iq+88zOsEvJeNvqogGrlUIi2WlUhQPAexeUsuGtxiGXX8qpbY40k2Nw3oxJYZciIkkw6sLhivlltHX2sHnv4bBLyWhbI80smDqBorFa8CaSjUZdOFx21hRyc4wXdjWEXUrGcne21jXrlJJIFht14TCxYAwXlRfzwq76sEvJWLWN7TS3d3GBwkEka426cIDoqaVt+1o43NYZdikZaUukGdBktEg2G53hsKAUd3jxLZ1aiseWSDPjxuQy/4zxYZciIkmScDiYWa6ZbTaz3wTP55jZJjOrNrNHzSw/aB8bPK8OtlfE7OPOoP1NM7sm0ZqG8q4Zk5hYkMcLO7M7HFo7utld3zro1/6WY/T0elz73RJp5vyZk8jTh+uIZK2RWGryP4DXgYnB828C33H3NWZ2P7ACuC/4ftjd55nZsqDfx8xsIbAMOBeYDjxrZgvcvWcEahtUXm4Ol88r5YVd9bg7Ztn3WcO9vc6Hf7ieNw8ePWmfMbnGzMmFlE0Yy+l83PL2fS185j1zRqBKEUlXCYWDmc0EPgTcA9xh0d+yHwA+HnRZDXyVaDgsDR4DPAZ8P+i/FFjj7h3AHjOrBhYBGxKpbShXzC/jt9sP8FZ9G/Oy8PTI/6tu4M2DR/nv753LwukTB2w/erybyOF26pqOUd/awekcRFw6t4SlF04fwWpFJN0keuTwXeAfgAnB8ylAs7t3B8/rgBnB4xlABMDdu82sJeg/A9gYs8/Y1yTNFfNLAXhhV/0pw6Gju4c/1zZz3oyJTCgYk+yyRsyD62soHZ/PHVcvYGxebtjliEiGiTsczOyvgUPu/oqZvX/kSjrle94C3AIwa1ZinxlcXlLI3NIinti2n+WXVZBzkvMq33t2Fz/841vk5hjnz5jE4rlTOKusiPKSQiqmFHHmpPS7I2ltYxvPvXmI26+cp2AQkbgkcuRwOXC9mV0HFBCdc/geUGxmecHRw0xgX9B/H1AO1JlZHjAJaIxp7xP7mr/g7iuBlQCVlZXxzabG+Mx75vBPv97OfX96i1uvnDdge8uxLh7aUMsV80u5sLyYF6sb+NELu/9iIveC8mKW/VU5f3PBdManydXCD22oJdeMTyyeHXYpIpKh4v5t5u53AncCBEcO/8vdP2FmPwduBNYAy4HHg5esC55vCLb/wd3dzNYBPzOzfyM6IT0feCneuk7HJy6dxaY9TXz7d29y0axi3n1W6V9sf2h9Da0d3Xzl2nM4d/okvnj12XR297K/5Rh7m9p5ff8RHnuljjt/+Sp3/+cOFpw5gVklhZRPHhf9XlJI+eRCJhSc+GOeUJCX1FU+bR3drK2KsOS8M5mqz1kQkTgl47+6XwbWmNnXgc3AA0H7A8DDwYRzE9EVSrj7a2a2FtgBdAO3JnOlUiwz4xt/ez6v7z/CFx7ZzBNfuOKdX6jtnd2senEPHzjnDM6dfuLmcvl5OcyeUsTsKUVcMb+Mz14xly2RZh7f8jbVh1rZGmnmt6/up/skM7xF+bksmlPC5fNKWTB1AjmnsVIqJwemTRrHjOJx5OcNHjC/2ryPo8e7+dS7K4b/ByEi0o+5J3x2JhSVlZVeVVU1IvvadfAo13//Rc46o4h7l13E3LLx/PiF3Xz9idf5xefezSWzJ5/W/rp7etnfcvyd1UDtndH5eQfeqm9lfXUjuxva4q7XDKZOKGDsmIEBUX+0gzmlRfzm9vdk5RJdEUmMmb3i7pVD9UuPk+Qhmz91Av/3pou4Y+0WlnzvBf7nB+ezen0Ni+eWnHYwQPQ6ivLgtBJnDd7n7eZj7Gs+dlr77erp5e3m40Sa2tnXfIzunoG3HTczPn7pLAWDiCRE4RD44MKpPHvH+/inX2/nX556E4Bvf+TCpL3f9OJxTC8el7T9i4gkQuEQ44yJBfz7313CU9sPUH2olcvnTQm7JBGRUCgc+jEzrj1/WthliIiESndOExGRARQOIiIygMJBREQGUDiIiMgACgcRERlA4SAiIgMoHEREZACFg4iIDJCxN94zs3qg9jReUgo0JKmcdKZxjy4a9+gSz7hnu3vZUJ0yNhxOl5lVDedOhNlG4x5dNO7RJZnj1mklEREZQOEgIiIDjKZwWBl2ASHRuEcXjXt0Sdq4R82cg4iIDN9oOnIQEZFhyrpwMLMlZvammVWb2VcG2T7WzB4Ntm8ys4rUVznyhjHuO8xsh5ltM7Pfm9nsMOocaUONO6bfh83MzSwrVrQMZ9xm9tHg7/w1M/tZqmtMhmH8nM8ys+fMbHPws35dGHWONDNbZWaHzGz7Sbabmd0b/LlsM7OLE35Td8+aLyAXeAuYC+QDW4GF/fp8Hrg/eLwMeDTsulM07iuBwuDx50bLuIN+E4DngY1AZdh1p+jvez6wGZgcPD8j7LpTNO6VwOeCxwuBmrDrHqGxvxe4GNh+ku3XAb8FDFgMbEr0PbPtyGERUO3uu929E1gDLO3XZymwOnj8GHCVmVkKa0yGIcft7s+5e3vwdCMwM8U1JsNw/r4BvgZ8EzieyuKSaDjj/izwA3c/DODuh1JcYzIMZ9wOTAweTwLeTmF9SePuzwNNp+iyFHjIozYCxWaW0EdaZls4zAAiMc/rgrZB+7h7N9ACZPqHRQ9n3LFWEP1fRqYbctzB4XW5uz+RysKSbDh/3wuABWb2opltNLMlKasueYYz7q8CnzSzOuBJ4PbUlBa60/0dMCR9hvQoY2afBCqB94VdS7KZWQ7wb8CnQi4lDHlETy29n+hR4vNmdr67N4daVfLdBDzo7t82s8uAh83sPHfvDbuwTJNtRw77gPKY5zODtkH7mFke0UPPxpRUlzzDGTdm9kHgH4Hr3b0jRbUl01DjngCcB/zRzGqInotdlwWT0sP5+64D1rl7l7vvAXYSDYtMNpxxrwDWArj7BqCA6P2Hst2wfgecjmwLh5eB+WY2x8zyiU44r+vXZx2wPHh8I/AHD2Z0MtiQ4zazi4B/JxoM2XD+GYYYt7u3uHupu1e4ewXRuZbr3b0qnHJHzHB+zn9N9KgBMyslepppdyqLTILhjHsvcBWAmf0XouFQn9Iqw7EOuDlYtbQYaHFMadIjAAAAwElEQVT3/YnsMKtOK7l7t5ndBjxNdGXDKnd/zczuBqrcfR3wANFDzWqiEzzLwqt4ZAxz3N8CxgM/D+bf97r79aEVPQKGOe6sM8xxPw1cbWY7gB7gS+6e0UfIwxz3F4EfmdnfE52c/lQW/OcPM3uEaNiXBvMpdwFjANz9fqLzK9cB1UA78OmE3zML/txERGSEZdtpJRERGQEKBxERGUDhICIiAygcRERkAIWDiIgMoHAQEZEBFA4iIjKAwkFERAb4//4Bo3o38UqIAAAAAElFTkSuQmCC\n", 1274 | "text/plain": [ 1275 | "
" 1276 | ] 1277 | }, 1278 | "metadata": {}, 1279 | "output_type": "display_data" 1280 | }, 1281 | { 1282 | "name": "stdout", 1283 | "output_type": "stream", 1284 | "text": [ 1285 | "Cost is minimized near a cutoff of: 0.04\n" 1286 | ] 1287 | } 1288 | ], 1289 | "source": [ 1290 | "TN_cost = 0\n", 1291 | "TP_cost = 0\n", 1292 | "FP_cost = 0.05*500 #$cost of losing an annoyed customer (assuming 5% defection and $500 sign-on bonus)\n", 1293 | "FN_cost = 450 # $cost of of letting a fradulent transaction slip through\n", 1294 | "\n", 1295 | "cutoffs = np.arange(0.01, 1, 0.01)\n", 1296 | "costs = []\n", 1297 | "for c in cutoffs:\n", 1298 | " costs.append(np.sum(np.sum(np.array([[TN_cost, FP_cost], [FN_cost, TP_cost]]) * \n", 1299 | " pd.crosstab(index=test_data.iloc[:, 0], \n", 1300 | " columns=np.where(predictions > c, 1, 0)))))\n", 1301 | "\n", 1302 | "costs = np.array(costs)\n", 1303 | "plt.plot(cutoffs, costs)\n", 1304 | "plt.show()\n", 1305 | "print('Cost is minimized near a cutoff of:', cutoffs[np.argmin(costs)])" 1306 | ] 1307 | }, 1308 | { 1309 | "cell_type": "markdown", 1310 | "metadata": {}, 1311 | "source": [ 1312 | "## Clean up\n", 1313 | "\n", 1314 | "We will leave the prediction endpoint running at the end of this notebook so we can handle incoming event streams. However, don't forget to delete the prediction endpoint when you're done. You can do that at the Amazon SageMaker console in the Endpoints page. Or you can run `xgb_predictor.delete_endpoint()`" 1315 | ] 1316 | }, 1317 | { 1318 | "cell_type": "code", 1319 | "execution_count": 49, 1320 | "metadata": {}, 1321 | "outputs": [], 1322 | "source": [ 1323 | "#xgb_predictor.delete_endpoint()" 1324 | ] 1325 | }, 1326 | { 1327 | "cell_type": "markdown", 1328 | "metadata": {}, 1329 | "source": [ 1330 | "\n", 1331 | "## Data Acknowledgements\n", 1332 | "\n", 1333 | "The dataset used to demonstrated the fraud detection solution has been collected and analysed during a research collaboration of Worldline and the Machine Learning Group (http://mlg.ulb.ac.be) of ULB (Université Libre de Bruxelles) on big data mining and fraud detection. More details on current and past projects on related topics are available on https://www.researchgate.net/project/Fraud-detection-5 and the page of the [DefeatFraud](https://mlg.ulb.ac.be/wordpress/portfolio_page/defeatfraud-assessment-and-validation-of-deep-feature-engineering-and-learning-solutions-for-fraud-detection/) project\n", 1334 | "We cite the following works:\n", 1335 | "* Andrea Dal Pozzolo, Olivier Caelen, Reid A. Johnson and Gianluca Bontempi. Calibrating Probability with Undersampling for Unbalanced Classification. In Symposium on Computational Intelligence and Data Mining (CIDM), IEEE, 2015\n", 1336 | "* Dal Pozzolo, Andrea; Caelen, Olivier; Le Borgne, Yann-Ael; Waterschoot, Serge; Bontempi, Gianluca. Learned lessons in credit card fraud detection from a practitioner perspective, Expert systems with applications,41,10,4915-4928,2014, Pergamon\n", 1337 | "* Dal Pozzolo, Andrea; Boracchi, Giacomo; Caelen, Olivier; Alippi, Cesare; Bontempi, Gianluca. Credit card fraud detection: a realistic modeling and a novel learning strategy, IEEE transactions on neural networks and learning systems,29,8,3784-3797,2018,IEEE\n", 1338 | "* Dal Pozzolo, Andrea Adaptive Machine learning for credit card fraud detection ULB MLG PhD thesis (supervised by G. Bontempi)\n", 1339 | "* Carcillo, Fabrizio; Dal Pozzolo, Andrea; Le Borgne, Yann-Aël; Caelen, Olivier; Mazzer, Yannis; Bontempi, Gianluca. Scarff: a scalable framework for streaming credit card fraud detection with Spark, Information fusion,41, 182-194,2018,Elsevier\n", 1340 | "* Carcillo, Fabrizio; Le Borgne, Yann-Aël; Caelen, Olivier; Bontempi, Gianluca. Streaming active learning strategies for real-life credit card fraud detection: assessment and visualization, International Journal of Data Science and Analytics, 5,4,285-300,2018,Springer International Publishing" 1341 | ] 1342 | } 1343 | ], 1344 | "metadata": { 1345 | "kernelspec": { 1346 | "display_name": "conda_mxnet_p36", 1347 | "language": "python", 1348 | "name": "conda_mxnet_p36" 1349 | }, 1350 | "language_info": { 1351 | "codemirror_mode": { 1352 | "name": "ipython", 1353 | "version": 3 1354 | }, 1355 | "file_extension": ".py", 1356 | "mimetype": "text/x-python", 1357 | "name": "python", 1358 | "nbconvert_exporter": "python", 1359 | "pygments_lexer": "ipython3", 1360 | "version": "3.6.5" 1361 | } 1362 | }, 1363 | "nbformat": 4, 1364 | "nbformat_minor": 2 1365 | } 1366 | -------------------------------------------------------------------------------- /notebooks/train_nn.py: -------------------------------------------------------------------------------- 1 | import argparse 2 | import numpy as np 3 | import os 4 | import tensorflow as tf 5 | from tensorflow.contrib.eager.python import tfe 6 | from keras.models import Sequential 7 | from keras.layers import Dense, Dropout, Activation 8 | from keras.layers import Embedding 9 | from keras.layers import Conv1D, GlobalMaxPooling1D 10 | import pandas as pd 11 | from sklearn.metrics import classification_report 12 | from sklearn.metrics import precision_score,accuracy_score 13 | 14 | tf.logging.set_verbosity(tf.logging.ERROR) 15 | 16 | max_features = 20000 17 | maxlen = 400 18 | embedding_dims = 300 19 | filters = 250 20 | kernel_size = 3 21 | hidden_dims = 250 22 | 23 | 24 | def parse_args(): 25 | 26 | parser = argparse.ArgumentParser() 27 | 28 | # hyperparameters sent by the client are passed as command-line arguments to the script 29 | parser.add_argument('--epochs', type=int, default=1) 30 | parser.add_argument('--batch_size', type=int, default=64) 31 | 32 | # data directories 33 | parser.add_argument('--train', type=str, default=os.environ.get('SM_CHANNEL_TRAINING')) 34 | parser.add_argument('--test', type=str, default=os.environ.get('SM_CHANNEL_VALIDATION')) 35 | 36 | # model directory: we will use the default set by SageMaker, /opt/ml/model 37 | parser.add_argument('--model_dir', type=str, default=os.environ.get('SM_MODEL_DIR')) 38 | 39 | return parser.parse_known_args() 40 | 41 | 42 | def get_train_data(train_dir): 43 | 44 | #print('train_dir = ',train_dir) 45 | 46 | train = pd.read_csv(os.path.join(train_dir,'train.csv'), delimiter=',') 47 | #print(train.head(10)) 48 | 49 | x_train = train.iloc[:, 0:28] 50 | y_train = train.iloc[:,28:29] 51 | 52 | #print('x train', x_train.shape,'y train', y_train.shape) 53 | 54 | 55 | return x_train, y_train 56 | 57 | 58 | def get_test_data(test_dir): 59 | 60 | test = pd.read_csv(os.path.join(test_dir,'validation.csv'), delimiter=',') 61 | #print(test.head(10)) 62 | 63 | x_test = test.iloc[:,0:28] 64 | y_test = test.iloc[:,28:29] 65 | #print('x test', x_test.shape,'y test', y_test.shape) 66 | 67 | return x_test, y_test 68 | 69 | 70 | def get_model(): 71 | 72 | model = tf.keras.models.Sequential([ 73 | tf.keras.layers.Dense(28, input_dim=28, activation='relu'), 74 | tf.keras.layers.Dense(8, activation='relu'), 75 | tf.keras.layers.Dense(1, activation='sigmoid') 76 | ]) 77 | 78 | print(model.summary) 79 | 80 | model.compile(optimizer='adam', 81 | loss='binary_crossentropy', 82 | metrics=['accuracy']) 83 | 84 | 85 | return model 86 | 87 | 88 | if __name__ == "__main__": 89 | 90 | args, _ = parse_args() 91 | 92 | print(args) 93 | 94 | x_train, y_train = get_train_data(args.train) 95 | x_test, y_test = get_test_data(args.test) 96 | 97 | model = get_model() 98 | 99 | model.summary() 100 | 101 | model.fit( 102 | x_train, 103 | y_train, 104 | epochs=args.epochs, 105 | batch_size=args.batch_size, 106 | validation_data=(x_test, y_test) 107 | ) 108 | 109 | # create a TensorFlow SavedModel for deployment to a SageMaker endpoint with TensorFlow Serving 110 | 111 | tf.contrib.saved_model.save_keras_model(model, args.model_dir) --------------------------------------------------------------------------------