<commit_before>#include <algorithm>
#include <set>
#include <list>
#include <iterator>

#include "otc/otcli.h"
#include "otc/tree_operations.h"
#include "otc/tree_iter.h"
using namespace otc;
using std::vector;
using std::unique_ptr;
using std::set;
using std::list;
using std::map;
using namespace otc;

typedef TreeMappedWithSplits Tree_t;

template <typename T>
std::ostream& operator<<(std::ostream& o, const std::set<T>& s)
{
  auto it = s.begin();
  o<<*it++;
  for(; it != s.end(); it++)
    o<<" "<<*it;
  return o;
}

template <typename T>
std::ostream& operator<<(std::ostream& o, const std::list<T>& s)
{
  auto it = s.begin();
  o<<*it++;
  for(; it != s.end(); it++)
    o<<" "<<*it;
  return o;
}

struct RSplit
{
  set<int> in;
  set<int> out;
  set<int> all;
  RSplit() = default;
  RSplit(const set<int>& i, const set<int>& a)
    :in(i),all(a)
  {
    std::set_difference(all.begin(),all.end(),in.begin(),in.end(),std::inserter(out,out.end()));
    assert(in.size() + out.size() == all.size());
  }
};

void merge(int c1, int c2, map<int,int>& component, map<int,list<int>>& elements)
{
  if (elements[c2].size() > elements[c1].size())
    std::swap(c1,c2);

  for(int i:elements[c2])
    component[i] = c1;

  elements[c1].splice(elements[c1].begin(), elements[c2]);
}

unique_ptr<Tree_t> BUILD(const std::set<int>& tips, const vector<RSplit>& splits)
{
  std::unique_ptr<Tree_t> tree(new Tree_t());
  tree->createRoot();

  if (tips.size() == 1)
  {
    auto Node1 = tree->createChild(tree->getRoot());
    Node1->setOttId(*tips.begin());
    return tree;
  }
  else if (tips.size() == 2)
  {
    auto Node1a = tree->createChild(tree->getRoot());
    auto Node1b = tree->createChild(tree->getRoot());
    auto it = tips.begin();
    Node1a->setOttId(*it++);
    Node1b->setOttId(*it++);
    return tree;
  }

  map<int,int> component;    // tip -> component
  map<int,list<int>> elements; // component -> elements
  for(int i: tips)
  {
    component[i] = i;
    elements[i].push_back(i);
  }

  for(const auto& split: splits)
  {
    int c1 = -1;
    for(int i: split.in)
    {
      int c2 = component[i];
      if (c1 != -1 and c1 != c2)
	merge(c1,c2,component,elements);
      c1 = component[i];
    }
  }

  int first = *tips.begin();
  if (elements[component[first]].size() == tips.size())
  {
    std::cout<<"Failure: 1 component!\n";
    return {};
  }

  std::cout<<"Components:\n";
  map<int,set<int>> subtips;
  for(int c: tips)
  {
    if (c != component[c]) continue;

    set<int>& s = subtips[c];
    for(int l: elements[c])
      s.insert(l);
    std::cout<<"   "<<s<<"\n";
  }

  map<int,vector<RSplit>> subsplits;
  for(const auto& split: splits)
  {
    int first = *split.in.begin();
    int c = component[first];

  }

  return tree;
}

unique_ptr<Tree_t> BUILD(const std::set<int>& tips, const vector<RSplit>& splits, int n)
{

  return {};
}

map<long,int> get_name_mapping(const vector<long>& ids)
{
  std::map<long,int> names;
  for(int i=0;i<ids.size();i++)
    names[ids[i]] = i;
  return names;
}

set<int> remap_names(const set<long>& ids, const map<long,int>& name)
{
  set<int> indices;
  for(auto id: ids)
  {
    auto i = name.find(id);
    if (i == name.end())
      throw OTCError()<<"Can't find ottid "<<id<<" in taxonomy";
    indices.insert(i->second);
  }
  return indices;
}

vector<long> get_vector(const set<long>& ids)
{
  vector<long> v;
  for(long id: ids)
    v.push_back(id);
  return v;
}

unique_ptr<Tree_t> merge(const vector<unique_ptr<Tree_t>>& trees)
{
  // Standardize names to 0..n-1 for this subproblem
  const auto& taxonomy = trees.back();
  auto leafset = taxonomy->getRoot()->getData().desIds;
  std::cout<<leafset<<std::endl;
  // i -> ids[i]
  vector<long> leaves = get_vector(leafset);
  // ids[i] -> i
  auto names = get_name_mapping(leaves);
  auto rename = [&names](const set<long>& ids) {return remap_names(ids,names);};
  auto all_leaves = rename(leafset);

  vector<RSplit> splits;
  for(const auto& tree: trees)
  {
    std::cout<<"Tree!\n";
    auto root = tree->getRoot();
    const auto leafTaxa = rename(root->getData().desIds);
    for(auto nd: iter_post_const(*tree))
    {
      const auto& descendants = rename(nd->getData().desIds);
      RSplit split{descendants, leafTaxa};
      if (split.in.size()>1 and split.out.size())
      {
      	splits.push_back(split);
	std::cout<<split.in<<" | "<<split.out<<"\n";
      }
    }
    BUILD(all_leaves, splits);
  }

  for(int n=2;n<=splits.size();)
  {
    unique_ptr<Tree_t> result = BUILD(all_leaves, splits, n);
    if (not result)
      splits.erase(splits.begin()+(n-1));
    else
      n++;
  }

  return BUILD(all_leaves, splits, splits.size());
}

int main(int argc, char *argv[]) {
    OTCLI otCLI("otc-subproblem-stats",
                "takes at series of tree files. Each is treated as a subproblem.\n" \
                "For each subproblem there is tab-separated report for:\n" \
                "    Subproblem name\n" \
                "    InSp = # of informative (nontrivial) splits\n" \
                "    LSS = size of the leaf label set\n" \
                "    ILSS = size of the set of labels included in at least one \"ingroup\"\n" \
                "    NT = The number of trees.\n" \
                "    TreeSummaryName = tree index or summary name\n" \
                "where the summary name can be Phylo-only or Total. \n" \
                "  \"Total\" summarizes info all trees in the file (including the taxonomy).\n" \
                "  \"Phylo-only\" former summarizes all of the phylogenetic inputs",
                "taxonomy.tre supertree/step_7_scratch/export-sub-temp/ott1000236.tre supertree/step_7_scratch/export-sub-temp/ott1000250.tre");

    vector<unique_ptr<Tree_t>> trees;
    auto get = [&trees](OTCLI &, unique_ptr<Tree_t> nt) {trees.push_back(std::move(nt)); return true;};

    // Want splits for each tip.
    // Not sure these trees are aligned to the taxonomy
    // They should have only terminals in desIds.
    treeProcessingMain<Tree_t>(otCLI, argc, argv, get, nullptr, 1);

    merge(trees);
}
<commit_msg>Stop remapping names.<commit_after>#include <algorithm>
#include <set>
#include <list>
#include <iterator>

#include "otc/otcli.h"
#include "otc/tree_operations.h"
#include "otc/tree_iter.h"
using namespace otc;
using std::vector;
using std::unique_ptr;
using std::set;
using std::list;
using std::map;
using namespace otc;

typedef TreeMappedWithSplits Tree_t;

template <typename T>
std::ostream& operator<<(std::ostream& o, const std::set<T>& s)
{
  auto it = s.begin();
  o<<*it++;
  for(; it != s.end(); it++)
    o<<" "<<*it;
  return o;
}

template <typename T>
std::ostream& operator<<(std::ostream& o, const std::list<T>& s)
{
  auto it = s.begin();
  o<<*it++;
  for(; it != s.end(); it++)
    o<<" "<<*it;
  return o;
}

struct RSplit
{
  set<long> in;
  set<long> out;
  set<long> all;
  RSplit() = default;
  RSplit(const set<long>& i, const set<long>& a)
    :in(i),all(a)
  {
    std::set_difference(all.begin(),all.end(),in.begin(),in.end(),std::inserter(out,out.end()));
    assert(in.size() + out.size() == all.size());
  }
};

void merge(long c1, long c2, map<long,long>& component, map<long,list<long>>& elements)
{
  if (elements[c2].size() > elements[c1].size())
    std::swap(c1,c2);

  for(long i:elements[c2])
    component[i] = c1;

  elements[c1].splice(elements[c1].begin(), elements[c2]);
}

unique_ptr<Tree_t> BUILD(const std::set<long>& tips, const vector<RSplit>& splits)
{
  std::unique_ptr<Tree_t> tree(new Tree_t());
  tree->createRoot();

  if (tips.size() == 1)
  {
    auto Node1 = tree->createChild(tree->getRoot());
    Node1->setOttId(*tips.begin());
    return tree;
  }
  else if (tips.size() == 2)
  {
    auto Node1a = tree->createChild(tree->getRoot());
    auto Node1b = tree->createChild(tree->getRoot());
    auto it = tips.begin();
    Node1a->setOttId(*it++);
    Node1b->setOttId(*it++);
    return tree;
  }

  map<long,long> component;    // tip -> component
  map<long,list<long>> elements; // component -> elements
  for(long i: tips)
  {
    component[i] = i;
    elements[i].push_back(i);
  }

  for(const auto& split: splits)
  {
    long c1 = -1;
    for(long i: split.in)
    {
      long c2 = component[i];
      if (c1 != -1 and c1 != c2)
	merge(c1,c2,component,elements);
      c1 = component[i];
    }
  }

  long first = *tips.begin();
  if (elements[component[first]].size() == tips.size())
  {
    std::cout<<"Failure: 1 component!\n";
    return {};
  }

  std::cout<<"Components:\n";
  map<long,set<long>> subtips;
  for(long c: tips)
  {
    if (c != component[c]) continue;

    set<long>& s = subtips[c];
    for(long l: elements[c])
      s.insert(l);
    std::cout<<"   "<<s<<"\n";
  }

  map<long,vector<RSplit>> subsplits;
  for(const auto& split: splits)
  {
    long first = *split.in.begin();
    long c = component[first];

  }

  return tree;
}

