JavaScript własne narzędzia

Są pewne funkcje w Javie, których niestety nie ma domyślnie w JS. Większość z nich jest tak oczywista, że nie ma potrzeby ich tłumaczyć. Pomocne mogą być np: wyszukiwanie fragmentu w treści, podmienianie treści za pomocą tablicy, filtrowanie tablicy, sortowanie tablicy, iteracja tablicy lub mapy.

 

/**
 * @param {String} toMatch
 * @returns {boolean}
 */
String.prototype.matchStr = function(toMatch) {
    if(!toMatch) return false;
    var match = this.toLowerCase().match(new RegExp(toMatch.toLowerCase(), 'g'));
    return match!==null && match.length>0;
};

 

/**
 * @returns {boolean}
 */
String.prototype.isEmpty = function() {
    return this.trim() === '';
};

 

/**
 * @param {String} replace
 * @param {String} with_this
 * @returns {String}
 */
String.prototype.replaceAll = function(replace, with_this) {
    return this.replace(new RegExp(replace, 'g'), with_this);
};

 

/**
 * @param {Array} find
 * @param {Array} replace
 * @returns {String}
 */
String.prototype.replaceArray = function(find, replace) {
    var replaceString = this;
    for (var i = 0; i < find.length; i++) {
        replaceString = replaceString.replaceAll(find[i], replace[i]);
    }
    return replaceString;
};

 

Sortowanie z uwzględnieniem polskich znaków

String.prototype.comparePl_search = ['ą','ć','ę','ł','ń','ó','ś','ź','ż'];
String.prototype.comparePl_replace = ['azz','czz','ezz','lzz','nzz','ozz','szz','zzz','zzzz'];

/**
 * Sortowanie z uwzględnieniem polskich znaków
 * @param {String} compareTo
 * @returns {Number}
 */
String.prototype.comparePl = function(compareTo) {
    var str = this.toLowerCase().replaceArray(this.comparePl_search, this.comparePl_replace);
    compareTo = compareTo.toLowerCase().replaceArray(this.comparePl_search, this.comparePl_replace);
    return str > compareTo ? 1 : (str < compareTo ? -1 : 0);
};

 

W Java 8 pojawiła się klasa Stream dzięki, której wraz z wyrażeniami Lambda programowanie w Javie stało się jeszcze przyjemniejsze. Poniżej bez Lambda coś namiastkę Stream. Funkcja filter pozwoli na odsianie niepotrzebnych obiektów no i niezastąpiona funkcja forEach.

PRZYKŁAD

var arr = [1,2,3,4,5];

arr.filter(function(val, i) {
    return val>1 && val<5;
}).forEach(function(val, i) {
    console.log(val);
});

ŹRÓDŁO

Array.prototype.stream = function() {
    
    var _arr = this;
    var filterFunc = null;
    
    /**
     * @param {function} func Funcka z atrybutami WARTOŚĆ, KOLEJOŚĆ, TABLICA np.: function(p, i, arr) { }, która powinna zwrócić TAK lub NIE
     * @returns {Array}
     */
    this.filter = function(func) {
        filterFunc = func;
        return _arr;
    };
    
    /**
     * @param {dunction} func Funcka z atrybutami WARTOŚĆ, KOLEJOŚĆ, TABLICA np.: function(p, i, arr) { }, która zwracajnąc NIE przerywa iterację
     * @returns {Array}
     */
    this.forEach = function(func) {
        for(var i=0; i<_arr.length; i++) { 
            if(filterFunc && !filterFunc(_arr[i], i, _arr)) continue;
            if(func) {
                var ret = func(_arr[i], i, _arr);
                if(typeof ret !== 'undefined' && typeof ret === 'boolean' && !ret) break;
            }
        }
        return _arr;
    };
    
    return _arr;
};

 

Podobnie jak wyżej z tą różnicą, że operacje wykonywane są na mapie (innymi słowy na obiekcie). Funkcja filter pozwoli na odsianie niepotrzebnych obiektów, funkcja sort posortuje tablicę wg własnego komparatora no i niezastąpiona funkcja forEach.

PRZYKŁAD

var mapa = {
     'poz1': {
         'nazwa': 'nazwa pozycji 1',
         'wartosc': 'inna wartość'
     },
     // (...)
     'pozN': {
         'nazwa': 'nazwa pozycji n',
         'wartosc': 'inna wartość'
     }
};

new Map(mapa).filter(function(key, val, i) {
     return i>0;
}).sort(function(a, b) {
     return a['nazwa'].comparePl(b['nazwa']);
}).forEach(function(key, val, i) {
     console.log(key + ' → ' + val['nazwa']);
});

ŹRÓDŁO

/**
 * Przetwarzanie danych KLUCZ → WARTOŚĆ
 * @param {object} _map Dane KLUCZ → WARTOŚĆ
 * @returns {Map}
 */
function Map(_map) {
    
    var _this = this;
    
    var filterFunc = null;

    /**
     * @param {function} func Funcka z atrybutami KLUCZ, WARTOŚĆ, KOLEJOŚĆ, MAPA np.: function(k, p, i, map) { }, która powinna zwrócić TAK lub NIE
     * @returns {Map}
     */
    this.filter = function(func) {
        filterFunc = func;
        return _this;
    };

    /**
     * @param {dunction} func Funcka z atrybutami KLUCZ, WARTOŚĆ, KOLEJOŚĆ, MAPA np.: function(k, p, i, map) { }, która zwracajnąc NIE przerywa iterację
     * @returns {Map}
     */
    this.forEach = function(func) {
        var i = 0;
        for(var key in _map) { 
            if(filterFunc && !filterFunc(key, _map[key], i, _map)) continue;
            if(func) {
                var ret = func(key, _map[key], i, _map);
                if(typeof ret !== 'undefined' && typeof ret === 'boolean' && !ret) break;
            }
            i ++;
        }
        return _this;
    };

    /**
     * @param {type} comparator
     * @returns {Map}
     */
    this.sort = function(comparator) {
        var arr = [];
        _this.forEach(function(k, p) {
            p['__key'] = k;
            arr.push(p);
        });
        arr.sort(comparator);
        _map = {};
        arr.stream().forEach(function(p) {
            _map[p['__key']] = p;
            p['__key'] = null;
        });
        return _this;
    };

    this.toObject = function() { return _map; };
}