def show_predictions(model_path, tub_paths, start=0, end=100, index=0): images, y, predictions = [], [], [] img_ok = 0 model = MyModel(min_throttle=0., max_throttle=1.) model.load(model_path) pi = PreprocessImage() for path in tub_paths: files = glob.glob(os.path.join(path, 'record*.json')) for filename in files: with open(filename, encoding='utf-8') as data_file: data = json.loads(data_file.read()) if os.path.isfile(os.path.join(path, data['cam/image_array'])): img_ok += 1 y.append([data['user/angle'], data['user/throttle']]) img = Image.open( os.path.join(path, data['cam/image_array'])) predictions.append(model.run(pi.run(np.array(img)))) img = np.array(img) images.append(img) images = np.array(images) y = np.array(y) predictions = np.array(predictions) fig, ax = plt.subplots() plt.plot(y[start:end, index]) plt.plot(predictions[start:end, index]) plt.show()
def make_video(tub_path, video_filename='video.avi', model_path=None, preprocess_angle=None, index=None, min_throttle=0., max_throttle=1.): files = glob.glob(os.path.join(tub_path, 'record*.json')) files = sorted( files, key=lambda x: int(re.findall(r'\d+', os.path.basename(x))[0])) if model_path is not None: model = MyModel(min_throttle=min_throttle, max_throttle=max_throttle) model.load(model_path) pi = PreprocessImage() video = None fourcc = cv2.VideoWriter_fourcc(*'XVID') for filename in files: with open(filename, encoding='utf-8') as data_file: data = json.loads(data_file.read()) if os.path.isfile(os.path.join(tub_path, data['cam/image_array'])): frame = cv2.imread( os.path.join(tub_path, data['cam/image_array'])) throttle = data['user/throttle'] angle = data['user/angle'] xa = int(frame.shape[1] * ((angle + 1) / 2.)) ya = int(frame.shape[0] * .95) xt = int(frame.shape[1] * .95) yt = int(frame.shape[0] - frame.shape[0] * throttle) if index is None or index == 0: cv2.circle(frame, (xa, ya), 2, (255, 128, 0), -1) if index is None or index == 1: cv2.circle(frame, (xt, yt), 2, (255, 128, 0), -1) if model_path is not None: img = Image.open( os.path.join(tub_path, data['cam/image_array'])) p_angle, p_throttle = model.run(pi.run(np.array(img))) if preprocess_angle is not None: p_angle = preprocess_angle(p_angle) xa = int(frame.shape[1] * ((p_angle + 1) / 2.)) ya = int(frame.shape[0] * .9) xt = int(frame.shape[1] * .9) yt = int(frame.shape[0] - frame.shape[0] * p_throttle) if index is None or index == 0: cv2.circle(frame, (xa, ya), 2, (0, 128, 255), -1) if index is None or index == 1: cv2.circle(frame, (xt, yt), 2, (0, 128, 255), -1) if video is None: h, w, ch = frame.shape video = cv2.VideoWriter(video_filename, fourcc, 20., (w, h)) video.write(frame) cv2.destroyAllWindows() video.release()
class Submission: """ API Wrapper class which loads a saved model upon construction, and uses this to implement an API for feature selection and missing value prediction. This API will be used to perform active learning evaluation in private. """ def __init__(self): # Load a saved model here. self.model = MyModel() self.model.load('most_popular.npy', 'num_answers.npy') def select_feature(self, masked_data, can_query): """ Use your model to select a new feature to observe from a list of candidate features for each student in the input data, with the goal of selecting features with maximise performance on a held-out set of answers for each student. Args: masked_data (np.array): Array of shape (num_students, num_questions) containing data revealed to the model at the current step. Unobserved values are denoted by -1. can_query (np.array): Binary array of shape (num_students, num_questions), indicating which features can be queried by the model in the current step. Returns: selections (list): List of ints, length num_students, containing the index of the feature selected to query for each student (row) in the dataset. """ # Use the loaded model to perform feature selection. selections = self.model.select_feature(masked_data, can_query) return selections def predict(self, masked_data): """ Use your model to predict missing values in the input data. Args: masked_data (np.array): Array of shape (num_students, num_questions) containing data revealed to the model at the current step. Unobserved values are denoted by -1. Returns: predictions (np.array): Array of shape (num_students, num_questions) containing predictions for the unobserved values in `masked_data`. The values given to the observed data in this array will be ignored. """ # Use the loaded model to perform missing value prediction. predictions = self.model.predict(masked_data) return predictions
def drive(cfg, model_path=None, use_joystick=False, use_chaos=False, min_throttle=0, max_throttle=.5, verbose=0): """ Construct a working robotic vehicle from many parts. Each part runs as a job in the Vehicle loop, calling either it's run or run_threaded method depending on the constructor flag `threaded`. All parts are updated one after another at the framerate given in cfg.DRIVE_LOOP_HZ assuming each part finishes processing in a timely manner. Parts may have named outputs and inputs. The framework handles passing named outputs to parts requesting the same named input. """ V = dk.vehicle.Vehicle() cam = PiCamera(resolution=cfg.CAMERA_RESOLUTION) V.add(cam, outputs=['cam/image_array'], threaded=True) if use_joystick or cfg.USE_JOYSTICK_AS_DEFAULT: ctr = JoystickController( max_throttle=cfg.JOYSTICK_MAX_THROTTLE, steering_scale=cfg.JOYSTICK_STEERING_SCALE, auto_record_on_throttle=cfg.AUTO_RECORD_ON_THROTTLE) else: # This web controller will create a web server that is capable # of managing steering, throttle, and modes, and more. ctr = LocalWebController(use_chaos=use_chaos) V.add(ctr, inputs=['cam/image_array'], outputs=['user/angle', 'user/throttle', 'user/mode', 'recording'], threaded=True) # See if we should even run the pilot module. # This is only needed because the part run_condition only accepts boolean def pilot_condition(mode): if mode == 'user': return False else: return True pilot_condition_part = Lambda(pilot_condition) V.add(pilot_condition_part, inputs=['user/mode'], outputs=['run_pilot']) # Preprocess image if the mode is not user. pi = PreprocessImage() V.add(pi, inputs=['cam/image_array'], outputs=['cam/image_array_preprocessed'], run_condition='run_pilot') # Run the pilot if the mode is not user. kl = MyModel(min_throttle=min_throttle, max_throttle=max_throttle, joystick_max_throttle=cfg.JOYSTICK_MAX_THROTTLE, verbose=verbose) if model_path: kl.load(model_path) V.add(kl, inputs=['cam/image_array_preprocessed'], outputs=['pilot/angle', 'pilot/throttle'], run_condition='run_pilot') # Choose what inputs should change the car. def drive_mode(mode, user_angle, user_throttle, pilot_angle, pilot_throttle): if mode == 'user': return user_angle, user_throttle elif mode == 'local_angle': return pilot_angle, user_throttle else: return pilot_angle, pilot_throttle drive_mode_part = Lambda(drive_mode) V.add(drive_mode_part, inputs=[ 'user/mode', 'user/angle', 'user/throttle', 'pilot/angle', 'pilot/throttle' ], outputs=['angle', 'throttle']) steering_controller = PCA9685(cfg.STEERING_CHANNEL) steering = PWMSteering(controller=steering_controller, left_pulse=cfg.STEERING_LEFT_PWM, right_pulse=cfg.STEERING_RIGHT_PWM) throttle_controller = PCA9685(cfg.THROTTLE_CHANNEL) throttle = PWMThrottle(controller=throttle_controller, max_pulse=cfg.THROTTLE_FORWARD_PWM, zero_pulse=cfg.THROTTLE_STOPPED_PWM, min_pulse=cfg.THROTTLE_REVERSE_PWM) V.add(steering, inputs=['angle']) V.add(throttle, inputs=['throttle']) # add tub to save data inputs = [ 'cam/image_array', 'user/angle', 'user/throttle', 'user/mode', 'timestamp' ] types = ['image_array', 'float', 'float', 'str', 'str'] # multiple tubs # th = TubHandler(path=cfg.DATA_PATH) # tub = th.new_tub_writer(inputs=inputs, types=types) # single tub print("Tub:", cfg.TUB_PATH) tub = TubWriter(path=cfg.TUB_PATH, inputs=inputs, types=types) V.add(tub, inputs=inputs, run_condition='recording') # run the vehicle V.start(rate_hz=cfg.DRIVE_LOOP_HZ, max_loop_count=cfg.MAX_LOOPS)
class Submission: """ API Wrapper class which loads a saved model upon construction, and uses this to implement an API for feature selection and missing value prediction. This API will be used to perform active learning evaluation in private. Note that the model's final predictions must be binary, but that both categorical and binary data is available to the model for feature selection and making predictions. """ def __init__(self): # Load a saved model here. self.model = MyModel() self.model.load('model_task_4_most_popular.npy', 'model_task_4_num_answers.npy') def select_feature(self, masked_data, masked_binary_data, can_query): """ Use your model to select a new feature to observe from a list of candidate features for each student in the input data, with the goal of selecting features with maximise performance on a held-out set of answers for each student. Args: masked_data (np.array): Array of shape (num_students, num_questions) containing data revealed to the model at the current step. Unobserved values are denoted by -1. masked_binary_data (np.array): Array of shape (num_students, num_questions) containing binary data revealed to the model at the current step. Unobserved values are denoted by -1. can_query (np.array): Binary array of shape (num_students, num_questions), indicating which features can be queried by the model in the current step. Returns: selections (list): List of ints, length num_students, containing the index of the feature selected to query for each student (row) in the dataset. """ # Use the loaded model to perform feature selection. selections = self.model.select_feature(masked_data, can_query) return selections def update_model(self, masked_data, masked_binary_data, can_query): """ Update the model to incorporate newly revealed data if desired (e.g. training or updating model state). Args: masked_data (np.array): Array of shape (num_students, num_questions) containing categorical data revealed to the model at the current step. Unobserved values are denoted by -1. masked_binary_data (np.array): Array of shape (num_students, num_questions) containing binary data revealed to the model at the current step. Unobserved values are denoted by -1. can_query (np.array): Binary array of shape (num_students, num_questions), indicating which features can be queried by the model in the current step. Returns: selections (list): List of ints, length num_students, containing the index of the feature selected to query for each student (row) in the dataset. """ # Update the model after new data has been revealed, if required. pass def predict(self, masked_data, masked_binary_data): """ Use your model to predict missing binary values in the input data. Both categorical and binary versions of the observed input data are available for making predictions with. Args: masked_data (np.array): Array of shape (num_students, num_questions) containing categorical data revealed to the model at the current step. Unobserved values are denoted by -1. masked_binary_data (np.array): Array of shape (num_students, num_questions) containing binary data revealed to the model at the current step. Unobserved values are denoted by -1. Returns: predictions (np.array): Array of shape (num_students, num_questions) containing predictions for the unobserved values in `masked_binary_data`. The values given to the observed data in this array will be ignored. """ # Use the loaded model to perform missing value prediction. predictions = self.model.predict(masked_data, masked_binary_data) return predictions