unique_ptr<Tree_t> BUILD(const std::set<long>& tips, const vector<RSplit>& splits, int n)
{

  return {};
}

unique_ptr<Tree_t> merge(const vector<unique_ptr<Tree_t>>& trees)
{
  // Standardize names to 0..n-1 for this subproblem
  const auto& taxonomy = trees.back();
  auto all_leaves = taxonomy->getRoot()->getData().desIds;
  std::cout<<all_leaves<<std::endl;

  vector<RSplit> splits;
  for(const auto& tree: trees)
  {
    std::cout<<"Tree!\n";
    auto root = tree->getRoot();
    const auto leafTaxa = root->getData().desIds;
    for(auto nd: iter_post_const(*tree))
    {
      const auto& descendants = nd->getData().desIds;
      RSplit split{descendants, leafTaxa};
      if (split.in.size()>1 and split.out.size())
      {
      	splits.push_back(split);
	std::cout<<split.in<<" | "<<split.out<<"\n";
      }
    }
    BUILD(all_leaves, splits);
  }

  for(int n=2;n<=splits.size();)
  {
    unique_ptr<Tree_t> result = BUILD(all_leaves, splits, n);
    if (not result)
      splits.erase(splits.begin()+(n-1));
    else
      n++;
  }

  return BUILD(all_leaves, splits, splits.size());
}

int main(int argc, char *argv[]) {
    OTCLI otCLI("otc-subproblem-stats",
                "takes at series of tree files. Each is treated as a subproblem.\n" \
                "For each subproblem there is tab-separated report for:\n" \
                "    Subproblem name\n" \
                "    InSp = # of informative (nontrivial) splits\n" \
                "    LSS = size of the leaf label set\n" \
                "    ILSS = size of the set of labels included in at least one \"ingroup\"\n" \
                "    NT = The number of trees.\n" \
                "    TreeSummaryName = tree index or summary name\n" \
                "where the summary name can be Phylo-only or Total. \n" \
                "  \"Total\" summarizes info all trees in the file (including the taxonomy).\n" \
                "  \"Phylo-only\" former summarizes all of the phylogenetic inputs",
                "taxonomy.tre supertree/step_7_scratch/export-sub-temp/ott1000236.tre supertree/step_7_scratch/export-sub-temp/ott1000250.tre");

    vector<unique_ptr<Tree_t>> trees;
    auto get = [&trees](OTCLI &, unique_ptr<Tree_t> nt) {trees.push_back(std::move(nt)); return true;};

    // Want splits for each tip.
    // Not sure these trees are aligned to the taxonomy
    // They should have only terminals in desIds.
    treeProcessingMain<Tree_t>(otCLI, argc, argv, get, nullptr, 1);

    merge(trees);
}
<|endoftext|>


<commit_before>/*
Copyright (C) 2018 Rodrigo Jose Hernandez Cordoba

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
#include "Grid.h"
#include "aeongames/Renderer.h"
namespace AeonGames
{
    Grid::Grid ( const Renderer& aRenderer ) : mRenderer{aRenderer}
    {
    }
    Grid::~Grid()
    {
    }
}
<commit_msg>Trying to fix Linux build.<commit_after>/*
Copyright (C) 2018 Rodrigo Jose Hernandez Cordoba

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
#include "aeongames/Renderer.h"
#include "Grid.h"
namespace AeonGames
{
    Grid::Grid ( const Renderer& aRenderer ) : mRenderer{aRenderer}
    {
    }
    Grid::~Grid()
    {
    }
}
<|endoftext|>


<commit_before>/*
 * Copyright 2007-2020 CM4all GmbH
 * All rights reserved.
 *
 * author: Max Kellermann <mk@cm4all.com>
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * - Redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer.
 *
 * - Redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the
 * distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
 * FOUNDATION OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 * OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#pragma once

#include "net/SocketAddress.hxx"

#include <sys/socket.h>
#include <sys/un.h>

class UniqueSocketDescriptor;

/**
 * Create a listener socket for a child process.
 */
struct ChildSocket {
	struct sockaddr_un address;

	ChildSocket() noexcept {
		address.sun_family = AF_UNSPEC;
	}

	bool IsDefined() const noexcept {
		return GetAddress().IsDefined();
	}

	/**
	 * Throws std::runtime_error on error.
	 */
	UniqueSocketDescriptor Create(int socket_type, int backlog);

	void Unlink() noexcept;

	SocketAddress GetAddress() const noexcept {
		return SocketAddress((const struct sockaddr *)&address,
				     SUN_LEN(&address));
	}

	/**
	 * Throws std::runtime_error on error.
	 */
	UniqueSocketDescriptor Connect() const;
};
<commit_msg>child_socket: convert struct to class<commit_after>/*
 * Copyright 2007-2020 CM4all GmbH
 * All rights reserved.
 *
 * author: Max Kellermann <mk@cm4all.com>
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * - Redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer.
 *
 * - Redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the
 * distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
 * FOUNDATION OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 * OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#pragma once

#include "net/SocketAddress.hxx"

#include <sys/socket.h>
#include <sys/un.h>

class UniqueSocketDescriptor;

/**
 * Create a listener socket for a child process.
 */
class ChildSocket {
	struct sockaddr_un address;

public:
	ChildSocket() noexcept {
		address.sun_family = AF_UNSPEC;
	}

	bool IsDefined() const noexcept {
		return GetAddress().IsDefined();
	}

	/**
	 * Throws std::runtime_error on error.
	 */
	UniqueSocketDescriptor Create(int socket_type, int backlog);

	void Unlink() noexcept;

	SocketAddress GetAddress() const noexcept {
		return SocketAddress((const struct sockaddr *)&address,
				     SUN_LEN(&address));
	}

	/**
	 * Throws std::runtime_error on error.
	 */
	UniqueSocketDescriptor Connect() const;
};
<|endoftext|>


<commit_before>//===========================================
//  Lumina-DE source code
//  Copyright (c) 2012-2015, Ken Moore
//  Available under the 3-clause BSD license
//  See the LICENSE file for full details
//===========================================
#include "LClock.h"
#include "LSession.h"
#include <LuminaThemes.h>
#include <LuminaXDG.h>

LClock::LClock(QWidget *parent, QString id, bool horizontal) : LPPlugin(parent, id, horizontal){
  button = new QToolButton(this);
    button->setAutoRaise(true);
    button->setToolButtonStyle(Qt::ToolButtonTextOnly);
    button->setStyleSheet("font-weight: bold;");
    button->setPopupMode(QToolButton::DelayedPopup); //make sure it runs the update routine first
    button->setMenu(new QMenu());
	//button->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
	//this->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
    connect(button, SIGNAL(clicked()), this, SLOT(openMenu()));
    connect(button->menu(), SIGNAL(aboutToHide()), this, SIGNAL(MenuClosed()));
  calendar = new QCalendarWidget(this);
  calAct = new QWidgetAction(this);
	calAct->setDefaultWidget(calendar);
  TZMenu = new QMenu(this);
    connect(TZMenu, SIGNAL(triggered(QAction*)), this, SLOT(ChangeTZ(QAction*)) );

  //Now assemble the menu
  button->menu()->addAction(calAct);
  button->menu()->addMenu(TZMenu);

  this->layout()->setContentsMargins(0,0,0,0); //reserve some space on left/right
  this->layout()->addWidget(button);

  //Setup the timer
  timer = new QTimer();
  //Load all the initial settings
  updateFormats();
  LocaleChange();
  ThemeChange();
  OrientationChange();
  //Now connect/start the timer
  connect(timer,SIGNAL(timeout()), this, SLOT(updateTime()) );
  connect(QApplication::instance(), SIGNAL(SessionConfigChanged()), this, SLOT(updateFormats()) );
  timer->start();
}

LClock::~LClock(){
  timer->stop();
  delete timer;
}

void LClock::updateTime(bool adjustformat){
  QDateTime CT = QDateTime::currentDateTime();
  //Now update the display
  QString label;
  QString timelabel;
  QString datelabel;
  if(deftime){ timelabel = CT.time().toString(Qt::DefaultLocaleShortDate) ; }
  else{ timelabel=CT.toString(timefmt); }
  if(defdate){ datelabel = CT.date().toString(Qt::DefaultLocaleShortDate); }
  else{ datelabel = CT.toString(datefmt); }
  if(datetimeorder == "dateonly"){
	  label = datelabel;
	  button->setToolTip(timelabel);
  }else if(datetimeorder == "timedate"){
	  label = timelabel + "\n" + datelabel;
	  button->setToolTip("");
  }else if(datetimeorder == "datetime"){
	  label = datelabel + "\n" + timelabel;
	  button->setToolTip("");
  }else{
	 label = timelabel;
	button->setToolTip(datelabel);
  }
  if( this->layout()->direction() == QBoxLayout::TopToBottom ){
    //different routine for vertical text (need newlines instead of spaces)
    label.replace(" ","\n");
  }
  if(adjustformat){
   //Check the font/spacing for the display and adjust as necessary
    /*double efflines = label.count("\n")+1; //effective lines (with wordwrap)
    if( (button->fontMetrics().height()*efflines) > button->height() ){
      //Force a pixel metric font size to fit everything
      int szH = qRound( (button->height() - button->fontMetrics().lineSpacing() )/efflines );
      //Need to supply a *width* pixel, not a height metric
      int szW = qRound( (szH*button->fontMetrics().maxWidth())/( (double) button->fontMetrics().height()) );
      qDebug() << "Change Clock font:" << button->height() << szH << szW << efflines << button->fontMetrics().height() << button->fontMetrics().lineSpacing();
      button->setStyleSheet("font-weight: bold; font-size: "+QString::number(szW)+"px;");
    }else{
      button->setStyleSheet("font-weight: bold;");
    }*/
  }
  button->setText(label);

}

