Mentions légales du service

Skip to content
Snippets Groups Projects
Commit 77cb4be0 authored by hhakim's avatar hhakim
Browse files

Rewrite in C++ left and right Faust functions (TransformHelper) and set them...

Rewrite in C++ left and right Faust functions (TransformHelper) and set them in pyfaust wrapper (add unit tests test_right/left), also add a __len__ override.
parent e297cee9
Branches
Tags
No related merge requests found
......@@ -711,6 +711,40 @@ class TestFaustPy(unittest.TestCase):
test_Fct[test_Fct==0] = 1
self.assertTrue(((((test_Fct-ref_Fct)/ref_Fct) < 0.01)).all())
def test_left(self):
print("Test Faust.left()")
for i in range(len(self.F)):
lFt = self.F.left(i)
if i == 0:
lFt = Faust([lFt])
lFr = Faust([self.F.factors(j) for j in range(i+1)])
self.assertEqual(len(lFr), len(lFt))
for fid in range(i+1):
a = lFt.factors(fid)
b = lFr.factors(fid)
if(not isinstance(a, np.ndarray)):
a = a.toarray()
if(not isinstance(b, np.ndarray)):
b = b.toarray()
np.allclose(a,b)
def test_right(self):
print("Test Faust.right()")
for i in range(len(self.F)):
rFt = self.F.right(i)
if i == len(self.F)-1:
rFt = Faust([rFt])
rFr = Faust([self.F.factors(j) for j in range(i, len(self.F))])
self.assertEqual(len(rFr), len(rFt))
for fid in range(len(rFr)):
a = rFt.factors(fid)
b = rFr.factors(fid)
if(not isinstance(a, np.ndarray)):
a = a.toarray()
if(not isinstance(b, np.ndarray)):
b = b.toarray()
np.allclose(a,b)
class TestFaustPyCplx(TestFaustPy):
def setUp(self):
......@@ -1302,6 +1336,8 @@ class TestFaustFactory(unittest.TestCase):
for i in range(pM.shape[0]):
self.assertAlmostEqual(norm(pM[i,:]), k)
if __name__ == "__main__":
if(len(sys.argv)> 1):
# argv[1] is for adding a directory in PYTHONPATH
......
......@@ -164,7 +164,16 @@ namespace Faust {
TransformHelper<FPP,Cpu>* optimize_storage(const bool time=true);
TransformHelper<FPP,Cpu>* optimize(const bool transp=false);
void optimize_multiply(const bool transp=false);
/**
\brief Returns the left hand side factors of this from index 0 to id included (as a new TransformHelper obj).
*/
TransformHelper<FPP,Cpu>* left(const faust_unsigned_int id, const bool copy=false) const;
/**
\brief Returns the right hand side factors of this from index id to the size()-1 (as a new TransformHelper obj).
*/
TransformHelper<FPP,Cpu>* right(const faust_unsigned_int id, const bool copy=false) const;
static TransformHelper<FPP,Cpu>* randFaust(RandFaustType t, unsigned int min_num_factors, unsigned int max_num_factors, unsigned int min_dim_size, unsigned int max_dim_size, float density=.1f, bool per_row=true);
static TransformHelper<FPP,Cpu>* hadamardFaust(unsigned int n, const bool norma=true);
......@@ -172,8 +181,9 @@ namespace Faust {
static TransformHelper<FPP,Cpu>* eyeFaust(unsigned int n, unsigned int m);
~TransformHelper();
unsigned long long get_fact_addr(const faust_unsigned_int id) const;
/* use carefully */
MatGeneric<FPP,Cpu>* get_gen_fact_nonconst(const faust_unsigned_int id) const;
private:
void copy_slices(TransformHelper<FPP, Cpu>* th, const bool transpose = false);
const MatGeneric<FPP,Cpu>* get_gen_fact(const faust_unsigned_int id) const;
......
......@@ -322,6 +322,26 @@ namespace Faust {
delete [] times;
}
template<typename FPP>
TransformHelper<FPP,Cpu>* TransformHelper<FPP,Cpu>::left(const faust_unsigned_int id, const bool copy /* default to false */) const
{
if(id >= this->size()) throw out_of_range("factor id is lower than zero or greater or equal to the size of Transform.");
std::vector<Faust::MatGeneric<FPP,Cpu>*> left_factors;
for(int i=0; i <= id; i++)
left_factors.push_back(const_cast<Faust::MatGeneric<FPP,Cpu>*>(get_gen_fact(i)));
return new TransformHelper<FPP,Cpu>(left_factors, FPP(1.0), false, copy, true);
}
template<typename FPP>
TransformHelper<FPP,Cpu>* TransformHelper<FPP,Cpu>::right(const faust_unsigned_int id, const bool copy /* default to false */) const
{
if(id >= this->size()) throw out_of_range("factor id is lower than zero or greater or equal to the size of Transform.");
std::vector<Faust::MatGeneric<FPP,Cpu>*> right_factors;
for(int i=id; i < size(); i++)
right_factors.push_back(const_cast<Faust::MatGeneric<FPP,Cpu>*>(get_gen_fact(i)));
return new TransformHelper<FPP,Cpu>(right_factors, FPP(1.0), false, copy, true);
}
template<typename FPP>
TransformHelper<FPP,Cpu>* TransformHelper<FPP,Cpu>::pruneout(const int nnz_tres, const int npasses, const bool only_forward)
{
......@@ -612,6 +632,12 @@ namespace Faust {
return this->transform->data[is_transposed?size()-id-1:id];
}
template<typename FPP>
MatGeneric<FPP,Cpu>* TransformHelper<FPP,Cpu>::get_gen_fact_nonconst(const faust_unsigned_int id) const
{
return this->transform->data[is_transposed?size()-id-1:id];
}
template<typename FPP>
unsigned long long TransformHelper<FPP,Cpu>::get_fact_addr(const faust_unsigned_int id) const
{
......
......@@ -1335,11 +1335,31 @@ class Faust:
>>> from pyfaust import rand
>>> F = rand(2, 100, .5)
>>> nf = F.numfactors()
>>> nf == len(F)
True
<b/> See also Faust.factors
<b/> See also Faust.factors, Faust.__len__
"""
return F.m_faust.get_nb_factors()
def __len__(F):
"""
Returns the number of factors of F.
Returns:
the number of factors.
Examples:
>>> from pyfaust import rand
>>> F = rand(2, 100, .5)
>>> nf = F.numfactors()
>>> nf == len(F)
True
<b/> See also Faust.factors, Faust.numfactors
"""
return F.numfactors()
def factors(F, indices):
"""
Returns the i-th factor of F.
......@@ -1401,7 +1421,10 @@ class Faust:
<b/> See also Faust.factors, Faust.left, Faust.numfactors
"""
i = F._check_factor_idx(i)
return F.factors(range(i,F.numfactors()))
rF = Faust(core_obj=F.m_faust.right(i))
if(len(rF) == 1):
return rF.factors(0)
return rF
def left(F, i):
"""
......@@ -1414,7 +1437,10 @@ class Faust:
<b/> See also Faust.factors, Faust.right
"""
i = F._check_factor_idx(i)
return F.factors(range(0, i+1))
lF = Faust(core_obj=F.m_faust.left(i))
if(len(lF) == 1):
return lF.factors(0)
return lF
def _check_factor_idx(F, i):
if(not isinstance(i, (float, int))):
......
......@@ -89,6 +89,8 @@ class FaustCoreCpp
void get_fact_dense(const unsigned int& i, FPP* elts,
unsigned int* num_rows, unsigned int* num_cols,
const bool transpose) const;
FaustCoreCpp<FPP>* left(const faust_unsigned_int) const;
FaustCoreCpp<FPP>* right(const faust_unsigned_int) const;
faust_unsigned_int get_fact_nnz(const faust_unsigned_int) const;
bool is_fact_sparse(const faust_unsigned_int id) const;
FaustCoreCpp<FPP>* slice(unsigned int, unsigned int, unsigned int, unsigned int);
......
......@@ -298,6 +298,22 @@ FaustCoreCpp<FPP>* FaustCoreCpp<FPP>::slice(unsigned int start_row_id, unsigned
return core;
}
template<typename FPP>
FaustCoreCpp<FPP>* FaustCoreCpp<FPP>::right(const faust_unsigned_int id) const
{
Faust::TransformHelper<FPP,Cpu>* th = this->transform->right(id);
FaustCoreCpp<FPP>* core = new FaustCoreCpp<FPP>(th);
return core;
}
template<typename FPP>
FaustCoreCpp<FPP>* FaustCoreCpp<FPP>::left(const faust_unsigned_int id) const
{
Faust::TransformHelper<FPP,Cpu>* th = this->transform->left(id);
FaustCoreCpp<FPP>* core = new FaustCoreCpp<FPP>(th);
return core;
}
template<typename FPP>
FaustCoreCpp<FPP>* FaustCoreCpp<FPP>::fancy_idx(unsigned long int* row_ids, unsigned long int
num_rows, unsigned long int* col_ids,
......
......@@ -79,6 +79,8 @@ cdef extern from "FaustCoreCpp.h" :
const bool transpose) const
unsigned int get_fact_nnz(const unsigned int i) const
bool is_fact_sparse(const unsigned int i) const
FaustCoreCpp[FPP]* right(const unsigned int) const
FaustCoreCpp[FPP]* left(const unsigned int) const
FaustCoreCpp[FPP]* get_slice(unsigned int, unsigned int, unsigned int,
unsigned int) const
FaustCoreCpp[FPP]* slice(unsigned int, unsigned int, unsigned int,
......
......@@ -701,6 +701,24 @@ cdef class FaustCore:
core._isReal = self._isReal
return core
def left(self, id):
core = FaustCore(core=True)
if(self._isReal):
core.core_faust_dbl = self.core_faust_dbl.left(id)
else:
core.core_faust_cplx = self.core_faust_cplx.left(id)
core._isReal = self._isReal
return core
def right(self, id):
core = FaustCore(core=True)
if(self._isReal):
core.core_faust_dbl = self.core_faust_dbl.right(id)
else:
core.core_faust_cplx = self.core_faust_cplx.right(id)
core._isReal = self._isReal
return core
def fancy_idx(self, indices):
cdef unsigned long int[:] row_indices_view
cdef unsigned long int[:] col_indices_view
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment