{"cells": [{"metadata": {"_uuid": "f673f458b149e8b081b5f4ad637c1fd8d5f04984", "_execution_state": "idle", "_cell_guid": "93ec7a2d-7645-454d-8d1b-3382f54f65f2", "collapsed": false}, "source": "Keras is installed on the Kaggle Kernels but if you want to use pretrained Imagenet models, Keras will try to download some additional files like the pretrained weights.  The Kernel won't let you go download files off the Internet though. To get around this problem, I've uploaded the model files for VGG16 and VGG19 as a Data Source.  Data Sources have file size limits (<500 megs).  The mainly affects the full model files.  To get around this, I've split up the hdf5 files into multiple parts. This is just an example of how to load the split model files and how to create your own.", "execution_count": null, "outputs": [], "cell_type": "markdown"}, {"outputs": [], "cell_type": "code", "metadata": {"_uuid": "2d62a480e5e6eea7368191825b188ee4d9dfcd67", "_execution_state": "idle", "trusted": false, "_cell_guid": "72d2befe-7fe9-46c7-8007-95601bc56117"}, "execution_count": null, "source": "# This Python 3 environment comes with many helpful analytics libraries installed\n# It is defined by the kaggle/python docker image: https://github.com/kaggle/docker-python\n# For example, here's several helpful packages to load in \n\nimport numpy as np # linear algebra\nimport pandas as pd # data processing, CSV file I/O (e.g. pd.read_csv)\n\n# Input data files are available in the \"../input/\" directory.\n# For example, running this (by clicking run or pressing Shift+Enter) will list the files in the input directory\n\nfrom subprocess import check_output\nprint(check_output([\"ls\", \"../input\"]).decode(\"utf8\"))\n\n# Any results you write to the current directory are saved as output."}, {"metadata": {"_execution_state": "idle", "_uuid": "42d5889cd8acf34bff7108fc708d23f74cf0c7ba", "_cell_guid": "24ade5f1-9d6c-4066-ba0f-f04fd9b7be78", "collapsed": false}, "cell_type": "markdown", "execution_count": null, "outputs": [], "source": "You're probably going to be using some other data set with the Keras models one so just remember that the data will be in additional subdirectories under \"../input\"."}, {"metadata": {"_execution_state": "idle", "_uuid": "67b165b7e7bff276b114f8a0232c4139945af573", "trusted": false, "_cell_guid": "b3b0dd40-1488-44be-b19a-3248beb96218", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "import h5py\nimport numpy as np\nimport json\nimport os\nfrom random import randint"}, {"metadata": {"_execution_state": "idle", "_uuid": "48201443cf967272e15718d826312085d282748c", "trusted": false, "_cell_guid": "e70b5acc-a7e1-4ec9-9e3e-06c466b1f553", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "from keras import applications\nfrom keras.engine import topology"}, {"metadata": {"_execution_state": "idle", "_uuid": "6e2157e2a5e3f86b3f5f377b7f4996d667b84cbc", "trusted": false, "_cell_guid": "cb905e4e-0446-47b1-af14-abf0274ac90f", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "from keras.preprocessing import image\nfrom keras.applications.imagenet_utils import preprocess_input"}, {"metadata": {"_uuid": "ce3c6978b83858bbaa4b64687b47660abc57663e", "_execution_state": "idle", "_cell_guid": "795fe301-cbac-4a4c-8358-8d87b4a229a0", "collapsed": false}, "source": "# Loading a split model", "execution_count": null, "outputs": [], "cell_type": "markdown"}, {"metadata": {"_execution_state": "idle", "_uuid": "97cfe4732d6840a8e4b7814b7c039fbf4ce923b3", "trusted": false, "_cell_guid": "ef0cd6a0-ffe2-4454-9bb9-0648db59678e", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "def load_split_weights(model, model_path_pattern='model_%d.h5', memb_size=102400000):  \n    \"\"\"Loads weights from split hdf5 files.\n    \n    Parameters\n    ----------\n    model : keras.models.Model\n        Your model.\n    model_path_pattern : str\n        The path name should have a \"%d\" wild card in it.  For \"model_%d.h5\", the following\n        files will be expected:\n        model_0.h5\n        model_1.h5\n        model_2.h5\n        ...\n    memb_size : int\n        The number of bytes per hdf5 file.  \n    \"\"\"\n    model_f = h5py.File(model_path_pattern, \"r\", driver=\"family\", memb_size=memb_size)\n    topology.load_weights_from_hdf5_group_by_name(model_f, model.layers)\n    \n    return model"}, {"metadata": {"_execution_state": "idle", "_uuid": "156bb77afe38710a4190ed063de5390c43092023", "_cell_guid": "1f282788-a425-49ad-8596-a2105224df90", "collapsed": false}, "cell_type": "markdown", "execution_count": null, "outputs": [], "source": "Create a full VGG19 model with no weights loaded."}, {"metadata": {"_execution_state": "idle", "_uuid": "6a4e03c8ca358fd77ba15c9a6e2a69a8665061ec", "trusted": false, "_cell_guid": "816a6284-bd26-4804-9795-9ebfead0d4d2", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "model = applications.VGG19(include_top=True, weights=None)  "}, {"metadata": {"_execution_state": "idle", "_uuid": "4372f82e5e79cc3a3e2cc3f8305e2757f7d268b3", "_cell_guid": "f817c2f1-f20e-48fb-b874-f7d4a9d5f62f", "collapsed": false}, "cell_type": "markdown", "execution_count": null, "outputs": [], "source": "Load the weights."}, {"metadata": {"_execution_state": "idle", "_uuid": "320b1866830f2bb3d59cf944214e090f3795029a", "trusted": false, "_cell_guid": "512a4634-84c8-4cf1-9b37-d454e6fb6460", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "keras_models_dir = '../input/keras-models'\nmodel_path_pattern = keras_models_dir + \"/vgg19_weights_tf_dim_ordering_tf_kernels_%d.h5\" \nmodel = load_split_weights(model, model_path_pattern = model_path_pattern)"}, {"metadata": {"_execution_state": "idle", "_uuid": "f8c6bd84700f27ea1aa36e31721749637ffc5de6", "trusted": false, "_cell_guid": "7124573d-89a6-46fa-9d8d-13d912885d3c", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "def load_img_to_np(img_path, target_size=(224, 224)):\n    \"\"\"Loads an image file into a numpy array for preprocess_image.\n    \n    Parameters\n    ----------\n    img_path : str\n        Path for image.\n    target_size : (int, int)\n        Height and width for the image to be resized to.\n        \n    Returns\n    -------\n    numpy.ndarray (len(shape)=4)\n    \n    \"\"\"\n    img = image.load_img(img_path, target_size=target_size)\n    \n    # RGB -> BGR\n    img_np = np.asarray(img)[...,::-1]\n    \n    # reshape for preprocess_input\n    return img_np.reshape(1, img_np.shape[0], img_np.shape[1], img_np.shape[2]).copy().astype(np.float32)"}, {"metadata": {"_uuid": "aaf4a22265926a142d2e7c8aa457fac1711dae6b", "_execution_state": "idle", "_cell_guid": "cc35dbba-195a-4acf-8612-ac0c8eecc290", "collapsed": false}, "source": "The original decode_predictions() tries to download imagenet_class_index.json.  I grabbed to code from here and made some modifications to load it from Keras models.", "execution_count": null, "outputs": [], "cell_type": "markdown"}, {"metadata": {"_uuid": "1d503caef0546523cf2dfd1200dd00a837b760b1", "_execution_state": "idle", "trusted": false, "_cell_guid": "ebd7b974-ee24-477d-ba5a-bc4d700a3a2d", "collapsed": false}, "source": "def decode_predictions(preds, top=5):\n    \"\"\"Decodes the prediction of an ImageNet model.\n    # Arguments\n        preds: Numpy tensor encoding a batch of predictions.\n        top: integer, how many top-guesses to return.\n    # Returns\n        A list of lists of top class prediction tuples\n        `(class_name, class_description, score)`.\n        One list of tuples per sample in batch input.\n    # Raises\n        ValueError: in case of invalid shape of the `pred` array\n            (must be 2D).\n    \"\"\"\n    if len(preds.shape) != 2 or preds.shape[1] != 1000:\n        raise ValueError('`decode_predictions` expects '\n                         'a batch of predictions '\n                         '(i.e. a 2D array of shape (samples, 1000)). '\n                         'Found array with shape: ' + str(preds.shape))\n    fpath = '../input/keras-models/imagenet_class_index.json'\n    CLASS_INDEX = json.load(open(fpath))\n    results = []\n    for pred in preds:\n        top_indices = pred.argsort()[-top:][::-1]\n        result = [tuple(CLASS_INDEX[str(i)]) + (pred[i],) for i in top_indices]\n        result.sort(key=lambda x: x[2], reverse=True)\n        results.append(result)\n    return results", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_execution_state": "idle", "_uuid": "a2c5497bdc7aaee1ac9925aba6d84e4f17e394a2", "trusted": false, "_cell_guid": "90a12bd5-a897-4ec8-93e9-2817dd357b22", "collapsed": false}, "cell_type": "code", "execution_count": null, "outputs": [], "source": "def make_predition(model, img_np):\n    \"\"\"Make predictions for an image.  \n    \n    Parameters\n    ----------\n    model : Keras.models.Model\n        Your model.\n    img_np : numpy.ndarray (len(shape)=4)\n        Array of images as numpy arrays.\n        \n    Returns\n    -------\n    List\n    \"\"\"\n    preds = model.predict(preprocess_input(img_np))\n    return decode_predictions(preds)"}, {"metadata": {"_uuid": "0065ebf2fa813800128da5cae04ce85badf9f754", "_execution_state": "idle", "trusted": false, "_cell_guid": "f72c2bdf-cb25-41d7-bb85-cf3d937d8672", "collapsed": false}, "source": "kitten_file = '%s/images/kitten.jpg' % keras_models_dir\nkitten_img = image.load_img(kitten_file, target_size=(224, 224))\nkitten_img", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "1213dc1d6a74d5501173a12bfd2edb9b36d63df1", "_execution_state": "idle", "trusted": false, "_cell_guid": "32e1ca10-3956-4d01-ae40-c2643ec69c3e", "collapsed": false}, "source": "kitten_np = load_img_to_np(kitten_file)\nprint(make_predition(model, kitten_np))", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "2895d5a21c1af3701453c28696de84af2899518b", "_execution_state": "idle", "trusted": false, "_cell_guid": "8aa2e903-adcf-4849-bdb9-42baef70db90", "collapsed": false}, "source": "dogs_cats_dir = \"../input/dogs-vs-cats-redux-kernels-edition\"\nimg_files = [file for file in os.listdir(\"%s/train/\" % dogs_cats_dir) if file.endswith(\".jpg\")]\ncat_files = ['%s/train/%s' % (dogs_cats_dir, file) for file in img_files if file.startswith(\"cat\")]\ndog_files = ['%s/train/%s' % (dogs_cats_dir, file) for file in img_files if file.startswith(\"dog\")]", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "c355cf3292f61157356ebbd64c7378dee3176ddf", "_execution_state": "idle", "trusted": false, "_cell_guid": "bb6a8219-0d09-4865-882e-df1efb38f378", "collapsed": false}, "source": "dog_idx = randint(0, len(dog_files))\n\ndog_file = dog_files[dog_idx]\ndog_img = image.load_img(dog_file, target_size=(224, 224))\ndog_img", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "d232ff84067b1705e801959fc5dbe9a1d253c614", "_execution_state": "idle", "trusted": false, "_cell_guid": "eb4ba64f-f79a-4698-bfb3-10f7947f9073", "collapsed": false}, "source": "dog_np = load_img_to_np(dog_file)\nprint(make_predition(model, dog_np))", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "92e6de688ac6895b748e9419fcf8ca40208e2490", "_execution_state": "idle", "trusted": false, "_cell_guid": "451d213f-fd17-4940-8a61-521fb5798b01", "collapsed": false}, "source": "cat_idx = randint(0, len(dog_files))\ncat_file = cat_files[cat_idx]\ncat_img = image.load_img(cat_file, target_size=(224, 224))\ncat_img", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "0859ec505c1dea6d8f7e15bcbfe7d584717f0b09", "_execution_state": "idle", "trusted": false, "_cell_guid": "d119b84c-24d3-4b02-9ece-3db1afc85765", "collapsed": false}, "source": "cat_np = load_img_to_np(cat_file)\nprint(make_predition(model, cat_np))", "execution_count": null, "outputs": [], "cell_type": "code"}, {"metadata": {"_uuid": "d7b3f36f1c782b7b8e01379c01a9e761af2c0a39", "_execution_state": "idle", "_cell_guid": "64e85ca7-d60a-4273-8ab6-252584c95b13", "collapsed": false}, "source": "# Splitting hdf5 model files", "execution_count": null, "outputs": [], "cell_type": "markdown"}, {"metadata": {"_uuid": "47d9788424c4a681cd4ac42e916128cedec9efa5", "_execution_state": "idle", "_cell_guid": "e2db3ea4-db41-4cdb-ba9a-257f3372a5b0", "collapsed": false}, "source": "Here's my function for splitting up hdf5 model files.  You can change the memb_size but the number of bytes must match when you call load_split_weights() to load the weights back into your model.", "execution_count": null, "outputs": [], "cell_type": "markdown"}, {"metadata": {"_uuid": "852a625ee3458d4d17fcf67bbd376424097622cf", "_execution_state": "idle", "trusted": false, "_cell_guid": "176da118-df57-46e6-a0e2-f6eee66c0ee9", "collapsed": false}, "source": "def split_h5_file(src_path, dest_path_pattern='model_%d.h5', memb_size=102400000):\n    \"\"\"Takes an hdf5 file and makes a copy of it split into multiple files.\n    \n    Parameters\n    ----------\n    src_path : str\n        The path of the source hdf5 file.\n    dest_path_pattern : str\n        The path pattern of the destination hdf5 files. The path pattern should have a \"%d\" wild card in it.  \n        For \"model_%d.h5\", the following\n        files will be expected:\n            model_0.h5\n            model_1.h5\n            model_2.h5\n    memb_size : int\n        Max number of bytes for each split file.\n    \"\"\"\n    src_f = h5py.File(src_path,'r+')\n    dest_f = h5py.File(dest_path_pattern, driver=\"family\", memb_size=memb_size)\n \n    # copy items\n    for (name, _) in src_f.items():\n        src_f.copy(name, dest_f) \n        \n    # copy attribs\n    for (name, value) in src_f.attrs.items():\n        dest_f.attrs.create(name, value)    \n        \n    dest_f.flush()\n    dest_f.close()\n    src_f.close()", "execution_count": null, "outputs": [], "cell_type": "code"}], "metadata": {"kernelspec": {"display_name": "Python 3", "name": "python3", "language": "python"}, "language_info": {"codemirror_mode": {"name": "ipython", "version": 3}, "file_extension": ".py", "mimetype": "text/x-python", "version": "3.6.1", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "name": "python"}}, "nbformat": 4, "nbformat_minor": 0}