void LClock::updateFormats(){
  qDebug() << "Updating clock format";
  timefmt = LSession::handle()->sessionSettings()->value("TimeFormat","").toString();
  datefmt = LSession::handle()->sessionSettings()->value("DateFormat","").toString();
  deftime = timefmt.simplified().isEmpty();
  defdate = datefmt.simplified().isEmpty();
  //Adjust the timer interval based on the smallest unit displayed
  if(deftime){ timer->setInterval(500); } //1/2 second
  else if(timefmt.contains("z")){ timer->setInterval(1); } //every millisecond (smallest unit)
  else if(timefmt.contains("s")){ timer->setInterval(500); } //1/2 second
  else if(timefmt.contains("m")){ timer->setInterval(2000); } //2 seconds
  else{ timer->setInterval(1000); } //unknown format - use 1 second interval
  datetimeorder = LSession::handle()->sessionSettings()->value("DateTimeOrder", "timeonly").toString().toLower();
  //this->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred);
  updateTime(true);
  //Now fix the size of the widget with the new size hint
  this->setFixedWidth( this->sizeHint().width() +6);
}

void LClock::updateMenu(){
  QDateTime cdt = QDateTime::currentDateTime();
  TZMenu->setTitle(QString(tr("Time Zone (%1)")).arg(cdt.timeZoneAbbreviation()) );
  calendar->showToday(); //make sure the current month is visible
  calendar->setSelectedDate(QDate::currentDate()); //select the actual date for today
}

void LClock::openMenu(){
  updateMenu();
  button->showMenu();
}

void LClock::closeMenu(){
  button->menu()->hide();
}

void LClock::ChangeTZ(QAction *act){
  LTHEME::setCustomEnvSetting("TZ",act->whatsThis());
  QTimer::singleShot(500, this, SLOT(updateTime()) );
}

void LClock::LocaleChange(){
  //Refresh all the time zone information
  TZMenu->clear();
    TZMenu->addAction(tr("Use System Time"));
    TZMenu->addSeparator();
  QList<QByteArray> TZList = QTimeZone::availableTimeZoneIds();
  //Orgnize time zones for smaller menus (Continent/Country/City)
  // Note: id = Continent/City
  QStringList info;
  for(int i=0; i<TZList.length(); i++){
    QTimeZone tz(TZList[i]);
    if(!QString(tz.id()).contains("/")){ continue; }
    info << "::::"+QString(tz.id()).section("/",0,0)+"::::"+QLocale::countryToString(tz.country())+"::::"+QString(tz.id()).section("/",1,100).replace("_"," ")+"::::"+QString(tz.id());
  }
  //Now sort alphabetically
  info.sort();
  //Now create the menu tree
  QString continent, country; //current continent/country
  QMenu *tmpC=0; //continent menu
  QMenu *tmpCM=0; //country menu
  for(int i=0; i<info.length(); i++){
    //Check if different continent
    if(info[i].section("::::",1,1)!=continent){
      if(tmpC!=0){
        if(tmpCM!=0 && !tmpCM->isEmpty()){
	  tmpC->addMenu(tmpCM);
	}
	if(!tmpC->isEmpty()){ TZMenu->addMenu(tmpC); }
      }
      tmpC = new QMenu(this);
	tmpC->setTitle(info[i].section("::::",1,1));
      tmpCM = new QMenu(this);
	  tmpCM->setTitle(info[i].section("::::",2,2));
    //Check if different country
    }else if(info[i].section("::::",2,2)!=country){
        if(tmpC!=0 && tmpCM!=0 && !tmpCM->isEmpty()){
	  tmpC->addMenu(tmpCM);
	}
	tmpCM = new QMenu(this);
	  tmpCM->setTitle(info[i].section("::::",2,2));
    }
    //Now create the entry within the country menu
    if(tmpCM!=0){
      QAction *act = new QAction(info[i].section("::::",3,3), this);
	act->setWhatsThis(info[i].section("::::",4,4) );
      tmpCM->addAction(act);
    }
    //Save the values for the next run
    continent = info[i].section("::::",1,1);
    country = info[i].section("::::",2,2);

    if(i== info.length()-1){
      //last go through - save all menus
      if(tmpCM!=0 && tmpC!=0 && !tmpCM->isEmpty()){ tmpC->addMenu(tmpCM); }
      if(tmpC!=0 && !tmpC->isEmpty()){ TZMenu->addMenu(tmpC); }
    }
  }

}

void LClock::ThemeChange(){
  TZMenu->setIcon(LXDG::findIcon("clock",""));
}

void LClock::OrientationChange(){
  if(this->layout()->direction()==QBoxLayout::LeftToRight){
    this->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Expanding);
    button->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Expanding);
  }else{
    this->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
    button->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
  }
  updateTime(true); //re-adjust the font/spacings
  this->layout()->update();
}
<commit_msg>Make sure the clock plugin for the panel adjusts to account for 1 or 2 lines of text depending on size limitations.<commit_after>//===========================================
//  Lumina-DE source code
//  Copyright (c) 2012-2015, Ken Moore
//  Available under the 3-clause BSD license
//  See the LICENSE file for full details
//===========================================
#include "LClock.h"
#include "LSession.h"
#include <LuminaThemes.h>
#include <LuminaXDG.h>

LClock::LClock(QWidget *parent, QString id, bool horizontal) : LPPlugin(parent, id, horizontal){
  button = new QToolButton(this);
    button->setAutoRaise(true);
    button->setToolButtonStyle(Qt::ToolButtonTextOnly);
    button->setStyleSheet("font-weight: bold;");
    button->setPopupMode(QToolButton::DelayedPopup); //make sure it runs the update routine first
    button->setMenu(new QMenu());
	//button->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
	//this->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
    connect(button, SIGNAL(clicked()), this, SLOT(openMenu()));
    connect(button->menu(), SIGNAL(aboutToHide()), this, SIGNAL(MenuClosed()));
  calendar = new QCalendarWidget(this);
  calAct = new QWidgetAction(this);
	calAct->setDefaultWidget(calendar);
  TZMenu = new QMenu(this);
    connect(TZMenu, SIGNAL(triggered(QAction*)), this, SLOT(ChangeTZ(QAction*)) );

  //Now assemble the menu
  button->menu()->addAction(calAct);
  button->menu()->addMenu(TZMenu);

  this->layout()->setContentsMargins(0,0,0,0); //reserve some space on left/right
  this->layout()->addWidget(button);

  //Setup the timer
  timer = new QTimer();
  //Load all the initial settings
  updateFormats();
  LocaleChange();
  ThemeChange();
  OrientationChange();
  //Now connect/start the timer
  connect(timer,SIGNAL(timeout()), this, SLOT(updateTime()) );
  connect(QApplication::instance(), SIGNAL(SessionConfigChanged()), this, SLOT(updateFormats()) );
  timer->start();
}

LClock::~LClock(){
  timer->stop();
  delete timer;
}

void LClock::updateTime(bool adjustformat){
  QDateTime CT = QDateTime::currentDateTime();
  //Now update the display
  QString label;
  QString timelabel;
  QString datelabel;
  if(deftime){ timelabel = CT.time().toString(Qt::DefaultLocaleShortDate) ; }
  else{ timelabel=CT.toString(timefmt); }
  if(defdate){ datelabel = CT.date().toString(Qt::DefaultLocaleShortDate); }
  else{ datelabel = CT.toString(datefmt); }
  if(datetimeorder == "dateonly"){
	  label = datelabel;
	  button->setToolTip(timelabel);
  }else if(datetimeorder == "timedate"){
	  label = timelabel + "\n" + datelabel;
	  button->setToolTip("");
  }else if(datetimeorder == "datetime"){
	  label = datelabel + "\n" + timelabel;
	  button->setToolTip("");
  }else{
	 label = timelabel;
	button->setToolTip(datelabel);
  }
  if( this->layout()->direction() == QBoxLayout::TopToBottom ){
    //different routine for vertical text (need newlines instead of spaces)
    label.replace(" ","\n");
  }else if( this->size().height() < 2*this->fontMetrics().height() ){
    label.replace("\n",", ");
  }
  if(adjustformat){
   //Check the font/spacing for the display and adjust as necessary
    /*double efflines = label.count("\n")+1; //effective lines (with wordwrap)
    if( (button->fontMetrics().height()*efflines) > button->height() ){
      //Force a pixel metric font size to fit everything
      int szH = qRound( (button->height() - button->fontMetrics().lineSpacing() )/efflines );
      //Need to supply a *width* pixel, not a height metric
      int szW = qRound( (szH*button->fontMetrics().maxWidth())/( (double) button->fontMetrics().height()) );
      qDebug() << "Change Clock font:" << button->height() << szH << szW << efflines << button->fontMetrics().height() << button->fontMetrics().lineSpacing();
      button->setStyleSheet("font-weight: bold; font-size: "+QString::number(szW)+"px;");
    }else{
      button->setStyleSheet("font-weight: bold;");
    }*/
    this->setFixedWidth( this->sizeHint().width() +6);
  }
  button->setText(label);
}

