| /** \file filterbuilder.cpp . |
| ----------------------------------------------------------------------------- |
| |
| |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you 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. |
| |
| ----------------------------------------------------------------------------- |
| |
| Description: |
| |
| ----------------------------------------------------------------------------- |
| |
| |
| -------------------------------------------------------------------------- */ |
| |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Include dependencies */ |
| /* ----------------------------------------------------------------------- */ |
| #include "uima/fsfilterbuilder.hpp" |
| #include "uima/fsindex.hpp" |
| #include "uima/internal_fspromoter.hpp" |
| /* ----------------------------------------------------------------------- */ |
| /* Constants */ |
| /* ----------------------------------------------------------------------- */ |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Forward declarations */ |
| /* ----------------------------------------------------------------------- */ |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Types / Classes */ |
| /* ----------------------------------------------------------------------- */ |
| |
| /* |
| Here are straightforward implementations of FSFilters. |
| Nothing exciting. |
| */ |
| using namespace std; |
| namespace uima { |
| namespace internal { |
| |
| ////////////////////////////////////////////////////// |
| class NOTFilter : public FSFilter { |
| private: |
| FSFilter * iv_pFilter; |
| public: |
| NOTFilter(FSFilter* pFilter) |
| : iv_pFilter(pFilter) { |
| assert(EXISTS(iv_pFilter)); |
| } |
| |
| bool isFiltered(FeatureStructure const & fs) const { |
| assert(EXISTS(iv_pFilter)); |
| return ! iv_pFilter->isFiltered(fs); |
| } |
| |
| void deInit() { |
| assert(EXISTS(iv_pFilter)); |
| iv_pFilter->deInit(); |
| delete iv_pFilter; |
| } |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class BoolBinaryOperationFilter : public FSFilter { |
| protected: |
| FSFilter * iv_pFilter1; |
| FSFilter * iv_pFilter2; |
| |
| BoolBinaryOperationFilter(FSFilter * pFilter1, FSFilter * pFilter2) |
| : iv_pFilter1(pFilter1), |
| iv_pFilter2(pFilter2) { |
| assert(EXISTS(iv_pFilter1)); |
| assert(EXISTS(iv_pFilter2)); |
| } |
| public: |
| void deInit() { |
| assert(EXISTS(iv_pFilter1)); |
| iv_pFilter1->deInit(); |
| delete iv_pFilter1; |
| assert(EXISTS(iv_pFilter2)); |
| iv_pFilter2->deInit(); |
| delete iv_pFilter2; |
| } |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class ANDFilter : public BoolBinaryOperationFilter { |
| public: |
| ANDFilter(FSFilter * pFilter1, FSFilter * pFilter2) |
| : BoolBinaryOperationFilter(pFilter1, pFilter2) {} |
| |
| bool isFiltered(FeatureStructure const & fs) const { |
| assert(EXISTS(iv_pFilter1)); |
| assert(EXISTS(iv_pFilter2)); |
| // ensure that filter 2 is not used when filter 1 already returns false |
| bool bResult1 = iv_pFilter1->isFiltered(fs); |
| if (!bResult1) { |
| return false; |
| } |
| // cerr << __FILE__ << ", " << __LINE__ << ": value of filter1: " << iv_pFilter1->isFiltered(fs) << ", value of filter2: " << iv_pFilter2->isFiltered(fs) << endl; |
| return iv_pFilter2->isFiltered(fs); |
| } |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class ORFilter : public BoolBinaryOperationFilter { |
| public: |
| ORFilter(FSFilter * pFilter1, FSFilter * pFilter2) |
| : BoolBinaryOperationFilter(pFilter1, pFilter2) {} |
| |
| bool isFiltered(FeatureStructure const & fs) const { |
| assert(EXISTS(iv_pFilter1)); |
| assert(EXISTS(iv_pFilter2)); |
| bool bResult1 = iv_pFilter1->isFiltered(fs); |
| if (bResult1) { |
| return true; |
| } |
| return iv_pFilter2->isFiltered(fs); |
| } |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class TypeFilter : public FSFilter { |
| private: |
| Type iv_type; |
| bool iv_bUseSusumption; |
| public: |
| TypeFilter(Type const & crType, bool bUseSubsumption) |
| : iv_type(crType), |
| iv_bUseSusumption(bUseSubsumption) {} |
| |
| bool isFiltered(FeatureStructure const & fs) const { |
| if (iv_bUseSusumption) { |
| return iv_type.subsumes(fs.getType()); |
| } |
| return iv_type == fs.getType(); |
| } |
| |
| }; |
| |
| ////////////////////////////////////////////////////// |
| FeatureStructure getPath(FeatureStructure const & crFS, vector<Feature> const & crFeatures, size_t uiStep) { |
| FeatureStructure result = crFS; |
| size_t i; |
| for (i=0; i<uiStep; ++i) { |
| result = result.getFSValue(crFeatures[i]); |
| } |
| return result; |
| } |
| |
| ////////////////////////////////////////////////////// |
| template<class T> |
| class BuiltinFeatureValueFilter : public FSFilter { |
| private: |
| vector<Feature> iv_features; |
| FSFilterBuilder::EnComparisonOperator iv_enOp; |
| T iv_val; |
| |
| bool compare(FSFilterBuilder::EnComparisonOperator enOp, T val1, T val2) const { |
| switch (enOp) { |
| case FSFilterBuilder::EQUALS: |
| return val1 == val2; |
| case FSFilterBuilder::GREATER: |
| return val1 > val2; |
| case FSFilterBuilder::LESS: |
| return val1 < val2; |
| }; |
| assert(false); |
| return false; |
| } |
| |
| protected: |
| virtual T getFeature(FeatureStructure const &, Feature const &) const = 0; |
| public: |
| BuiltinFeatureValueFilter(vector<Feature> const & crFeatures, FSFilterBuilder::EnComparisonOperator enOp, T val) |
| : iv_features(crFeatures), |
| iv_enOp(enOp), |
| iv_val(val) {} |
| |
| bool isFiltered(FeatureStructure const & crFS) const { |
| size_t uiLast = iv_features.size() - 1; |
| FeatureStructure fs = getPath(crFS, iv_features, uiLast); |
| T val = getFeature(fs, iv_features[uiLast]); |
| return compare(iv_enOp, val, iv_val); |
| } |
| |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class IntFeatureFilter : public BuiltinFeatureValueFilter<int> { |
| protected: |
| int getFeature(FeatureStructure const & crFS, Feature const & crFeat) const { |
| return crFS.getIntValue(crFeat); |
| } |
| public: |
| IntFeatureFilter(vector<Feature> const & crFeatures, FSFilterBuilder::EnComparisonOperator enOp, int val) |
| : BuiltinFeatureValueFilter<int>(crFeatures, enOp, val) {} |
| }; |
| |
| ////////////////////////////////////////////////////// |
| class FloatFeatureFilter : public BuiltinFeatureValueFilter<float> { |
| protected: |
| float getFeature(FeatureStructure const & crFS, Feature const & crFeat) const { |
| return crFS.getFloatValue(crFeat); |
| } |
| public: |
| FloatFeatureFilter(vector<Feature> const & crFeatures, FSFilterBuilder::EnComparisonOperator enOp, float val) |
| : BuiltinFeatureValueFilter<float>(crFeatures, enOp, val) {} |
| }; |
| ///////////////////////////////////////////////////////////// |
| class UnicodeStringRefFeatureFilter : public BuiltinFeatureValueFilter<UnicodeStringRef> { |
| protected: |
| UnicodeStringRef getFeature(FeatureStructure const & crFS, Feature const & crFeat) const { |
| return crFS.getStringValue(crFeat); |
| } |
| public: |
| UnicodeStringRefFeatureFilter(vector<Feature> const & crFeaturePath, UnicodeStringRef const & crUStr) |
| : BuiltinFeatureValueFilter<UnicodeStringRef>(crFeaturePath, FSFilterBuilder::EQUALS, crUStr ) {} |
| }; |
| |
| class StringFeatureFilter : public FSFilter { |
| private: |
| UnicodeStringRefFeatureFilter * iv_pUnicodeStringRefFeatureFilter; |
| icu::UnicodeString iv_string; |
| public: |
| StringFeatureFilter(vector<Feature> const & crFeaturePath, UChar const * cpUTFBuffer, size_t uiLength) |
| : iv_pUnicodeStringRefFeatureFilter(NULL) { |
| iv_string = icu::UnicodeString( cpUTFBuffer, uiLength ); |
| UnicodeStringRef up(iv_string.getBuffer(), iv_string.length() ); |
| iv_pUnicodeStringRefFeatureFilter = new UnicodeStringRefFeatureFilter(crFeaturePath, up); |
| assert( EXISTS( iv_pUnicodeStringRefFeatureFilter ) ); |
| } |
| |
| ~StringFeatureFilter() { |
| if (iv_pUnicodeStringRefFeatureFilter != NULL) { |
| delete iv_pUnicodeStringRefFeatureFilter; |
| iv_pUnicodeStringRefFeatureFilter = NULL; |
| } |
| } |
| |
| virtual bool isFiltered(FeatureStructure const &crFS) const { |
| assert( EXISTS( iv_pUnicodeStringRefFeatureFilter ) ); |
| return iv_pUnicodeStringRefFeatureFilter->isFiltered(crFS); |
| } |
| |
| virtual void deInit() { |
| assert( EXISTS( iv_pUnicodeStringRefFeatureFilter ) ); |
| iv_pUnicodeStringRefFeatureFilter->deInit(); |
| } |
| |
| }; |
| |
| |
| ////////////////////////////////////////////////////// |
| class MatchFilter : public FSFilter { |
| private: |
| vector<Feature> iv_features; |
| FSFilter * iv_pFilter; |
| public: |
| MatchFilter(vector<Feature> const & crFeaturePath, FSFilter * pFilter) |
| : iv_features(crFeaturePath), |
| iv_pFilter(pFilter) { |
| assert(EXISTS(iv_pFilter)); |
| } |
| |
| bool isFiltered(FeatureStructure const & crFS) const { |
| FeatureStructure fs = getPath(crFS, iv_features, iv_features.size()); |
| assert(EXISTS(iv_pFilter)); |
| return iv_pFilter->isFiltered(fs); |
| } |
| |
| void deInit() { |
| assert(EXISTS(iv_pFilter)); |
| iv_pFilter->deInit(); |
| delete iv_pFilter; |
| } |
| }; |
| |
| |
| } |
| } // namespace uima |
| |
| /* ----------------------------------------------------------------------- */ |
| /* Implementation */ |
| /* ----------------------------------------------------------------------- */ |
| |
| namespace uima { |
| |
| FSFilterBuilder::FSFilterBuilder() {} |
| |
| FSFilterBuilder::~FSFilterBuilder() {} |
| |
| FSFilter * FSFilterBuilder::createNOTFilter(FSFilter * pFilter) const { |
| return new internal::NOTFilter(pFilter); |
| } |
| |
| FSFilter * FSFilterBuilder::createANDFilter(FSFilter * pFilter1, FSFilter * pFilter2) const { |
| return new internal::ANDFilter(pFilter1, pFilter2); |
| } |
| |
| FSFilter * FSFilterBuilder::createORFilter(FSFilter * pFilter1, FSFilter * pFilter2) const { |
| return new internal::ORFilter(pFilter1, pFilter2); |
| } |
| |
| FSFilter * FSFilterBuilder::createTypeFilter(Type const & crType, bool bUseSubsumption) const { |
| return new internal::TypeFilter(crType, bUseSubsumption); |
| } |
| |
| FSFilter * FSFilterBuilder::createIntFeatureFilter(vector<Feature> const & crFeatures, EnComparisonOperator enOp, int iVal) const { |
| return new internal::IntFeatureFilter(crFeatures, enOp, iVal); |
| } |
| |
| FSFilter * FSFilterBuilder::createFloatFeatureFilter(vector<Feature> const & crFeatures, EnComparisonOperator enOp, float fVal) const { |
| return new internal::FloatFeatureFilter(crFeatures, enOp, fVal); |
| } |
| |
| FSFilter * FSFilterBuilder::createMatchFilter(vector<Feature> const & crFeaturePath, FSFilter * pFilter) const { |
| return new internal::MatchFilter(crFeaturePath, pFilter); |
| } |
| |
| FSFilter * FSFilterBuilder::createStringFeatureFilter(vector<Feature> const & crFeaturePath, UChar const * cpUTFBuffer, size_t uiLength) const { |
| return new internal::StringFeatureFilter(crFeaturePath, cpUTFBuffer, uiLength); |
| } |
| |
| |
| } // namespace uima |
| |
| /* ----------------------------------------------------------------------- */ |
| |
| |
| |