public void train(List<Sample> samples) {
   BLEBeacon.setBLEBeaconIdsToSamples(bleBeacons, samples);
   List<List<Sample>> samplesList = Sample.samplesToConsecutiveSamplesList(samples);
   if (doHyperParameterOptimize) {
     doHyperParameterOptimize = false;
     trainWithHyperParameters(samplesList);
   }
   List<Sample> samplesAvaragedTrain = Sample.meanTrimList(samplesList, minRssi);
   this.trainByAveragedSamples(samplesAvaragedTrain);
 }
  public static List<BLEBeacon> readMapBLEBeacons(InputStream is) {
    int z = 0;
    List<BLEBeacon> bleBeacons = new ArrayList<>();

    try {
      JSONObject json = (JSONObject) JSON.parse(is);

      String type = json.getString("type");
      if (type.equals("FeatureCollection")) {
        JSONArray features = json.getJSONArray("features");
        Iterator<JSONObject> iter = features.iterator();
        while (iter.hasNext()) {
          JSONObject feature = iter.next();
          JSONObject properties = feature.getJSONObject("properties");
          JSONObject geometry = feature.getJSONObject("geometry");
          type = properties.getString("type");
          if (type.equals("beacon")) {

            int major = Integer.parseInt(properties.getString("major"));
            int minor = Integer.parseInt(properties.getString("minor"));
            String uuid = properties.getString("uuid");
            int outPower = Integer.parseInt(properties.getString("power"));
            int interval = Integer.parseInt(properties.getString("interval"));

            double x = geometry.getJSONArray("coordinates").getInt(0);
            double y = geometry.getJSONArray("coordinates").getInt(1);

            BLEBeacon bleBeacon = new BLEBeacon(minor, major, minor, x, y, z);
            bleBeacon.setUuid(uuid);
            bleBeacon.setOutputPower(outPower);

            bleBeacons.add(bleBeacon);
          }
        }
      }
    } catch (NullPointerException | JSONException e) {
      e.printStackTrace();
    }

    return bleBeacons;
  }
  @Override
  public double[] getLogLikelihoods(List<Beacon> beacons, State[] locations) {
    List<Beacon> beaconsCleansed = Beacon.filterBeacons(beacons, minRssi, maxRssi);

    beaconsCleansed = beaconFilter.setBLEBeacon(bleBeacons).filter(beaconsCleansed, locations);
    BLEBeacon.setBLEBeaconIdsToMeasuredBeacons(bleBeacons, beaconsCleansed);
    int[] activeBeaconList = ModelAdaptUtils.beaconsToActiveBeaconArray(beaconsCleansed);

    final double[] ySub = ModelAdaptUtils.beaconsToVecSubset(beaconsCleansed);
    final double[][] X = ModelAdaptUtils.locationsToMat(locations);

    // Adjust bias by average bias
    final double[] rssiBiases = ModelAdaptUtils.biasesToVec(locations);

    double logLLs[] = null;
    try {
      Class<?> cls = gpLDPL.getClass();
      Constructor<?> cst = cls.getConstructor(gpLDPL.getClass());
      final GaussianProcessLDPLMean gpLDPLtmp = (GaussianProcessLDPLMean) cst.newInstance(gpLDPL);
      gpLDPLtmp.updateByActiveBeaconList(activeBeaconList);
      int n = X.length;
      final double logpro[] = new double[n];
      Future<?>[] futures = new Future<?>[n];
      for (int i = 0; i < n; i++) {
        final int idx = i;
        futures[idx] =
            ExecutorServiceHolder.getExecutorService()
                .submit(
                    new Runnable() {
                      public void run() {
                        // Subtract bias from an observation vector.
                        double[] ySubAdjusted = ArrayUtils.addScalar(ySub, -rssiBiases[idx]);
                        logpro[idx] = gpLDPLtmp.logProbaygivenx(X[idx], ySubAdjusted);
                      }
                    });
      }
      for (int i = 0; i < n; i++) {
        futures[i].get();
      }
      logLLs = logpro;
    } catch (InstantiationException
        | IllegalAccessException
        | IllegalArgumentException
        | InvocationTargetException
        | NoSuchMethodException
        | SecurityException e) {
      e.printStackTrace();
    } catch (InterruptedException | ExecutionException e) {
      e.printStackTrace();
    }
    return logLLs;
  }
  protected void trainByAveragedSamples(List<Sample> samples) {
    int nBeacons = bleBeacons.size();
    BLEBeacon.setBLEBeaconIdsToSamples(bleBeacons, samples);
    setupGPLDPL();
    this.samples = samples;
    double[][] X = ModelAdaptUtils.samplesToLocationsMat(samples);
    double[][] Y = ModelAdaptUtils.samplesToBeaconsListMat(samples, minRssi, nBeacons);
    double[][] bLocs = ModelAdaptUtils.BLEBeaconsToMat(bleBeacons, nBeacons);
    gpLDPL.setSourceLocs(bLocs);

    int[] actBecList = new int[nBeacons];
    for (int i = 0; i < nBeacons; i++) actBecList[i] = i;
    gpLDPL.setActiveBeaconList(actBecList);

    gpLDPL.fit(X, Y);
  }