void LClock::updateFormats(){
  qDebug() << "Updating clock format";
  timefmt = LSession::handle()->sessionSettings()->value("TimeFormat","").toString();
  datefmt = LSession::handle()->sessionSettings()->value("DateFormat","").toString();
  deftime = timefmt.simplified().isEmpty();
  defdate = datefmt.simplified().isEmpty();
  //Adjust the timer interval based on the smallest unit displayed
  if(deftime){ timer->setInterval(500); } //1/2 second
  else if(timefmt.contains("z")){ timer->setInterval(1); } //every millisecond (smallest unit)
  else if(timefmt.contains("s")){ timer->setInterval(500); } //1/2 second
  else if(timefmt.contains("m")){ timer->setInterval(2000); } //2 seconds
  else{ timer->setInterval(1000); } //unknown format - use 1 second interval
  datetimeorder = LSession::handle()->sessionSettings()->value("DateTimeOrder", "timeonly").toString().toLower();
  //this->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred);
  updateTime(true);
  //Now fix the size of the widget with the new size hint
  //this->setFixedWidth( this->sizeHint().width() +6);
}

void LClock::updateMenu(){
  QDateTime cdt = QDateTime::currentDateTime();
  TZMenu->setTitle(QString(tr("Time Zone (%1)")).arg(cdt.timeZoneAbbreviation()) );
  calendar->showToday(); //make sure the current month is visible
  calendar->setSelectedDate(QDate::currentDate()); //select the actual date for today
}

void LClock::openMenu(){
  updateMenu();
  button->showMenu();
}

void LClock::closeMenu(){
  button->menu()->hide();
}

void LClock::ChangeTZ(QAction *act){
  LTHEME::setCustomEnvSetting("TZ",act->whatsThis());
  QTimer::singleShot(500, this, SLOT(updateTime()) );
}

void LClock::LocaleChange(){
  //Refresh all the time zone information
  TZMenu->clear();
    TZMenu->addAction(tr("Use System Time"));
    TZMenu->addSeparator();
  QList<QByteArray> TZList = QTimeZone::availableTimeZoneIds();
  //Orgnize time zones for smaller menus (Continent/Country/City)
  // Note: id = Continent/City
  QStringList info;
  for(int i=0; i<TZList.length(); i++){
    QTimeZone tz(TZList[i]);
    if(!QString(tz.id()).contains("/")){ continue; }
    info << "::::"+QString(tz.id()).section("/",0,0)+"::::"+QLocale::countryToString(tz.country())+"::::"+QString(tz.id()).section("/",1,100).replace("_"," ")+"::::"+QString(tz.id());
  }
  //Now sort alphabetically
  info.sort();
  //Now create the menu tree
  QString continent, country; //current continent/country
  QMenu *tmpC=0; //continent menu
  QMenu *tmpCM=0; //country menu
  for(int i=0; i<info.length(); i++){
    //Check if different continent
    if(info[i].section("::::",1,1)!=continent){
      if(tmpC!=0){
        if(tmpCM!=0 && !tmpCM->isEmpty()){
	  tmpC->addMenu(tmpCM);
	}
	if(!tmpC->isEmpty()){ TZMenu->addMenu(tmpC); }
      }
      tmpC = new QMenu(this);
	tmpC->setTitle(info[i].section("::::",1,1));
      tmpCM = new QMenu(this);
	  tmpCM->setTitle(info[i].section("::::",2,2));
    //Check if different country
    }else if(info[i].section("::::",2,2)!=country){
        if(tmpC!=0 && tmpCM!=0 && !tmpCM->isEmpty()){
	  tmpC->addMenu(tmpCM);
	}
	tmpCM = new QMenu(this);
	  tmpCM->setTitle(info[i].section("::::",2,2));
    }
    //Now create the entry within the country menu
    if(tmpCM!=0){
      QAction *act = new QAction(info[i].section("::::",3,3), this);
	act->setWhatsThis(info[i].section("::::",4,4) );
      tmpCM->addAction(act);
    }
    //Save the values for the next run
    continent = info[i].section("::::",1,1);
    country = info[i].section("::::",2,2);

    if(i== info.length()-1){
      //last go through - save all menus
      if(tmpCM!=0 && tmpC!=0 && !tmpCM->isEmpty()){ tmpC->addMenu(tmpCM); }
      if(tmpC!=0 && !tmpC->isEmpty()){ TZMenu->addMenu(tmpC); }
    }
  }

}

void LClock::ThemeChange(){
  TZMenu->setIcon(LXDG::findIcon("clock",""));
}

void LClock::OrientationChange(){
  if(this->layout()->direction()==QBoxLayout::LeftToRight){
    this->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Expanding);
    button->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Expanding);
  }else{
    this->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
    button->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
  }
  updateTime(true); //re-adjust the font/spacings
  this->layout()->update();
}
<|endoftext|>


<commit_before>// This file is part of the dune-gdt project:
//   https://github.com/dune-community/dune-gdt
// Copyright 2010-2018 dune-gdt developers and contributors. All rights reserved.
// License: Dual licensed as BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)
//      or  GPL-2.0+ (http://opensource.org/licenses/gpl-license)
//          with "runtime exception" (http://www.dune-project.org/license.html)
// Authors:
//   Felix Schindler (2015 - 2017)
//   Rene Milk       (2016 - 2018)
//   Tobias Leibner  (2016 - 2017)

#ifndef DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH
#define DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH

#include <vector>

#include <dune/common/dynvector.hh>

#include <dune/xt/common/crtp.hh>

#include <dune/xt/functions/type_traits.hh>

#include <dune/xt/grid/type_traits.hh>

#include <dune/gdt/spaces/basefunctionset/interface.hh>

namespace Dune {
namespace GDT {

template <class TestBase, class Field = typename TestBase::RangeFieldType>
class LocalVolumeFunctionalInterface
{
  static_assert(XT::Functions::is_localfunction_set<TestBase>::value, "");

public:
  typedef TestBase TestBaseType;
  typedef Field FieldType;

  virtual ~LocalVolumeFunctionalInterface() = default;

  virtual void apply(const TestBaseType& test_basis, DynamicVector<FieldType>& ret) const = 0;

  DynamicVector<FieldType> apply(const TestBaseType& test_basis) const
  {
    DynamicVector<FieldType> ret(test_basis.size(), 0.);
    apply(test_basis, ret);
    return ret;
  }
}; // class LocalFunctionalInterface

template <class TestBase, class Intersection, class Field = typename TestBase::RangeFieldType>
class LocalFaceFunctionalInterface
{
  static_assert(XT::Functions::is_localfunction_set<TestBase>::value, "");
  static_assert(XT::Grid::is_intersection<Intersection>::value, "");

public:
  typedef TestBase TestBaseType;
  typedef Intersection IntersectionType;
  typedef Field FieldType;

  virtual ~LocalFaceFunctionalInterface() = default;

  virtual void
  apply(const TestBaseType& test_basis, const IntersectionType& intersection, DynamicVector<FieldType>& ret) const = 0;

  DynamicVector<FieldType> apply(const TestBaseType& test_basis, const IntersectionType& intersection) const
  {
    DynamicVector<FieldType> ret(test_basis.size(), 0.);
    apply(test_basis, intersection, ret);
    return ret;
  }
}; // class LocalFaceFunctionalInterface

} // namespace GDT
} // namespace Dune

#endif // DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH
<commit_msg>[WIP|local.functionals.interfaces] disable all that is not yet rewritten<commit_after>// This file is part of the dune-gdt project:
//   https://github.com/dune-community/dune-gdt
// Copyright 2010-2018 dune-gdt developers and contributors. All rights reserved.
// License: Dual licensed as BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)
//      or  GPL-2.0+ (http://opensource.org/licenses/gpl-license)
//          with "runtime exception" (http://www.dune-project.org/license.html)
// Authors:
//   Felix Schindler (2015 - 2017)
//   Rene Milk       (2016 - 2018)
//   Tobias Leibner  (2016 - 2017)

#ifndef DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH
#define DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH

#include <vector>

#include <dune/common/dynvector.hh>

#include <dune/xt/common/crtp.hh>

#include <dune/xt/functions/type_traits.hh>

#include <dune/xt/grid/type_traits.hh>

#include <dune/gdt/spaces/basefunctionset/interface.hh>

namespace Dune {
namespace GDT {

template <class TestBase, class Field = typename TestBase::RangeFieldType>
class LocalVolumeFunctionalInterface
{
  static_assert(XT::Functions::is_localfunction_set<TestBase>::value, "");

public:
  typedef TestBase TestBaseType;
  typedef Field FieldType;

  virtual ~LocalVolumeFunctionalInterface() = default;

  virtual void apply(const TestBaseType& test_basis, DynamicVector<FieldType>& ret) const = 0;

