{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Taxi / Shared mobility" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The standard vehicles (added by default `addVehicle` or `adddemand`) in UXsim are a kind of privately owned vehicles: They travel from origin to destination and disappear. \n", "\n", "In this demonstration, we explain how to represent taxi-like (or *shared mobility* if you want a cool name) vehicles that repeatedly transport multiple passengers. Such taxi can be added by `addVehicle` with `mode=\"taxi\"` option. Furthermore, the passenger-to-taxi matching problem is handled by `uxsim.TaxiHandler` submodule.\n", "\n", "Let's define a grid shaped network scenario." ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [], "source": [ "%matplotlib inline\n", "%load_ext autoreload\n", "%autoreload 2" ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [], "source": [ "from pylab import *\n", "from uxsim import *\n", "from uxsim.TaxiHandler import *\n", "\n", "# World definition\n", "tmax = 7200\n", "deltan = 5\n", "W = World(\n", " name=\"\",\n", " deltan=deltan,\n", " tmax=tmax,\n", " print_mode=1, save_mode=1, show_mode=1,\n", " random_seed=0,\n", ")\n", "\n", "# Scenario definition: grid network\n", "#deploy nodes as an imax x jmax grid\n", "imax = 6\n", "jmax = 6\n", "nodes = {}\n", "for i in range(imax):\n", " for j in range(jmax):\n", " nodes[i,j] = W.addNode(f\"n{(i,j)}\", i, j, flow_capacity=1.6)\n", "\n", "#create links between neighborhood nodes\n", "links = {}\n", "for i in range(imax):\n", " for j in range(jmax):\n", " if i != imax-1:\n", " links[i,j,i+1,j] = W.addLink(f\"l{(i,j,i+1,j)}\", nodes[i,j], nodes[i+1,j], length=1000, free_flow_speed=20, number_of_lanes=1)\n", " if i != 0:\n", " links[i,j,i-1,j] = W.addLink(f\"l{(i,j,i-1,j)}\", nodes[i,j], nodes[i-1,j], length=1000, free_flow_speed=20, number_of_lanes=1)\n", " if j != jmax-1:\n", " links[i,j,i,j+1] = W.addLink(f\"l{(i,j,i,j+1)}\", nodes[i,j], nodes[i,j+1], length=1000, free_flow_speed=20, number_of_lanes=1)\n", " if j != 0:\n", " links[i,j,i,j-1] = W.addLink(f\"l{(i,j,i,j-1)}\", nodes[i,j], nodes[i,j-1], length=1000, free_flow_speed=20, number_of_lanes=1)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Taxis can be added by `W.addVehicle(origin_node, None, 0, mode=\"taxi\")` as follows. Their behavior is as follows:\n", "\n", "- When a taxi has no job, it circulates the network randomly.\n", "- When a taxi is ordered to serve a passenger, it travels to the origin node of the passenger to pickup, and then travels to the destination to drop-off.\n", "\n", "In addition, we need to define a taxi handler `Handler`. It is responsible to manage trip requests from passengers and give orders to taxis. This time, we use default `TaxiHandler_nearest` that matches a new passenger to their nearest vacant taxi." ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [], "source": [ "Handler = TaxiHandler_nearest(W)\n", "\n", "n_taxis = 3000\n", "for i in range(int(n_taxis/deltan)):\n", " node = random.choice(list(nodes.values()))\n", " W.addVehicle(node, None, 0, mode=\"taxi\")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A passenger' trip request is represented by `TripRequest` class. It can be added by `Handler.add_trip_request(origin_node, destination_node, departure_time)`. In this scenario, they are randomly set as follows." ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [], "source": [ "n_passengers = 20000\n", "for i in range(int(n_passengers/deltan)):\n", " node1 = random.choice(list(nodes.values()))\n", " node2 = random.choice(list(nodes.values()))\n", " while node1 == node2:\n", " node2 = random.choice(list(nodes.values()))\n", " Handler.add_trip_request(node1, node2, i/n_passengers*deltan*tmax/2)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now we can execute simulation. During the simulation, `Handler.assign_trip_request_to_taxi()` must be called repeatedly in order to let taxis do their jobs." ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "simulation setting:\n", " scenario name: \n", " simulation duration:\t 7200 s\n", " number of vehicles:\t 3000 veh\n", " total road length:\t 120000 m\n", " time discret. width:\t 5 s\n", " platoon size:\t\t 5 veh\n", " number of timesteps:\t 1440\n", " number of platoons:\t 600\n", " number of links:\t 120\n", " number of nodes:\t 36\n", " setup time:\t\t 0.52 s\n", "simulating...\n", " time| # of vehicles| ave speed| computation time\n", " 0 s| 0 vehs| 0.0 m/s| 0.00 s\n", " 600 s| 3000 vehs| 13.4 m/s| 2.83 s\n", " 1200 s| 3000 vehs| 15.0 m/s| 4.63 s\n", " 1800 s| 3000 vehs| 14.1 m/s| 5.85 s\n", " 2400 s| 3000 vehs| 14.8 m/s| 6.88 s\n", " 3000 s| 3000 vehs| 14.7 m/s| 7.98 s\n", " 3600 s| 3000 vehs| 14.3 m/s| 9.03 s\n", " 4200 s| 3000 vehs| 15.5 m/s| 9.81 s\n", " 4800 s| 3000 vehs| 14.5 m/s| 10.81 s\n", " 5400 s| 3000 vehs| 14.0 m/s| 11.55 s\n", " 6000 s| 3000 vehs| 14.9 m/s| 12.34 s\n", " 6600 s| 3000 vehs| 14.5 m/s| 13.13 s\n", " 7200 s| 3000 vehs| 14.9 m/s| 13.87 s\n", " simulation finished\n", "results:\n", " average speed:\t 15.5 m/s\n", " number of completed trips:\t 0 / 0\n", " total distance traveled:\t 0.0 m\n" ] } ], "source": [ "# Run the simulation \n", "while W.check_simulation_ongoing():\n", " W.exec_simulation(duration_t = 60)\n", " Handler.assign_trip_request_to_taxi() # for every 60 seconds, the taxi is assgined\n", "\n", "# Results\n", "W.analyzer.print_simple_stats()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that the trip-related stats shown by `W.analyzer.print_simple_stats()` are only for non-taxi trips, so the current one shows 0.\n", "\n", "The summary of taxi transportation can be printed as follows" ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "results for taxi transportation:\n", " total trip rquests: 20000\n", " completed trip requests: 20000\n", " completed trip requests ratio: 1.00\n", " average number of completed requests per taxi: 6.67\n", " average waiting time: 86.0\n", " average in-vehicle time: 283.8\n", " average trip time: 369.8\n" ] } ], "source": [ "Handler.print_stats()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "You can also export the trip logs as pandas.Dataframe." ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
| \n", " | orig | \n", "dest | \n", "depart_time | \n", "get_taxi_time | \n", "arrival_time | \n", "travel_time | \n", "waiting_time | \n", "used_taxi | \n", "
|---|---|---|---|---|---|---|---|---|
| 0 | \n", "n(4, 2) | \n", "n(3, 1) | \n", "0.0 | \n", "165 | \n", "340 | \n", "340.0 | \n", "165.0 | \n", "418 | \n", "
| 1 | \n", "n(5, 5) | \n", "n(4, 2) | \n", "0.9 | \n", "160 | \n", "500 | \n", "499.1 | \n", "159.1 | \n", "180 | \n", "
| 2 | \n", "n(1, 3) | \n", "n(4, 3) | \n", "1.8 | \n", "65 | \n", "220 | \n", "218.2 | \n", "63.2 | \n", "230 | \n", "
| 3 | \n", "n(3, 1) | \n", "n(3, 4) | \n", "2.7 | \n", "65 | \n", "245 | \n", "242.3 | \n", "62.3 | \n", "236 | \n", "
| 4 | \n", "n(0, 5) | \n", "n(2, 3) | \n", "3.6 | \n", "65 | \n", "325 | \n", "321.4 | \n", "61.4 | \n", "131 | \n", "
| ... | \n", "... | \n", "... | \n", "... | \n", "... | \n", "... | \n", "... | \n", "... | \n", "... | \n", "
| 3995 | \n", "n(4, 1) | \n", "n(2, 2) | \n", "3595.5 | \n", "3645 | \n", "3850 | \n", "254.5 | \n", "49.5 | \n", "452 | \n", "
| 3996 | \n", "n(2, 0) | \n", "n(3, 3) | \n", "3596.4 | \n", "3710 | \n", "4095 | \n", "498.6 | \n", "113.6 | \n", "547 | \n", "
| 3997 | \n", "n(5, 0) | \n", "n(3, 2) | \n", "3597.3 | \n", "3640 | \n", "3870 | \n", "272.7 | \n", "42.7 | \n", "355 | \n", "
| 3998 | \n", "n(1, 5) | \n", "n(0, 1) | \n", "3598.2 | \n", "3640 | \n", "3945 | \n", "346.8 | \n", "41.8 | \n", "0 | \n", "
| 3999 | \n", "n(2, 5) | \n", "n(1, 3) | \n", "3599.1 | \n", "3725 | \n", "3935 | \n", "335.9 | \n", "125.9 | \n", "340 | \n", "
4000 rows × 8 columns
\n", "