| SpMat_meat.hpp | | SpMat_meat.hpp | |
| | | | |
| skipping to change at line 2963 | | skipping to change at line 2963 | |
| | | | |
| mem_resize( uword(density * double(in_rows) * double(in_cols) + 0.5) ); | | mem_resize( uword(density * double(in_rows) * double(in_cols) + 0.5) ); | |
| | | | |
| if(n_nonzero == 0) | | if(n_nonzero == 0) | |
| { | | { | |
| return *this; | | return *this; | |
| } | | } | |
| | | | |
| eop_aux_randu<eT>::fill( access::rwp(values), n_nonzero ); | | eop_aux_randu<eT>::fill( access::rwp(values), n_nonzero ); | |
| | | | |
|
| uvec indices = linspace<uvec>( 0, in_rows*in_cols-1, n_nonzero ); | | uvec indices = linspace<uvec>( 0u, in_rows*in_cols-1, n_nonzero ); | |
| | | | |
| // perturb the indices | | // perturb the indices | |
| for(uword i=1; i < n_nonzero-1; ++i) | | for(uword i=1; i < n_nonzero-1; ++i) | |
| { | | { | |
| const uword index_left = indices[i-1]; | | const uword index_left = indices[i-1]; | |
| const uword index_right = indices[i+1]; | | const uword index_right = indices[i+1]; | |
| | | | |
| const uword center = (index_left + index_right) / 2; | | const uword center = (index_left + index_right) / 2; | |
| | | | |
| const uword delta1 = center - index_left - 1; | | const uword delta1 = center - index_left - 1; | |
| | | | |
| skipping to change at line 3038 | | skipping to change at line 3038 | |
| | | | |
| mem_resize( uword(density * double(in_rows) * double(in_cols) + 0.5) ); | | mem_resize( uword(density * double(in_rows) * double(in_cols) + 0.5) ); | |
| | | | |
| if(n_nonzero == 0) | | if(n_nonzero == 0) | |
| { | | { | |
| return *this; | | return *this; | |
| } | | } | |
| | | | |
| eop_aux_randn<eT>::fill( access::rwp(values), n_nonzero ); | | eop_aux_randn<eT>::fill( access::rwp(values), n_nonzero ); | |
| | | | |
|
| uvec indices = linspace<uvec>( 0, in_rows*in_cols-1, n_nonzero ); | | uvec indices = linspace<uvec>( 0u, in_rows*in_cols-1, n_nonzero ); | |
| | | | |
| // perturb the indices | | // perturb the indices | |
| for(uword i=1; i < n_nonzero-1; ++i) | | for(uword i=1; i < n_nonzero-1; ++i) | |
| { | | { | |
| const uword index_left = indices[i-1]; | | const uword index_left = indices[i-1]; | |
| const uword index_right = indices[i+1]; | | const uword index_right = indices[i+1]; | |
| | | | |
| const uword center = (index_left + index_right) / 2; | | const uword center = (index_left + index_right) / 2; | |
| | | | |
| const uword delta1 = center - index_left - 1; | | const uword delta1 = center - index_left - 1; | |
| | | | |
End of changes. 2 change blocks. |
| 2 lines changed or deleted | | 2 lines changed or added | |
|
| SpValProxy_bones.hpp | | SpValProxy_bones.hpp | |
| | | | |
| skipping to change at line 48 | | skipping to change at line 48 | |
| | | | |
| //! First, the ones that could modify a value. | | //! First, the ones that could modify a value. | |
| arma_inline SpValProxy& operator=(const eT rhs); | | arma_inline SpValProxy& operator=(const eT rhs); | |
| arma_inline SpValProxy& operator+=(const eT rhs); | | arma_inline SpValProxy& operator+=(const eT rhs); | |
| arma_inline SpValProxy& operator-=(const eT rhs); | | arma_inline SpValProxy& operator-=(const eT rhs); | |
| arma_inline SpValProxy& operator*=(const eT rhs); | | arma_inline SpValProxy& operator*=(const eT rhs); | |
| arma_inline SpValProxy& operator/=(const eT rhs); | | arma_inline SpValProxy& operator/=(const eT rhs); | |
| | | | |
| arma_inline SpValProxy& operator++(); | | arma_inline SpValProxy& operator++(); | |
| arma_inline SpValProxy& operator--(); | | arma_inline SpValProxy& operator--(); | |
|
| arma_inline eT operator++(const int unused); | | arma_inline eT operator++(const int); | |
| arma_inline eT operator--(const int unused); | | arma_inline eT operator--(const int); | |
| | | | |
| //! This will work for any other operations that do not modify a value. | | //! This will work for any other operations that do not modify a value. | |
| arma_inline operator eT() const; | | arma_inline operator eT() const; | |
| | | | |
| private: | | private: | |
| | | | |
| // Deletes the element if it is zero. Does not check if val_ptr == NULL! | | // Deletes the element if it is zero. Does not check if val_ptr == NULL! | |
| arma_inline arma_hot void check_zero(); | | arma_inline arma_hot void check_zero(); | |
| | | | |
| uword row; | | uword row; | |
| | | | |
End of changes. 1 change blocks. |
| 2 lines changed or deleted | | 2 lines changed or added | |
|
| arma_version.hpp | | arma_version.hpp | |
| | | | |
| skipping to change at line 13 | | skipping to change at line 13 | |
| // | | // | |
| // This Source Code Form is subject to the terms of the Mozilla Public | | // This Source Code Form is subject to the terms of the Mozilla Public | |
| // License, v. 2.0. If a copy of the MPL was not distributed with this | | // License, v. 2.0. If a copy of the MPL was not distributed with this | |
| // file, You can obtain one at http://mozilla.org/MPL/2.0/. | | // file, You can obtain one at http://mozilla.org/MPL/2.0/. | |
| | | | |
| //! \addtogroup arma_version | | //! \addtogroup arma_version | |
| //! @{ | | //! @{ | |
| | | | |
| #define ARMA_VERSION_MAJOR 3 | | #define ARMA_VERSION_MAJOR 3 | |
| #define ARMA_VERSION_MINOR 900 | | #define ARMA_VERSION_MINOR 900 | |
|
| #define ARMA_VERSION_PATCH 3 | | #define ARMA_VERSION_PATCH 4 | |
| #define ARMA_VERSION_NAME "Bavarian Sunflower" | | #define ARMA_VERSION_NAME "Bavarian Sunflower" | |
| | | | |
| struct arma_version | | struct arma_version | |
| { | | { | |
| static const unsigned int major = ARMA_VERSION_MAJOR; | | static const unsigned int major = ARMA_VERSION_MAJOR; | |
| static const unsigned int minor = ARMA_VERSION_MINOR; | | static const unsigned int minor = ARMA_VERSION_MINOR; | |
| static const unsigned int patch = ARMA_VERSION_PATCH; | | static const unsigned int patch = ARMA_VERSION_PATCH; | |
| | | | |
| static | | static | |
| inline | | inline | |
| | | | |
End of changes. 1 change blocks. |
| 1 lines changed or deleted | | 1 lines changed or added | |
|
| compiler_setup.hpp | | compiler_setup.hpp | |
| | | | |
| skipping to change at line 77 | | skipping to change at line 77 | |
| #error "*** Need a newer compiler ***" | | #error "*** Need a newer compiler ***" | |
| #endif | | #endif | |
| | | | |
| #define ARMA_GOOD_COMPILER | | #define ARMA_GOOD_COMPILER | |
| #undef ARMA_HAVE_STD_TR1 | | #undef ARMA_HAVE_STD_TR1 | |
| | | | |
| #if (__INTEL_COMPILER <= 1110) | | #if (__INTEL_COMPILER <= 1110) | |
| #undef ARMA_HAVE_STD_ISFINITE | | #undef ARMA_HAVE_STD_ISFINITE | |
| #endif | | #endif | |
| | | | |
|
| #undef arma_aligned | | // #undef arma_aligned | |
| #undef arma_align_mem | | // #define arma_aligned __attribute__((aligned(16))) | |
| | | | |
|
| #define arma_aligned __attribute__((aligned(16))); | | #if defined(_MSC_VER) | |
| #define arma_align_mem __attribute__((aligned(16))); | | #undef arma_align_mem | |
| | | #define arma_align_mem __declspec(align(16)) | |
| | | #else | |
| | | #undef arma_align_mem | |
| | | #define arma_align_mem __attribute__((aligned(16))) | |
| | | #endif | |
| | | | |
| #define ARMA_HAVE_ALIGNED_ATTRIBUTE | | #define ARMA_HAVE_ALIGNED_ATTRIBUTE | |
| #define ARMA_HAVE_ICC_ASSUME_ALIGNED | | #define ARMA_HAVE_ICC_ASSUME_ALIGNED | |
| | | | |
| #elif defined(__GNUG__) | | #elif defined(__GNUG__) | |
| | | | |
| #if (__GNUC__ < 4) | | #if (__GNUC__ < 4) | |
| #error "*** Need a newer compiler ***" | | #error "*** Need a newer compiler ***" | |
| #endif | | #endif | |
| | | | |
| | | | |
| skipping to change at line 181 | | skipping to change at line 186 | |
| #undef ARMA_HAVE_STD_ISFINITE | | #undef ARMA_HAVE_STD_ISFINITE | |
| #undef ARMA_HAVE_STD_SNPRINTF | | #undef ARMA_HAVE_STD_SNPRINTF | |
| #undef ARMA_HAVE_LOG1P | | #undef ARMA_HAVE_LOG1P | |
| #undef ARMA_HAVE_STD_ISINF | | #undef ARMA_HAVE_STD_ISINF | |
| #undef ARMA_HAVE_STD_ISNAN | | #undef ARMA_HAVE_STD_ISNAN | |
| #undef ARMA_HAVE_STD_TR1 | | #undef ARMA_HAVE_STD_TR1 | |
| | | | |
| // #undef arma_inline | | // #undef arma_inline | |
| // #define arma_inline inline __forceinline | | // #define arma_inline inline __forceinline | |
| | | | |
|
| // // disable warnings for "__forceinline can't be inlined" | | #pragma warning(push) | |
| // #pragma warning(disable: 4714) | | | |
| | | | |
| // disable warnings for "conditional expression is constant" | | | |
| #pragma warning(disable: 4127) | | | |
| | | | |
|
| // TODO: use #pragma warning(push) and #pragma warning(pop) | | #pragma warning(disable: 4127) // conditional expression is constant | |
| | | #pragma warning(disable: 4510) // default constructor could not be gener | |
| | | ated | |
| | | #pragma warning(disable: 4511) // copy constructor can't be generated | |
| | | #pragma warning(disable: 4512) // assignment operator can't be generated | |
| | | #pragma warning(disable: 4513) // destructor can't be generated | |
| | | #pragma warning(disable: 4514) // unreferenced inline function has been | |
| | | removed | |
| | | #pragma warning(disable: 4522) // multiple assignment operators specifie | |
| | | d | |
| | | #pragma warning(disable: 4623) // default constructor can't be generated | |
| | | #pragma warning(disable: 4624) // destructor can't be generated | |
| | | #pragma warning(disable: 4625) // copy constructor can't be generated | |
| | | #pragma warning(disable: 4626) // assignment operator can't be generated | |
| | | #pragma warning(disable: 4710) // function not inlined | |
| | | #pragma warning(disable: 4711) // call was inlined | |
| | | #pragma warning(disable: 4714) // __forceinline can't be inlined | |
| | | | |
| #if (_MANAGED == 1) || (_M_CEE == 1) | | #if (_MANAGED == 1) || (_M_CEE == 1) | |
| | | | |
| // don't do any alignment when compiling in "managed code" mode | | // don't do any alignment when compiling in "managed code" mode | |
| | | | |
| #else | | #else | |
| // #undef arma_aligned | | // #undef arma_aligned | |
|
| // #define arma_aligned __declspec(align(16)) | | // #define arma_aligned __declspec(align(16)) | |
| | | | |
| #undef arma_align_mem | | #undef arma_align_mem | |
| #define arma_align_mem __declspec(align(16)) | | #define arma_align_mem __declspec(align(16)) | |
| | | | |
| #define ARMA_HAVE_ALIGNED_ATTRIBUTE | | #define ARMA_HAVE_ALIGNED_ATTRIBUTE | |
| | | | |
| // disable warnings: "structure was padded due to __declspec(align(16))
" | | // disable warnings: "structure was padded due to __declspec(align(16))
" | |
| #pragma warning(disable: 4324) | | #pragma warning(disable: 4324) | |
| | | | |
| #endif | | #endif | |
| | | | |
End of changes. 5 change blocks. |
| 11 lines changed or deleted | | 28 lines changed or added | |
|
| eGlueCube_meat.hpp | | eGlueCube_meat.hpp | |
| | | | |
| skipping to change at line 81 | | skipping to change at line 81 | |
| return P1.get_n_elem(); | | return P1.get_n_elem(); | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlueCube<T1,T2,eglue_type>::operator[] (const uword i) const | | eGlueCube<T1,T2,eglue_type>::operator[] (const uword i) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
[i] + P2[i]; } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
[i] + P2[i]; } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
[i] - P2[i]; } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
[i] - P2[i]; } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
[i] / P2[i]; } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
[i] / P2[i]; } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
[i] * P2[i]; } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
[i] * P2[i]; } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlueCube<T1,T2,eglue_type>::at(const uword row, const uword col, const uwo
rd slice) const | | eGlueCube<T1,T2,eglue_type>::at(const uword row, const uword col, const uwo
rd slice) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at(row,col,slice) + P2.at(row,col,slice); } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at(row,col,slice) + P2.at(row,col,slice); } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at(row,col,slice) - P2.at(row,col,slice); } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at(row,col,slice) - P2.at(row,col,slice); } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at(row,col,slice) / P2.at(row,col,slice); } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at(row,col,slice) / P2.at(row,col,slice); } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at(row,col,slice) * P2.at(row,col,slice); } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at(row,col,slice) * P2.at(row,col,slice); } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlueCube<T1,T2,eglue_type>::at_alt(const uword i) const | | eGlueCube<T1,T2,eglue_type>::at_alt(const uword i) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at_alt(i) + P2.at_alt(i); } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at_alt(i) + P2.at_alt(i); } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at_alt(i) - P2.at_alt(i); } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at_alt(i) - P2.at_alt(i); } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at_alt(i) / P2.at_alt(i); } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at_alt(i) / P2.at_alt(i); } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at_alt(i) * P2.at_alt(i); } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at_alt(i) * P2.at_alt(i); } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| //! @} | | //! @} | |
| | | | |
End of changes. 6 change blocks. |
| 0 lines changed or deleted | | 9 lines changed or added | |
|
| eGlue_meat.hpp | | eGlue_meat.hpp | |
| | | | |
| skipping to change at line 66 | | skipping to change at line 66 | |
| return Proxy<T1>::is_fixed ? P1.get_n_elem() : ( Proxy<T2>::is_fixed ? P2
.get_n_elem() : P1.get_n_elem() ) ; | | return Proxy<T1>::is_fixed ? P1.get_n_elem() : ( Proxy<T2>::is_fixed ? P2
.get_n_elem() : P1.get_n_elem() ) ; | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlue<T1,T2,eglue_type>::operator[] (const uword ii) const | | eGlue<T1,T2,eglue_type>::operator[] (const uword ii) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
[ii] + P2[ii]; } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
[ii] + P2[ii]; } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
[ii] - P2[ii]; } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
[ii] - P2[ii]; } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
[ii] / P2[ii]; } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
[ii] / P2[ii]; } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
[ii] * P2[ii]; } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
[ii] * P2[ii]; } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlue<T1,T2,eglue_type>::at(const uword row, const uword col) const | | eGlue<T1,T2,eglue_type>::at(const uword row, const uword col) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at(row,col) + P2.at(row,col); } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at(row,col) + P2.at(row,col); } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at(row,col) - P2.at(row,col); } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at(row,col) - P2.at(row,col); } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at(row,col) / P2.at(row,col); } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at(row,col) / P2.at(row,col); } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at(row,col) * P2.at(row,col); } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at(row,col) * P2.at(row,col); } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| template<typename T1, typename T2, typename eglue_type> | | template<typename T1, typename T2, typename eglue_type> | |
| arma_inline | | arma_inline | |
| typename T1::elem_type | | typename T1::elem_type | |
| eGlue<T1,T2,eglue_type>::at_alt(const uword ii) const | | eGlue<T1,T2,eglue_type>::at_alt(const uword ii) const | |
| { | | { | |
| // the optimiser will keep only one return statement | | // the optimiser will keep only one return statement | |
| | | | |
|
| | | typedef typename T1::elem_type eT; | |
| | | | |
| if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at_alt(ii) + P2.at_alt(ii); } | | if(is_same_type<eglue_type, eglue_plus >::value == true) { return P1
.at_alt(ii) + P2.at_alt(ii); } | |
| else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at_alt(ii) - P2.at_alt(ii); } | | else if(is_same_type<eglue_type, eglue_minus>::value == true) { return P1
.at_alt(ii) - P2.at_alt(ii); } | |
| else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at_alt(ii) / P2.at_alt(ii); } | | else if(is_same_type<eglue_type, eglue_div >::value == true) { return P1
.at_alt(ii) / P2.at_alt(ii); } | |
| else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at_alt(ii) * P2.at_alt(ii); } | | else if(is_same_type<eglue_type, eglue_schur>::value == true) { return P1
.at_alt(ii) * P2.at_alt(ii); } | |
|
| | | else return eT(0); | |
| } | | } | |
| | | | |
| //! @} | | //! @} | |
| | | | |
End of changes. 6 change blocks. |
| 0 lines changed or deleted | | 9 lines changed or added | |
|
| op_median_meat.hpp | | op_median_meat.hpp | |
| | | | |
| skipping to change at line 381 | | skipping to change at line 381 | |
| void | | void | |
| op_median::direct_cx_median_index | | op_median::direct_cx_median_index | |
| ( | | ( | |
| uword& out_index1, | | uword& out_index1, | |
| uword& out_index2, | | uword& out_index2, | |
| std::vector< arma_cx_median_packet<T> >& X | | std::vector< arma_cx_median_packet<T> >& X | |
| ) | | ) | |
| { | | { | |
| arma_extra_debug_sigprint(); | | arma_extra_debug_sigprint(); | |
| | | | |
|
| const uword n_elem = X.size(); | | const uword n_elem = uword(X.size()); | |
| const uword half = n_elem/2; | | const uword half = n_elem/2; | |
| | | | |
| std::nth_element(X.begin(), X.begin() + half, X.end()); | | std::nth_element(X.begin(), X.begin() + half, X.end()); | |
| | | | |
| if((n_elem % 2) == 0) | | if((n_elem % 2) == 0) | |
| { | | { | |
| out_index1 = std::max_element(X.begin(), X.begin() + half)->index; | | out_index1 = std::max_element(X.begin(), X.begin() + half)->index; | |
| out_index2 = X[half].index; | | out_index2 = X[half].index; | |
| } | | } | |
| else | | else | |
| | | | |
End of changes. 1 change blocks. |
| 1 lines changed or deleted | | 1 lines changed or added | |
|