  DynamicVector<FieldType> apply(const TestBaseType& test_basis) const
  {
    DynamicVector<FieldType> ret(test_basis.size(), 0.);
    apply(test_basis, ret);
    return ret;
  }
}; // class LocalFunctionalInterface

#if 0
template <class TestBase, class Intersection, class Field = typename TestBase::RangeFieldType>
class LocalFaceFunctionalInterface
{
  static_assert(XT::Functions::is_localfunction_set<TestBase>::value, "");
  static_assert(XT::Grid::is_intersection<Intersection>::value, "");

public:
  typedef TestBase TestBaseType;
  typedef Intersection IntersectionType;
  typedef Field FieldType;

  virtual ~LocalFaceFunctionalInterface() = default;

  virtual void
  apply(const TestBaseType& test_basis, const IntersectionType& intersection, DynamicVector<FieldType>& ret) const = 0;

  DynamicVector<FieldType> apply(const TestBaseType& test_basis, const IntersectionType& intersection) const
  {
    DynamicVector<FieldType> ret(test_basis.size(), 0.);
    apply(test_basis, intersection, ret);
    return ret;
  }
}; // class LocalFaceFunctionalInterface
#endif // 0

} // namespace GDT
} // namespace Dune

#endif // DUNE_GDT_LOCAL_FUNCTIONALS_INTERFACES_HH
<|endoftext|>


<commit_before>/******************************************************************************
 *                    _   _____   __________                                  *
 *                   | | / / _ | / __/_  __/     Visibility                   *
 *                   | |/ / __ |_\ \  / /          Across                     *
 *                   |___/_/ |_/___/ /_/       Space and Time                 *
 *                                                                            *
 * This file is part of VAST. It is subject to the license terms in the       *
 * LICENSE file found in the top-level directory of this distribution and at  *
 * http://vast.io/license. No part of VAST, including this file, may be       *
 * copied, modified, propagated, or distributed except according to the terms *
 * contained in the LICENSE file.                                             *
 ******************************************************************************/

#include "vast/meta_index.hpp"

#include "vast/data.hpp"
#include "vast/detail/overload.hpp"
#include "vast/detail/set_operations.hpp"
#include "vast/detail/string.hpp"
#include "vast/expression.hpp"
#include "vast/logger.hpp"
#include "vast/system/atoms.hpp"
#include "vast/table_slice.hpp"
#include "vast/time.hpp"

namespace vast {

void meta_index::add(const uuid& partition, const table_slice& slice) {
  auto& part_synopsis = partition_synopses_[partition];
  auto& layout = slice.layout();
  if (blacklisted_layouts_.count(layout) == 1)
    return;
  auto i = part_synopsis.find(layout);
  table_synopsis* table_syn;
  if (i != part_synopsis.end()) {
    table_syn = &i->second;
  } else {
    // Create new synopses for a layout we haven't seen before.
    i = part_synopsis.emplace(layout, table_synopsis{}).first;
    table_syn = &i->second;
    for (auto& field : layout.fields)
      if (!has_skip_attribute(field.type))
        if (i->second.emplace_back(make_synopsis(field.type, synopsis_options_))
            != nullptr)
          VAST_DEBUG(this, "created new synopsis structure for type", field.type);
    // If we couldn't create a single synopsis for the layout, we will no
    // longer attempt to create synopses in the future.
    auto is_nullptr = [](auto& x) { return x == nullptr; };
    if (std::all_of(table_syn->begin(), table_syn->end(), is_nullptr)) {
      VAST_DEBUG(this, "could not create a synopsis for layout:", layout);
      blacklisted_layouts_.insert(layout);
    }
  }
  VAST_ASSERT(table_syn->size() == slice.columns());
  for (size_t col = 0; col < slice.columns(); ++col)
    if (auto& syn = (*table_syn)[col])
      for (size_t row = 0; row < slice.rows(); ++row)
        syn->add(slice.at(row, col));
}

std::vector<uuid> meta_index::lookup(const expression& expr) const {
  VAST_ASSERT(!caf::holds_alternative<caf::none_t>(expr));
  // TODO: we could consider a flat_set<uuid> here, which would then have
  // overloads for inplace intersection/union and simplify the implementation
  // of this function a bit.
  using result_type = std::vector<uuid>;
  auto all_partitions = [&] {
    result_type result;
    result.reserve(partition_synopses_.size());
    std::transform(partition_synopses_.begin(),
                   partition_synopses_.end(),
                   std::back_inserter(result),
                   [](auto& x) { return x.first; });
    std::sort(result.begin(), result.end());
    return result;
  };
  return caf::visit(detail::overload(
    [&](const conjunction& x) -> result_type {
      VAST_ASSERT(!x.empty());
      auto i = x.begin();
      auto result = lookup(*i);
      if (!result.empty())
        for (++i; i != x.end(); ++i) {
          auto xs = lookup(*i);
          if (xs.empty())
            return xs; // short-circuit
          detail::inplace_intersect(result, xs);
        }
      return result;
    },
    [&](const disjunction& x) -> result_type {
      result_type result;
      for (auto& op : x) {
        auto xs = lookup(op);
        if (xs.size() == partition_synopses_.size())
          return xs; // short-circuit
        detail::inplace_unify(result, xs);
      }
      return result;
    },
    [&](const negation&) -> result_type {
      // We cannot handle negations, because a synopsis may return false
      // positives, and negating such a result may cause false negatives.
      return all_partitions();
    },
    [&](const predicate& x) -> result_type {
      // Performs a lookup on all *matching* synopses with operator and data
      // from the predicate of the expression. The match function uses a record
      // field to determine whether the synopsis should be queried.
      auto search = [&](auto match) {
        VAST_ASSERT(caf::holds_alternative<data>(x.rhs));
        auto& rhs = caf::get<data>(x.rhs);
        result_type result;
        auto found_matching_synopsis = false;
        // We factor the nested loop into a lambda so that we can abort the
        // iteration more easily with a return statement.
        auto lookup = [&](auto& part_id, auto& part_syn) {
          for (auto& [layout, table_syn] : part_syn)
            for (size_t i = 0; i < table_syn.size(); ++i)
              if (table_syn[i] && match(layout.fields[i])) {
                found_matching_synopsis = true;
                if (table_syn[i]->lookup(x.op, make_view(rhs))) {
                  result.push_back(part_id);
                  return;
                }
              }
        };
        for (auto& [part_id, part_syn] : partition_synopses_)
          lookup(part_id, part_syn);
        std::sort(result.begin(), result.end());
        return found_matching_synopsis ? result : all_partitions();
      };
      return caf::visit(detail::overload(
        [&](const attribute_extractor& lhs, const data& d) -> result_type {
          if (lhs.attr == system::time_atom::value) {
            auto pred = [](auto& field) {
              return has_attribute(field.type, "time");
            };
            return search(pred);
          } else if (lhs.attr == system::type_atom::value) {
            result_type result;
            for (auto& [part_id, part_syn] : partition_synopses_)
              for (auto& pair : part_syn)
                if (evaluate(pair.first.name(), x.op, d)) {
                  result.push_back(part_id);
                  break;
                }
            return result;
          }
          VAST_WARNING(this, "cannot process attribute extractor:", lhs.attr);
          return all_partitions();
        },
        [&](const key_extractor& lhs, const data&) -> result_type {
          auto pred = [&](auto& field) {
            return detail::ends_with(field.name, lhs.key);
          };
          return search(pred);
        },
        [&](const type_extractor& lhs, const data&) -> result_type {
          auto pred = [&](auto& field) { return field.type == lhs.type; };
          return search(pred);
        },
        [&](const auto&, const auto&) -> result_type {
          VAST_WARNING(this, "cannot process predicate:", x);
          return all_partitions();
        }
      ), x.lhs, x.rhs);
    },
    [&](caf::none_t) -> result_type {
      VAST_ERROR(this, "received an empty expression");
      VAST_ASSERT(!"invalid expression");
      return all_partitions();
    }
  ), expr);
}

synopsis_options& meta_index::factory_options() {
  return synopsis_options_;
}

caf::error inspect(caf::serializer& sink, const meta_index& x) {
  return sink(x.synopsis_options_, x.partition_synopses_);
}

caf::error inspect(caf::deserializer& source, meta_index& x) {
  return source(x.synopsis_options_, x.partition_synopses_);
}

} // namespace vast
<commit_msg>Fix meta index bug<commit_after>/******************************************************************************
 *                    _   _____   __________                                  *
 *                   | | / / _ | / __/_  __/     Visibility                   *
 *                   | |/ / __ |_\ \  / /          Across                     *
 *                   |___/_/ |_/___/ /_/       Space and Time                 *
 *                                                                            *
 * This file is part of VAST. It is subject to the license terms in the       *
 * LICENSE file found in the top-level directory of this distribution and at  *
 * http://vast.io/license. No part of VAST, including this file, may be       *
 * copied, modified, propagated, or distributed except according to the terms *
 * contained in the LICENSE file.                                             *
 ******************************************************************************/

#include "vast/meta_index.hpp"

#include "vast/data.hpp"
#include "vast/detail/overload.hpp"
#include "vast/detail/set_operations.hpp"
#include "vast/detail/string.hpp"
#include "vast/expression.hpp"
#include "vast/logger.hpp"
#include "vast/system/atoms.hpp"
#include "vast/table_slice.hpp"
#include "vast/time.hpp"

