Skip to content

Commit

Permalink
fix: sampling operation and fix interfaces for some other operations,…
Browse files Browse the repository at this point in the history
… improve prospector (#61)

* Ignore empty lines in dimacs models

* Improve code for skipping empty lines

* DimacsWriter: Allow None paths when written

* Fix some prospector and hint typing

* Fix interfaces and some errors
  • Loading branch information
jmhorcas authored May 10, 2024
1 parent ab3ca22 commit 5dccbb6
Show file tree
Hide file tree
Showing 18 changed files with 285 additions and 188 deletions.
2 changes: 1 addition & 1 deletion flamapy/metamodels/pysat_metamodel/models/pysat_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ def __init__(self) -> None:
self.variables: dict[str, int] = {} # feature's name -> id
self.features: dict[int, str] = {} # id -> feature's name
self.original_model: VariabilityModel

def add_clause(self, clause: list[int]) -> None:
self._cnf.append(clause)

Expand Down
1 change: 1 addition & 0 deletions flamapy/metamodels/pysat_metamodel/models/txtcnf_model.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from typing import Optional
from enum import Enum, auto

from flamapy.core.exceptions import FlamaException


Expand Down
2 changes: 2 additions & 0 deletions flamapy/metamodels/pysat_metamodel/operations/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
from .pysat_false_optional_features import PySATFalseOptionalFeatures
from .pysat_metrics import PySATMetrics


__all__ = [
'PySATValid',
'PySATValidConfiguration',
Expand All @@ -21,4 +22,5 @@
'PySATCoreFeatures',
'PySATDeadFeatures',
'PySATFalseOptionalFeatures',
'PySATMetrics',
]
19 changes: 9 additions & 10 deletions flamapy/metamodels/pysat_metamodel/operations/pysat_commonality.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,32 +5,31 @@


class PySATCommonality(Commonality):

def __init__(self) -> None:
self.commonality: float = 0
self.result: float = 0
self.configuration = Configuration({})

def set_configuration(self, configuration: Configuration) -> None:
self.configuration = configuration

def get_commonality(self) -> float:
return self.commonality
return self.get_result()

def get_result(self) -> float:
return self.get_commonality()
return self.result

def execute(self, model: VariabilityModel) -> 'PySATCommonality':
glucose3products = PySATProducts()
glucose3products.execute(model)

products = glucose3products.get_result()
pysat_products_op = PySATProducts()
pysat_products_op.execute(model)
products = pysat_products_op.get_result()

feature = list(self.configuration.elements.keys())[0]

count = 0
for product in products:
count = count + \
1 if feature.name in product else count
count = count + 1 if feature in product else count

self.commonality = count / len(products)
self.result = count / len(products)

return self
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,13 @@
class PySATCoreFeatures(CoreFeatures):

def __init__(self) -> None:
self.core_features: list[list[Any]] = []
self.core_features: list[Any] = []
self.solver = Solver(name='glucose3')

def get_core_features(self) -> list[list[Any]]:
def get_core_features(self) -> list[Any]:
return self.core_features

def get_result(self) -> list[list[Any]]:
def get_result(self) -> list[Any]:
return self.get_core_features()

def execute(self, model: VariabilityModel) -> 'PySATCoreFeatures':
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,13 @@
class PySATDeadFeatures(DeadFeatures):

def __init__(self) -> None:
self.dead_features: list[list[Any]] = []
self.dead_features: list[Any] = []
self.solver = Solver(name='glucose3')

def get_dead_features(self) -> list[list[Any]]:
def get_dead_features(self) -> list[Any]:
return self.dead_features

def get_result(self) -> list[list[Any]]:
def get_result(self) -> list[Any]:
return self.get_dead_features()

def execute(self, model: VariabilityModel) -> 'PySATDeadFeatures':
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from flamapy.core.models import VariabilityModel
from flamapy.core.exceptions import FlamaException


LOGGER = logging.getLogger('PySATFalseOptionalFeatures')


Expand All @@ -19,24 +20,24 @@ def __init__(self) -> None:
self.solver = Solver(name='glucose3')

def execute(self, model: VariabilityModel) -> 'PySATFalseOptionalFeatures':
model = cast(PySATModel, model)

self.result = self._get_false_optional_features(model)
sat_model = cast(PySATModel, model)
self.result = self._get_false_optional_features(sat_model)
return self

def get_false_optional_features(self) -> list[list[Any]]:
def get_false_optional_features(self) -> list[Any]:
return self.get_result()

def get_result(self) -> list[Any]:
return self.result

def _get_false_optional_features(self, sat_model: PySATModel) -> list[Any]:
try:
feature_model=cast(FeatureModel,sat_model.original_model)
feature_model = cast(FeatureModel, sat_model.original_model)
except FlamaException:
LOGGER.exception("The transformation didn't attach the source model, which is required for this operation." )

real_optional_features = [f for f in feature_model.get_features()
LOGGER.exception("The transformation didn't attach the source model, "
"which is required for this operation.")

real_optional_features = [f.name for f in feature_model.get_features()
if not f.is_root() and not f.is_mandatory()]

result = []
Expand All @@ -45,10 +46,12 @@ def _get_false_optional_features(self, sat_model: PySATModel) -> list[Any]:

for feature in real_optional_features:
variable = sat_model.variables.get(feature.name)
parent_variable = sat_model.variables.get(feature.get_parent().name)
assert variable is not None
satisfiable = self.solver.solve(assumptions=[parent_variable, -variable])
if not satisfiable:
result.append(feature.name)
parent_feature = feature.get_parent()
if parent_feature is not None:
parent_variable = sat_model.variables.get(parent_feature.name)
assert variable is not None
satisfiable = self.solver.solve(assumptions=[parent_variable, -variable])
if not satisfiable:
result.append(feature.name)
self.solver.delete()
return result
15 changes: 9 additions & 6 deletions flamapy/metamodels/pysat_metamodel/operations/pysat_filter.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,16 +30,19 @@ def execute(self, model: VariabilityModel) -> 'PySATFilter':
for clause in model.get_all_clauses(): # AC es conjunto de conjuntos
self.solver.add_clause(clause) # añadimos la constraint

assumptions = [
model.variables.get(feat[0].name) if feat[1]
else -model.variables.get(feat[0].name)
for feat in self.configuration.elements.items()
]
assumptions = []
for feat in self.configuration.elements.items():
variable = model.variables.get(feat[0])
if variable is not None:
if feat[1]:
assumptions.append(variable)
else:
assumptions.append(-variable)

for solution in self.solver.enum_models(assumptions=assumptions):
product = []
for variable in solution:
if variable > 0:
if variable is not None and variable > 0:
product.append(model.features.get(variable))
self.filter_products.append(product)
self.solver.delete()
Expand Down
Loading

0 comments on commit 5dccbb6

Please sign in to comment.