Changeset 26310


Ignore:
Timestamp:
06/09/21 13:46:44 (4 years ago)
Author:
jdquinn
Message:

CHG: Incorporated other functions from Dan; added more functionality to ones/zeros; pending minor cleanup

Location:
issm/trunk-jpl/src/m
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • issm/trunk-jpl/src/m/classes/hydrologyshreve.m

    r26301 r26310  
    3737
    3838                        %Early return
    39                         if ~ismember('HydrologyShreveAnalysis',analyses) |  (strcmp(solution,'TransientSolution') & md.transient.ishydrology==0), return; end
     39                        if ~ismember('HydrologyShreveAnalysis',analyses) | (strcmp(solution,'TransientSolution') & md.transient.ishydrology==0), return; end
    4040
    4141                        md = checkfield(md,'fieldname','hydrology.spcwatercolumn','Inf',1,'timeseries',1);
  • issm/trunk-jpl/src/m/miscellaneous/MatlabFuncs.js

    r26308 r26310  
    1010- We cannot implement the following MATLAB built-in functions by name as their
    1111names are reserved keywords in JavaScript,
    12         class
     12    class
    1313
    1414TODO:
    1515- Implement,
    16         sort
    17         unique
     16    sort
     17    unique
    1818
    1919Sources:
     
    3636 */
    3737function any(A) {//{{{
    38         for (let i = 0; i < A.length; ++i) {
    39                 if (A[i] !== 0) {
    40                         return true;
    41                 }
    42         }
    43         return false;
     38    for (let i = 0; i < A.length; ++i) {
     39        if (A[i] !== 0) {
     40            return true;
     41        }
     42    }
     43    return false;
    4444} //}}}
    4545
     
    6161 */
    6262function diff(X) {//{{{
    63         let diffs = [];
    64         for (let i = 0; i < X.length - 1; ++i) {
    65                 diffs[i] = X[i + 1] - X[i];
    66         }
    67         return diffs;
     63    let diffs = [];
     64    for (let i = 0; i < (X.length - 1); ++i) {
     65        diffs[i] = X[i + 1] - X[i];
     66    }
     67    return diffs;
    6868} //}}}
    6969
     
    8282 */
    8383function disp(X) {//{{{
    84         console.log(X);
     84    console.log(X);
    8585} //}}}
    8686
     
    100100 */
    101101function error(msg) {//{{{
    102         throw new Error(msg);
     102    throw new Error(msg);
    103103} //}}}
    104104
     
    117117 */
    118118function find(X, n, direction) {//{{{
    119         if (typeof(X[0]) == 'number') {
    120                 let indices = [];
    121                 for (let i = 0; i < X.length; ++i) {
    122                         if (X[i] != 0) {
    123                                 indices.push(i);
    124                         }
    125                 }
    126                 return indices;
    127         } else { //TODO: If 2d array, assume return rows & cols - try to find a way to not always return rows/cols
    128                 let rowindices = [];
    129                 let colindices = [];
    130                 for (let i = 0; i < X.length; ++i) {
    131                         for (let j = 0; j < X[i].length; ++j) {
    132                                 if (X[i][j] != 0) {
    133                                         rowindices.push(i);
    134                                         colindices.push(j);
    135                                 }
    136                         }
    137                 }
    138                 return [rowindices, colindices];
    139         }
     119    if (typeof(X[0]) == 'number') {
     120        let indices = [];
     121        for (let i = 0; i < X.length; ++i) {
     122            if (X[i] != 0) {
     123                indices.push(i);
     124            }
     125        }
     126        return indices;
     127    } else { //TODO: If 2d array, assume return rows & cols - try to find a way to not always return rows/cols
     128        let rowindices = [];
     129        let colindices = [];
     130        for (let i = 0; i < X.length; ++i) {
     131            for (let j = 0; j < X[i].length; ++j) {
     132                if (X[i][j] != 0) {
     133                    rowindices.push(i);
     134                    colindices.push(j);
     135                }
     136            }
     137        }
     138        return [rowindices, colindices];
     139    }
    140140} //}}}
    141141
     
    152152 */
    153153function isempty(A) {//{{{
    154         //NOTE: Expanded for clarity/debugging. Can reduce later.
    155         if (A === undefined) {
    156                 return 1; //TODO: Fix this: for now, treat undefined as empty
    157         } else {
    158                 return A.length == 0;
    159         }
     154    //NOTE: Expanded for clarity/debugging. Can reduce later.
     155    if (A === undefined) {
     156        return 1; //TODO: Fix this: for now, treat undefined as empty
     157    } else {
     158        return A.length == 0;
     159    }
    160160} //}}}
    161161
     
    175175 */
    176176function ismember(A, B) {//{{{
    177         let b = B;
    178         if (typeof(B) == 'number' || typeof(B) == 'string') {
    179                 b = [B];
    180         }
    181         let indices = zeros(A.length);
    182         for (let i = 0; i < A.length; ++i) {
    183                 for (let j = 0; j < b.length; ++j) {
    184                         if (A[i] === b[j]) {
    185                                 indices[i] = 1;
    186                         }
    187                 }
    188         }
    189         if (indices.length) {
    190                 return indices;
    191         } else {
    192                 return 0;
    193         }
     177    let b = B;
     178    if (typeof(B) == 'number' || typeof(B) == 'string') {
     179        b = [B];
     180    }
     181    let indices = zeros(A.length);
     182    for (let i = 0; i < A.length; ++i) {
     183        for (let j = 0; j < b.length; ++j) {
     184            if (A[i] === b[j]) {
     185                indices[i] = 1;
     186            }
     187        }
     188    }
     189    if (indices.length) {
     190        return indices;
     191    } else {
     192        return 0;
     193    }
    194194} //}}}
    195195
     
    211211 */
    212212function isnan(A) {//{{{
    213         if (A.constructor !== Array) {
    214                 error('isnan: argument must be an array')
    215         }
    216         is_nan = [];
    217         for (let i = 0; i < A.length; ++i) {
    218                 if (Number.isNaN(A[i])) {
    219                         is_nan.push(1);
    220                 } else {
    221                         is_nan.push(0);
    222                 }
    223         }
    224         return is_nan;
     213    if (A.constructor !== Array) {
     214        error('isnan: argument must be an array')
     215    }
     216    is_nan = [];
     217    for (let i = 0; i < A.length; ++i) {
     218        if (Number.isNaN(A[i])) {
     219            is_nan.push(1);
     220        } else {
     221            is_nan.push(0);
     222        }
     223    }
     224    return is_nan;
    225225} //}}}/*
    226226
     
    240240 */
    241241function length(A) {//{{{
    242         return A.length;
     242    return A.length;
    243243} //}}}/*
    244244
     
    259259 */
    260260function max(A) {//{{{
    261         return Math.max.apply(null, A);
     261    return Math.max.apply(null, A);
    262262} //}}}/*
    263263
     
    278278 */
    279279function min(A) {//{{{
    280         return Math.min.apply(null, A);
     280    return Math.min.apply(null, A);
    281281} //}}}/*
    282282
    283283/**
    284  * FUNCTION sum - Sum of elements of an array
    285  *
    286  * Replicates behavior of MATLAB's 'sum' function
    287  *
    288  * Usage:
    289  *     S = sum(A)
    290  *
    291  * Sources:
    292  * - https://www.mathworks.com/help/matlab/ref/sum.html
    293  *
    294  * TODO:
    295  * - Implement support for multidimensional arrays
    296  * - Implement 'nanflag' parameter
    297  */
    298 function sum(A) {//{{{
    299         return ArraySum(A);
    300 } //}}}/*
    301 
    302 /**
    303284 * FUNCTION ones - Create array of all ones
    304285 *
    305  * Replicates behavior of MATLAB's 'ones' function
     286 * Replicates behavior of MATLAB's 'zeros' function
     287 *
     288 * Usage:
     289 *     X = ones
     290 *     X = ones(n)
     291 *     X = ones(sz1,...,szN)
     292 *     X = ones(sz)
    306293 *
    307294 * Sources:
    308295 * - https://www.mathworks.com/help/matlab/ref/ones.html
    309296 *
    310  * NOTE:
    311  * - Current behavior is to initialize and return a 1D array of length 'size'
    312  *
    313  * TODO:
    314  * - Implement actual behavior of MATLAB's 'ones' function
    315  */
    316 function ones(size) {//{{{
    317         return NewArrayFill(size, 1);
     297 * TODO:
     298 * - Create lower-level function to handle both ones and zeros functions as
     299 * they are essentially the same
     300 * - Implement functionality for more than 2 dimensions
     301 */
     302function ones() {//{{{
     303    nargs = arguments.length;
     304    if (nargs == 0) {
     305        return 1;
     306    } else if (nargs == 1) {
     307        let arg = arguments[0];
     308        if (typeof(arg) == 'number') {
     309            return NewArrayFill(arg, 1);
     310        } else if (arg.constructor == Array) {
     311            return ones(...arg); // spread array of sizes
     312        } else {
     313            error('ones: functionality for greater than 2 dimensions is not currently implemented')
     314        }
     315    } else if (nargs == 2) {
     316        return NewArrayFill2D(arguments[0], arguments[1], 1);
     317    } else {
     318        error('ones: functionality for greater than 2 dimensions is not currently implemented')
     319    }
    318320} //}}}
    319321
     
    337339 */
    338340function size(A, dim) {//{{{
    339         let nargs = arguments.length;
    340         if (nargs == 0) {
    341                 error('size: at least one argument is required');
    342         } else if (nargs == 1) {
    343                 if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
    344                         return [1, 1];
    345                 } else if (A.constructor != Array) {
    346                         error('size: A argument must be a number or an Array');
    347                 }
    348                 if (typeof(A) == 'undefined' || isNaN(A)) {
    349                         return [0];
    350                 } else if (A.length && A[0].constructor == Array) {
    351                         return [A.length, A[0].length];
    352                 } else {
    353                         return [A.length];
    354                 }
    355         } else if (nargs == 2) {
    356                 if (typeof(dim) != 'number' || dim < 0 || dim > 1) {
    357                         error('size: dim argument must be a number between 0 and 1, inclusive');
    358                 }
    359                 if (dim == 0) {
    360                         if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
    361                                 return 1;
    362                         } else {
    363                                 return A.length;
    364                         }
    365                 } else {
    366                         if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
    367                                 return 1;
    368                         } else if (typeof(A) == 'undefined' || isNaN(A)) {
    369                                 return 0;
    370                         } else if (A[0].constructor != Array) {
    371                                 error('size: A[0] is not an Array');
    372                         }
    373                         return A[0].length;
    374                 }
    375         } else {
    376                 error('size: functionality for more than 2 arguments is not currently implemented');
    377         }
     341    let nargs = arguments.length;
     342    if (nargs == 0) {
     343        error('size: at least one argument is required');
     344    } else if (nargs == 1) {
     345        if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
     346            return [1, 1];
     347        } else if (A.constructor != Array) {
     348            error('size: A argument must be a number or an Array');
     349        }
     350        if (typeof(A) == 'undefined' || isNaN(A)) {
     351            return [0];
     352        } else if (A.length && A[0].constructor == Array) {
     353            return [A.length, A[0].length];
     354        } else {
     355            return [A.length];
     356        }
     357    } else if (nargs == 2) {
     358        if (typeof(dim) != 'number' || dim < 0 || dim > 1) {
     359            error('size: dim argument must be a number between 0 and 1, inclusive');
     360        }
     361        if (dim == 0) {
     362            if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
     363                return 1;
     364            } else {
     365                return A.length;
     366            }
     367        } else {
     368            if (typeof(A) == 'number') { // scalar numbers are of size [1, 1]
     369                return 1;
     370            } else if (typeof(A) == 'undefined' || isNaN(A)) {
     371                return 0;
     372            } else if (A[0].constructor != Array) {
     373                error('size: A[0] is not an Array');
     374            }
     375            return A[0].length;
     376        }
     377    } else {
     378        error('size: functionality for more than 2 arguments is not currently implemented');
     379    }
    378380} //}}}
    379381
     
    387389 */
    388390function strcmpi(s1, s2) {//{{{
    389         return s1.toLowerCase() == s2.toLowerCase();
    390 } //}}}
    391 
    392 /**
    393  * FUNCTION sum - Sum of array elements
     391    return s1.toLowerCase() == s2.toLowerCase();
     392} //}}}
     393
     394/**
     395 * FUNCTION sum - Sum of elements of an array
    394396 *
    395397 * Replicates behavior of MATLAB's 'sum' function
     398 *
     399 * Usage:
     400 *     S = sum(A)
     401 *
     402 * Sources:
     403 * - https://www.mathworks.com/help/matlab/ref/sum.html
     404 *
     405 * TODO:
     406 * - Implement support for multidimensional arrays
     407 * - Implement 'nanflag' parameter
     408 */
     409function sum(A) {//{{{
     410    return ArraySum(A);
     411} //}}}
     412
     413/**
     414 * FUNCTION zeros - Create array of all zeros
     415 *
     416 * Replicates behavior of MATLAB's 'zeros' function
    396417 *
    397  * Sum(A) returns the sum of the elements of A along the first array dimension
    398  * whose size does not equal 1.
    399  * - If A is a 1D array, then sum(A) returns the sum of the elements
    400  *
    401  * Usage:
    402  *     S = sum(A)
    403  *
    404  * Sources:
    405  * - https://www.mathworks.com/help/matlab/ref/sum.html
    406  *
    407  * NOTE:
    408  * - Not all functionality is implemented
    409  */
    410 function sum(A) {//{{{
    411         return A.reduce((x, y) => x + y);
    412 } //}}}
    413 
    414 /**
    415  * FUNCTION zeros - Create array of all zeros
    416  *
    417  * Replicates behavior of MATLAB's 'zeros' function
     418 * Usage:
     419 *     X = zeros
     420 *     X = zeros(n)
     421 *     X = zeros(sz1,...,szN)
     422 *     X = zeros(sz)
    418423 *
    419424 * Sources:
    420425 * - https://www.mathworks.com/help/matlab/ref/zeros.html
    421426 *
    422  * NOTE:
    423  * - Current behavior is to initialize and return a 1D array of length 'size'
    424  *
    425  * TODO:
    426  * - Implement actual behavior of MATLAB's 'ones' function
    427  */
    428 function zeros(size, size2) {//{{{
    429         if (size2 !== undefined) {
    430                 return NewArrayFill2D(size, size2, 0);
    431         } else {
    432                 return NewArrayFill(size, 0);
    433         }
    434 } //}}}
     427 * TODO:
     428 * - Create lower-level function to handle both ones and zeros functions as
     429 * they are essentially the same
     430 * - Implement functionality for more than 2 dimensions
     431 */
     432function zeros() {//{{{
     433    nargs = arguments.length;
     434    if (nargs == 0) {
     435        return 0;
     436    } else if (nargs == 1) {
     437        let arg = arguments[0];
     438        if (typeof(arg) == 'number') {
     439            return NewArrayFill(arg, 0);
     440        } else if (arg.constructor == Array) {
     441            return zeros(...arg); // spread array of sizes
     442        } else {
     443            error('zeros: functionality for greater than 2 dimensions is not currently implemented')
     444        }
     445    } else if (nargs == 2) {
     446        return NewArrayFill2D(arguments[0], arguments[1], 0);
     447    } else {
     448        error('zeros: functionality for greater than 2 dimensions is not currently implemented')
     449    }
     450} //}}}
     451
     452/**
     453 * FUNCTIONS sin, cos, tan, asin, acos, atan2 - trig functions that work with radians
     454 *
     455 * Replicates behavior of MATLAB's trig functions
     456 *
     457 * Sources:
     458 * - https://www.mathworks.com/help/matlab/trigonometry.html
     459 *
     460 */
     461function sin(X) {//{{{
     462    let result = NewArrayFill(size, X.length);
     463    for (let i = 0; i < X.length; ++i) {
     464        result[i] = Math.sin(X[i]);
     465    }
     466    return result;
     467} //}}}
     468
     469function cos(X) {//{{{
     470    let result = NewArrayFill(size, X.length);
     471    for (let i = 0; i < X.length; ++i) {
     472        result[i] = Math.cos(X[i]);
     473    }
     474    return result;
     475} //}}}
     476
     477function tan(X) {//{{{
     478    let result = NewArrayFill(size, X.length);
     479    for (let i = 0; i < X.length; ++i) {
     480        result[i] = Math.tan(X[i]);
     481    }
     482    return result;
     483} //}}}
     484
     485function asin(X) {//{{{
     486    let result = NewArrayFill(size, X.length);
     487    for (let i = 0; i < X.length; ++i) {
     488        result[i] = Math.asin(X[i]);
     489    }
     490    return result;
     491} //}}}
     492
     493function acos(X) {//{{{
     494    let result = NewArrayFill(size, X.length);
     495    for (let i = 0; i < X.length; ++i) {
     496        result[i] = Math.acos(X[i]);
     497    }
     498    return result;
     499} //}}}
     500
     501// TODO: Test that the arguments do not need to be reversed, as they are in MATLAB and Python
     502function atan2(X, Y) {//{{{
     503    let result = NewArrayFill(size, X.length);
     504    for (let i = 0; i < X.length; ++i) {
     505        result[i] = Math.atan2(X[i], Y[i]);
     506    }
     507    return result;
     508} //}}}
     509
     510/**
     511 * FUNCTIONS sind, cosd, tand, asind, acosd, atan2d - trig functions that work with degrees
     512 *
     513 * Replicates behavior of MATLAB's trig functions
     514 *
     515 * Sources:
     516 * - https://www.mathworks.com/help/matlab/trigonometry.html
     517 *
     518 */
     519function sind(X) {//{{{
     520    let result = NewArrayFill(size, X.length);
     521    for (let i = 0; i < X.length; ++i) {
     522        result[i] = Math.sin(X[i] * DEG2RAD);
     523    }
     524    return result;
     525} //}}}
     526
     527function cosd(X) {//{{{
     528    let result = NewArrayFill(size, X.length);
     529    for (let i = 0; i < X.length; ++i) {
     530        result[i] = Math.cos(X[i] * DEG2RAD);
     531    }
     532    return result;
     533} //}}}
     534
     535function tand(X) {//{{{
     536    let result = NewArrayFill(size, X.length);
     537    for (let i = 0; i < X.length; ++i) {
     538        result[i] = Math.tan(X[i] * DEG2RAD);
     539    }
     540    return result;
     541} //}}}
     542
     543function asind(X) {//{{{
     544    let result = NewArrayFill(size, X.length);
     545    for (let i = 0; i < X.length; ++i) {
     546        result[i] = RAD2DEG * Math.asin(X[i]);
     547    }
     548    return result;
     549} //}}}
     550
     551function acosd(X) {//{{{
     552    let result = NewArrayFill(size, X.length);
     553    for (let i = 0; i < X.length; ++i) {
     554        result[i] = RAD2DEG * Math.acos(X[i]);
     555    }
     556    return result;
     557} //}}}
     558
     559// TODO: Test that the arguments do not need to be reversed, as they are in MATLAB and Python
     560function atan2d(X, Y) {//{{{
     561    let result = NewArrayFill(size, X.length);
     562    for (let i = 0; i < X.length; ++i) {
     563        result[i] = RAD2DEG * Math.atan2(X[i], Y[i]);
     564    }
     565    return result;
     566} //}}}
Note: See TracChangeset for help on using the changeset viewer.