namespace vast {

void meta_index::add(const uuid& partition, const table_slice& slice) {
  auto& part_synopsis = partition_synopses_[partition];
  auto& layout = slice.layout();
  if (blacklisted_layouts_.count(layout) == 1)
    return;
  auto i = part_synopsis.find(layout);
  table_synopsis* table_syn;
  if (i != part_synopsis.end()) {
    table_syn = &i->second;
  } else {
    // Create new synopses for a layout we haven't seen before.
    i = part_synopsis.emplace(layout, table_synopsis{}).first;
    table_syn = &i->second;
    for (auto& field : layout.fields) {
      auto synopsis = has_skip_attribute(field.type)
                        ? nullptr
                        : make_synopsis(field.type, synopsis_options_);
      if (table_syn->emplace_back(std::move(synopsis)) != nullptr)
          VAST_DEBUG(this, "created new synopsis structure for type", field.type);
    }
    // If we couldn't create a single synopsis for the layout, we will no
    // longer attempt to create synopses in the future.
    auto is_nullptr = [](auto& x) { return x == nullptr; };
    if (std::all_of(table_syn->begin(), table_syn->end(), is_nullptr)) {
      VAST_DEBUG(this, "could not create a synopsis for layout:", layout);
      blacklisted_layouts_.insert(layout);
    }
  }
  VAST_ASSERT(table_syn->size() == slice.columns());
  for (size_t col = 0; col < slice.columns(); ++col)
    if (auto& syn = (*table_syn)[col])
      for (size_t row = 0; row < slice.rows(); ++row)
        syn->add(slice.at(row, col));
}

std::vector<uuid> meta_index::lookup(const expression& expr) const {
  VAST_ASSERT(!caf::holds_alternative<caf::none_t>(expr));
  // TODO: we could consider a flat_set<uuid> here, which would then have
  // overloads for inplace intersection/union and simplify the implementation
  // of this function a bit.
  using result_type = std::vector<uuid>;
  auto all_partitions = [&] {
    result_type result;
    result.reserve(partition_synopses_.size());
    std::transform(partition_synopses_.begin(),
                   partition_synopses_.end(),
                   std::back_inserter(result),
                   [](auto& x) { return x.first; });
    std::sort(result.begin(), result.end());
    return result;
  };
  return caf::visit(detail::overload(
    [&](const conjunction& x) -> result_type {
      VAST_ASSERT(!x.empty());
      auto i = x.begin();
      auto result = lookup(*i);
      if (!result.empty())
        for (++i; i != x.end(); ++i) {
          auto xs = lookup(*i);
          if (xs.empty())
            return xs; // short-circuit
          detail::inplace_intersect(result, xs);
        }
      return result;
    },
    [&](const disjunction& x) -> result_type {
      result_type result;
      for (auto& op : x) {
        auto xs = lookup(op);
        if (xs.size() == partition_synopses_.size())
          return xs; // short-circuit
        detail::inplace_unify(result, xs);
      }
      return result;
    },
    [&](const negation&) -> result_type {
      // We cannot handle negations, because a synopsis may return false
      // positives, and negating such a result may cause false negatives.
      return all_partitions();
    },
    [&](const predicate& x) -> result_type {
      // Performs a lookup on all *matching* synopses with operator and data
      // from the predicate of the expression. The match function uses a record
      // field to determine whether the synopsis should be queried.
      auto search = [&](auto match) {
        VAST_ASSERT(caf::holds_alternative<data>(x.rhs));
        auto& rhs = caf::get<data>(x.rhs);
        result_type result;
        auto found_matching_synopsis = false;
        // We factor the nested loop into a lambda so that we can abort the
        // iteration more easily with a return statement.
        auto lookup = [&](auto& part_id, auto& part_syn) {
          for (auto& [layout, table_syn] : part_syn)
            for (size_t i = 0; i < table_syn.size(); ++i)
              if (table_syn[i] && match(layout.fields[i])) {
                found_matching_synopsis = true;
                if (table_syn[i]->lookup(x.op, make_view(rhs))) {
                  result.push_back(part_id);
                  return;
                }
              }
        };
        for (auto& [part_id, part_syn] : partition_synopses_)
          lookup(part_id, part_syn);
        std::sort(result.begin(), result.end());
        return found_matching_synopsis ? result : all_partitions();
      };
      return caf::visit(detail::overload(
        [&](const attribute_extractor& lhs, const data& d) -> result_type {
          if (lhs.attr == system::time_atom::value) {
            auto pred = [](auto& field) {
              return has_attribute(field.type, "time");
            };
            return search(pred);
          } else if (lhs.attr == system::type_atom::value) {
            result_type result;
            for (auto& [part_id, part_syn] : partition_synopses_)
              for (auto& pair : part_syn)
                if (evaluate(pair.first.name(), x.op, d)) {
                  result.push_back(part_id);
                  break;
                }
            return result;
          }
          VAST_WARNING(this, "cannot process attribute extractor:", lhs.attr);
          return all_partitions();
        },
        [&](const key_extractor& lhs, const data&) -> result_type {
          auto pred = [&](auto& field) {
            return detail::ends_with(field.name, lhs.key);
          };
          return search(pred);
        },
        [&](const type_extractor& lhs, const data&) -> result_type {
          auto pred = [&](auto& field) { return field.type == lhs.type; };
          return search(pred);
        },
        [&](const auto&, const auto&) -> result_type {
          VAST_WARNING(this, "cannot process predicate:", x);
          return all_partitions();
        }
      ), x.lhs, x.rhs);
    },
    [&](caf::none_t) -> result_type {
      VAST_ERROR(this, "received an empty expression");
      VAST_ASSERT(!"invalid expression");
      return all_partitions();
    }
  ), expr);
}

synopsis_options& meta_index::factory_options() {
  return synopsis_options_;
}

caf::error inspect(caf::serializer& sink, const meta_index& x) {
  return sink(x.synopsis_options_, x.partition_synopses_);
}

caf::error inspect(caf::deserializer& source, meta_index& x) {
  return source(x.synopsis_options_, x.partition_synopses_);
}

} // namespace vast
<|endoftext|>


<commit_before>#include "HelloWorldScene.h"
#include "AppMacros.h"
#include "cocos-ext.h"
USING_NS_CC;
using namespace cocos2d;
using namespace cocos2d::extension;
using namespace cocos2d::ui;

CCScene* HelloWorld::scene()
{
    // 'scene' is an autorelease object
    CCScene *scene = CCScene::create();

    // 'layer' is an autorelease object
    HelloWorld *layer = HelloWorld::create();

    // add layer as a child to scene
    scene->addChild(layer);

    // return the scene
    return scene;
}

// on "init" you need to initialize your instance
bool HelloWorld::init()
{
	m_pNode1 = NULL;
    m_pNode2 = NULL;
	setTouchEnabled( true );
	CCSize s =  CCDirector::sharedDirector()->getWinSize();
	/*CCSprite * spr = CCSprite::create("HelloWorld.png");
	spr->setPosition(ccp(s.width/2,s.height/2));
	spr->setScale(2.0f);
	this->addChild(spr);*/

	posx1 = posx2 = 0;

	CCEGLView::sharedOpenGLView()->setDesignResolutionSize( 960, 640, kResolutionShowAll );
	CCFileUtils* pFileUtils = CCFileUtils::sharedFileUtils();
    std::vector<std::string> searchPaths;

	searchPaths.push_back("publish");
	pFileUtils->setSearchPaths(searchPaths);
    ////////////////////////////////读取两个场景 pNode pNode2
    CCNode *pNode = SceneReader::sharedSceneReader()->createNodeWithSceneFile("NewScene.json");
    CCNode *pNode2 = SceneReader::sharedSceneReader()->createNodeWithSceneFile("NewScene2.json");
   //---------------------------------------------------------------------------------------------
	//step1  一个做远一个做中景
	addChild( pNode );
	addChild( pNode2 );
	CCNode* pSprite = GetNodeFromParent( pNode ,"testweapon1" );  //将场景中的一个子Node结点去出来控制
	pSprite->runAction( CCMoveBy::create( 10, ccp(1000, 0 ) ) );
	onCreateTouch( pNode, pNode2 );

	//step2  两个场景依次向后排列
	//CCArray *pArray = CCArray::create();
	//pArray->addObject( pNode );
	//pArray->addObject( pNode2 );
	//CCNode *pMergeParent = MergeNode( pArray );
    //addChild( pMergeParent );
	//onCreateTouch( pMergeParent, NULL );

    return true;
}
//------------------------------------------------------------
//
//
void HelloWorld::onCreateTouch( CCNode *pNode1, CCNode *pNode2 )
{
	m_pNode1 = pNode1;
    m_pNode2 = pNode2;
}
//-----------------------------------------------------------------------
//
//
CCNode* HelloWorld::MergeNode( CCArray* pArray  )
{
	CCSize s =  CCDirector::sharedDirector()->getWinSize();
	CCNode *ParantNode = CCNode::create();
	for( int i = 0; i < pArray->count(); i++ )
	{
		CCNode *pSubNode = (CCNode*)pArray->objectAtIndex(i);
		ParantNode->addChild( pSubNode );
		pSubNode->setPosition( ccpAdd( pSubNode->getPosition(), ccp( s.width * i, 0 ) ) );
	}
	//for( int i = 0; i < pArray->count(); i++ )
	//{
	//	CCNode *pSubNode = (CCNode*)pArray->objectAtIndex(i);

	//	for( int j = 0; j < pSubNode->getChildrenCount(); j++  )
	//	{
	//		CCNode *pSprite = (CCNode*)pSubNode->getChildren()->objectAtIndex(j);
	//		pSubNode->removeChild( pSprite );
	//		ParantNode->addChild( pSprite );
	//	}
	//}

	return ParantNode;
}
//------------------------------------------------------------
//
//
CCNode* HelloWorld::GetNodeFromParent( CCNode *parent, std::string key )
{
	for( int i = 0; i < parent->getChildrenCount(); i++ )
	{
		 CCNode *pSubNode = ( CCNode* )parent->getChildren()->objectAtIndex( i );
		 if( NULL != pSubNode->getComponent(key.c_str()) )
		 {
			 return pSubNode;
		 }
	}
	return NULL;
}

void HelloWorld::menuCloseCallback(CCObject* pSender)
{
#if (CC_TARGET_PLATFORM == CC_PLATFORM_WINRT) || (CC_TARGET_PLATFORM == CC_PLATFORM_WP8)
	CCMessageBox("You pressed the close button. Windows Store Apps do not implement a close button.","Alert");
#else
    CCDirector::sharedDirector()->end();
#if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
    exit(0);
#endif
#endif
}

void HelloWorld::registerWithTouchDispatcher(void)
{
        CCDirector::sharedDirector()->getTouchDispatcher()->addStandardDelegate(this, 0);
}

void HelloWorld::ccTouchesBegan(CCSet *pTouches, CCEvent *pEvent)
{
//    int index = 0;
//    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
//    {
//        index++;
//        CCTouch* pTouch = (CCTouch*)(*iterTouch);
//        CCPoint location = pTouch->getLocation();
//        CCPoint perLocation = pTouch->getPreviousLocation();
//        float value = location.x - perLocation.x;
//        posx1 += value;
//        posx2 += (value / 2);
//        ///
////        printf("\n location.x:%f, location.y:%f",location.x,location.y);
//        _layerColor->setPosition(ccp(posx1, visibleSize.height/2));
//    }
}

void HelloWorld::ccTouchesMoved(CCSet *pTouches, CCEvent *pEvent)
{
    int index = 0;
    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
    {
        index++;
        CCTouch* pTouch = (CCTouch*)(*iterTouch);
        CCPoint location = pTouch->getLocation();
        CCPoint perLocation = pTouch->getPreviousLocation();
        float value = location.x - perLocation.x;
        posx1 += value;
        posx2 += (value / 2);
		if( NULL != m_pNode1 )
		{
			m_pNode1->setPosition(ccp(posx1,0));
		}
		if( NULL != m_pNode2 )
		{
			m_pNode2->setPosition(ccp(posx2,0));
		}
    }
}

void HelloWorld::ccTouchesEnded(CCSet *pTouches, CCEvent *pEvent)
{
//    int index = 0;
//    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
//    {
//        index++;
//        CCTouch* pTouch = (CCTouch*)(*iterTouch);
//        CCPoint location = pTouch->getLocation();
//        CCPoint perLocation = pTouch->getPreviousLocation();
//        float value = location.x - perLocation.x;
//        posx1 += value;
//        posx2 += (value / 2);
//        ///
////        printf("\n location.x:%f, location.y:%f",location.x,location.y);
//        _layerColor->setPosition(ccp(posx1, visibleSize.height/2));
//    }
}

void HelloWorld::ccTouchesCancelled(CCSet *pTouches, CCEvent *pEvent)
{

}

<commit_msg>chang log<commit_after>#include "HelloWorldScene.h"
#include "AppMacros.h"
#include "cocos-ext.h"
USING_NS_CC;
using namespace cocos2d;
using namespace cocos2d::extension;
using namespace cocos2d::ui;

CCScene* HelloWorld::scene()
{
    // 'scene' is an autorelease object
    CCScene *scene = CCScene::create();

    // 'layer' is an autorelease object
    HelloWorld *layer = HelloWorld::create();

    // add layer as a child to scene
    scene->addChild(layer);

    // return the scene
    return scene;
}

// on "init" you need to initialize your instance
bool HelloWorld::init()
{
	m_pNode1 = NULL;
    m_pNode2 = NULL;
	setTouchEnabled( true );
	CCSize s =  CCDirector::sharedDirector()->getWinSize();
	/*CCSprite * spr = CCSprite::create("HelloWorld.png");
	spr->setPosition(ccp(s.width/2,s.height/2));
	spr->setScale(2.0f);
	this->addChild(spr);*/

	posx1 = posx2 = 0;

	CCEGLView::sharedOpenGLView()->setDesignResolutionSize( 960, 640, kResolutionShowAll );
	CCFileUtils* pFileUtils = CCFileUtils::sharedFileUtils();
    std::vector<std::string> searchPaths;

	searchPaths.push_back("publish");
	pFileUtils->setSearchPaths(searchPaths);
    ////////////////////////////////读取两个场景 pNode pNode2
    CCNode *pNode = SceneReader::sharedSceneReader()->createNodeWithSceneFile("NewScene.json");
    CCNode *pNode2 = SceneReader::sharedSceneReader()->createNodeWithSceneFile("NewScene2.json");
   //---------------------------------------------------------------------------------------------
	//step1  一个做远景一个做中景
	addChild( pNode );
	addChild( pNode2 );
	CCNode* pSprite = GetNodeFromParent( pNode ,"testweapon1" );  //将场景中的一个子Node结点取出来控制
	pSprite->runAction( CCMoveBy::create( 10, ccp(1000, 0 ) ) );
	onCreateTouch( pNode, pNode2 );

	//step2  两个场景依次向后排列
	//CCArray *pArray = CCArray::create();
	//pArray->addObject( pNode );
	//pArray->addObject( pNode2 );
	//CCNode *pMergeParent = MergeNode( pArray );
    //addChild( pMergeParent );
	//onCreateTouch( pMergeParent, NULL );

    return true;
}
//------------------------------------------------------------
//
//
void HelloWorld::onCreateTouch( CCNode *pNode1, CCNode *pNode2 )
{
	m_pNode1 = pNode1;
    m_pNode2 = pNode2;
}
//-----------------------------------------------------------------------
//
//
CCNode* HelloWorld::MergeNode( CCArray* pArray  )
{
	CCSize s =  CCDirector::sharedDirector()->getWinSize();
	CCNode *ParantNode = CCNode::create();
	for( int i = 0; i < pArray->count(); i++ )
	{
		CCNode *pSubNode = (CCNode*)pArray->objectAtIndex(i);
		ParantNode->addChild( pSubNode );
		pSubNode->setPosition( ccpAdd( pSubNode->getPosition(), ccp( s.width * i, 0 ) ) );
	}
	//for( int i = 0; i < pArray->count(); i++ )
	//{
	//	CCNode *pSubNode = (CCNode*)pArray->objectAtIndex(i);

	//	for( int j = 0; j < pSubNode->getChildrenCount(); j++  )
	//	{
	//		CCNode *pSprite = (CCNode*)pSubNode->getChildren()->objectAtIndex(j);
	//		pSubNode->removeChild( pSprite );
	//		ParantNode->addChild( pSprite );
	//	}
	//}

	return ParantNode;
}
//------------------------------------------------------------
//
//
CCNode* HelloWorld::GetNodeFromParent( CCNode *parent, std::string key )
{
	for( int i = 0; i < parent->getChildrenCount(); i++ )
	{
		 CCNode *pSubNode = ( CCNode* )parent->getChildren()->objectAtIndex( i );
		 if( NULL != pSubNode->getComponent(key.c_str()) )
		 {
			 return pSubNode;
		 }
	}
	return NULL;
}

void HelloWorld::menuCloseCallback(CCObject* pSender)
{
#if (CC_TARGET_PLATFORM == CC_PLATFORM_WINRT) || (CC_TARGET_PLATFORM == CC_PLATFORM_WP8)
	CCMessageBox("You pressed the close button. Windows Store Apps do not implement a close button.","Alert");
#else
    CCDirector::sharedDirector()->end();
#if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
    exit(0);
#endif
#endif
}

void HelloWorld::registerWithTouchDispatcher(void)
{
        CCDirector::sharedDirector()->getTouchDispatcher()->addStandardDelegate(this, 0);
}

void HelloWorld::ccTouchesBegan(CCSet *pTouches, CCEvent *pEvent)
{
//    int index = 0;
//    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
//    {
//        index++;
//        CCTouch* pTouch = (CCTouch*)(*iterTouch);
//        CCPoint location = pTouch->getLocation();
//        CCPoint perLocation = pTouch->getPreviousLocation();
//        float value = location.x - perLocation.x;
//        posx1 += value;
//        posx2 += (value / 2);
//        ///
////        printf("\n location.x:%f, location.y:%f",location.x,location.y);
//        _layerColor->setPosition(ccp(posx1, visibleSize.height/2));
//    }
}

void HelloWorld::ccTouchesMoved(CCSet *pTouches, CCEvent *pEvent)
{
    int index = 0;
    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
    {
        index++;
        CCTouch* pTouch = (CCTouch*)(*iterTouch);
        CCPoint location = pTouch->getLocation();
        CCPoint perLocation = pTouch->getPreviousLocation();
        float value = location.x - perLocation.x;
        posx1 += value;
        posx2 += (value / 2);
		if( NULL != m_pNode1 )
		{
			m_pNode1->setPosition(ccp(posx1,0));
		}
		if( NULL != m_pNode2 )
		{
			m_pNode2->setPosition(ccp(posx2,0));
		}
    }
}

void HelloWorld::ccTouchesEnded(CCSet *pTouches, CCEvent *pEvent)
{
//    int index = 0;
//    for (CCSetIterator iterTouch = pTouches->begin(); iterTouch != pTouches->end(); iterTouch++,index++)
//    {
//        index++;
//        CCTouch* pTouch = (CCTouch*)(*iterTouch);
//        CCPoint location = pTouch->getLocation();
//        CCPoint perLocation = pTouch->getPreviousLocation();
//        float value = location.x - perLocation.x;
//        posx1 += value;
//        posx2 += (value / 2);
//        ///
////        printf("\n location.x:%f, location.y:%f",location.x,location.y);
//        _layerColor->setPosition(ccp(posx1, visibleSize.height/2));
//    }
}

void HelloWorld::ccTouchesCancelled(CCSet *pTouches, CCEvent *pEvent)
{

}

<|endoftext|>


<commit_before>/**
 *  @copyright Copyright 2016 The J-PET Framework Authors. All rights reserved.
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may find a copy of the License in the LICENCE file.
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 *  @file TaskD.cpp
 */

#include "./TaskD.h"
#include "JPetWriter/JPetWriter.h"
#include <iostream>

//ClassImp(TaskD);

TaskD::TaskD(const char * name, const char * description):
  JPetTask(name, description)
{
}

void TaskD::init(const JPetTaskInterface::Options& opts)
{
  getStatistics().createHistogram( new TH1F("No. signals in TSlot", "Signals multiplicity per TSlot", 10,
					    -0.5, 9.5) );
  getStatistics().createHistogram( new TH1F("Scins multiplicity", "scintillators multiplicity", 65, 5.5,
					    70.5));

  // create a histogram of time difference for every scintillator in the setup
  // we loop over all scintillator objects in the parameters bank downloaded
  // from database for the run number given by user
  for(auto & scin : getParamBank().getScintillators()){
    TString name = Form("dt for scin %d", scin.first);
    getStatistics().createHistogram( new TH1F(name, name, 100, -10000., 10000.) );
  }

  // initialize some scalar counters
  getStatistics().createCounter("No. initial signals");
  getStatistics().createCounter("No. found hits");
}

void TaskD::exec()
{
  // A dummy analysis example:
  JPetPhysSignal currSignal = (JPetPhysSignal&) (*getEvent());

  // increment the counter of signals
  getStatistics().getCounter("No. initial signals")++;

  if (fSignals.empty()) {
    fSignals.push_back(currSignal);
  } else {
    if (fSignals[0].getTimeWindowIndex() == currSignal.getTimeWindowIndex()) {
      fSignals.push_back(currSignal);
    } else {
      getStatistics().getHisto1D("No. signals in TSlot").Fill(fSignals.size());
      saveHits(createHits(fSignals)); //create LORs from previously saved signals
      fSignals.clear();
      fSignals.push_back(currSignal);
    }
  }
}

std::vector<JPetHit> TaskD::createHits(std::vector<JPetPhysSignal>& signals)
{
  std::vector<JPetHit> hits;
  for (auto i = signals.begin(); i != signals.end(); ++i) {
    for (auto j = i; ++j != signals.end(); /**/) {
      if (i->getPM().getScin() == j->getPM().getScin()) {
        // found 2 signals from the same scintillator
        JPetHit hit;
        if (i->getPM().getSide() == JPetPM::SideA
            && j->getPM().getSide() == JPetPM::SideB) {
          hit.setSignalA(*i);
          hit.setSignalB(*j);
        } else if (j->getPM().getSide() == JPetPM::SideA
                   && i->getPM().getSide() == JPetPM::SideB) {
          hit.setSignalA(*j);
          hit.setSignalB(*i);
        } else {
          WARNING("TWO hits on the same scintillator side we ignore it");
          // if two hits on the same side, ignore
          continue;
        }

        hit.setScintillator(i->getPM().getScin());

        getStatistics().getHisto1D("Scins multiplicity").Fill((*i).getPM().getScin().getID());

        double dt = hit.getSignalA().getTime() - hit.getSignalB().getTime();
        hit.setTimeDiff(dt);

        double t = 0.5
                   * (hit.getSignalA().getTime() + hit.getSignalB().getTime());
        hit.setTime(t);

	// fill the appropriate dt histogram for this scintillator
	getStatistics().getHisto1D(
				   Form("dt for scin %d", hit.getScintillator().getID())
				    ).Fill(hit.getTimeDiff());

        hits.push_back(hit);
	// increment the counter of found hits
	getStatistics().getCounter("No. found hits")++;
      }
    }
  }
  return hits;
}

void TaskD::terminate()
{
  std::cout <<"terminate() Taskd()" <<std::endl;
  std::cout <<"number of signals:"<<fSignals.size() <<std::endl;
  for(auto sig: fSignals) {
    std::cout<<"some signal info:"<<sig.getPM().getScin().getID()<<std::endl;
    std::cout<<"unique id:"<<sig.GetUniqueID()<<std::endl;
  }
  saveHits(createHits(fSignals)); //if there is something left
  INFO( Form("From %d initial signals %d hits were paired.",
	     static_cast<int>(getStatistics().getCounter("No. initial signals")),
	     static_cast<int>(getStatistics().getCounter("No. found hits")) )
	);
}

void TaskD::saveHits(std::vector<JPetHit> hits)
{
  assert(fWriter);
  for (auto hit : hits) {
    fWriter->write(hit);
  }
}
<commit_msg>Temporarily remove last saveHits call<commit_after>/**
 *  @copyright Copyright 2016 The J-PET Framework Authors. All rights reserved.
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may find a copy of the License in the LICENCE file.
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 *  @file TaskD.cpp
 */

#include "./TaskD.h"
#include "JPetWriter/JPetWriter.h"
#include <iostream>

//ClassImp(TaskD);

TaskD::TaskD(const char * name, const char * description):
  JPetTask(name, description)
{
}

void TaskD::init(const JPetTaskInterface::Options& opts)
{
  getStatistics().createHistogram( new TH1F("No. signals in TSlot", "Signals multiplicity per TSlot", 10,
					    -0.5, 9.5) );
  getStatistics().createHistogram( new TH1F("Scins multiplicity", "scintillators multiplicity", 65, 5.5,
					    70.5));

  // create a histogram of time difference for every scintillator in the setup
  // we loop over all scintillator objects in the parameters bank downloaded
  // from database for the run number given by user
  for(auto & scin : getParamBank().getScintillators()){
    TString name = Form("dt for scin %d", scin.first);
    getStatistics().createHistogram( new TH1F(name, name, 100, -10000., 10000.) );
  }

  // initialize some scalar counters
  getStatistics().createCounter("No. initial signals");
  getStatistics().createCounter("No. found hits");
}

void TaskD::exec()
{
  // A dummy analysis example:
  JPetPhysSignal currSignal = (JPetPhysSignal&) (*getEvent());

  // increment the counter of signals
  getStatistics().getCounter("No. initial signals")++;

  if (fSignals.empty()) {
    fSignals.push_back(currSignal);
  } else {
    if (fSignals[0].getTimeWindowIndex() == currSignal.getTimeWindowIndex()) {
      fSignals.push_back(currSignal);
    } else {
      getStatistics().getHisto1D("No. signals in TSlot").Fill(fSignals.size());
      saveHits(createHits(fSignals)); //create LORs from previously saved signals
      fSignals.clear();
      fSignals.push_back(currSignal);
    }
  }
}

std::vector<JPetHit> TaskD::createHits(std::vector<JPetPhysSignal>& signals)
{
  std::vector<JPetHit> hits;
  for (auto i = signals.begin(); i != signals.end(); ++i) {
    for (auto j = i; ++j != signals.end(); /**/) {
      if (i->getPM().getScin() == j->getPM().getScin()) {
        // found 2 signals from the same scintillator
        JPetHit hit;
        if (i->getPM().getSide() == JPetPM::SideA
            && j->getPM().getSide() == JPetPM::SideB) {
          hit.setSignalA(*i);
          hit.setSignalB(*j);
        } else if (j->getPM().getSide() == JPetPM::SideA
                   && i->getPM().getSide() == JPetPM::SideB) {
          hit.setSignalA(*j);
          hit.setSignalB(*i);
        } else {
          WARNING("TWO hits on the same scintillator side we ignore it");
          // if two hits on the same side, ignore
          continue;
        }

        hit.setScintillator(i->getPM().getScin());

        getStatistics().getHisto1D("Scins multiplicity").Fill((*i).getPM().getScin().getID());

        double dt = hit.getSignalA().getTime() - hit.getSignalB().getTime();
        hit.setTimeDiff(dt);

        double t = 0.5
                   * (hit.getSignalA().getTime() + hit.getSignalB().getTime());
        hit.setTime(t);

	// fill the appropriate dt histogram for this scintillator
	getStatistics().getHisto1D(
				   Form("dt for scin %d", hit.getScintillator().getID())
				    ).Fill(hit.getTimeDiff());

        hits.push_back(hit);
	// increment the counter of found hits
	getStatistics().getCounter("No. found hits")++;
      }
    }
  }
  return hits;
}

void TaskD::terminate()
{
  std::cout <<"terminate() Taskd()" <<std::endl;
  std::cout <<"number of signals:"<<fSignals.size() <<std::endl;
  for(auto sig: fSignals) {
    std::cout<<"some signal info:"<<sig.getPM().getScin().getID()<<std::endl;
    std::cout<<"unique id:"<<sig.GetUniqueID()<<std::endl;
  }
  //  saveHits(createHits(fSignals)); //if there is something left
  INFO( Form("From %d initial signals %d hits were paired.",
	     static_cast<int>(getStatistics().getCounter("No. initial signals")),
	     static_cast<int>(getStatistics().getCounter("No. found hits")) )
	);
}

void TaskD::saveHits(std::vector<JPetHit> hits)
{
  assert(fWriter);
  for (auto hit : hits) {
    fWriter->write(hit);
  }
}
<|endoftext|>