Enumerable은 Prototype 프레임워크의 초석이며 Enumerable은 단독으로 사용되지 않습니다. Prototype에서는 다른 개체가 Enumerable의 메서드를 혼합하므로 이러한 개체에 Array, Hash, ObjectRange를 적용할 수 있습니다. , DOM 및 AJAX와 관련된 일부 개체.
Enumerable은 열거, 즉 값의 컬렉션 역할을 하는 객체에 대한 유용한 메서드 세트를 제공합니다.
Enumerable은 우리가 모듈이라고 부르는 것입니다. : 독립적으로 사용하기 위한 것이 아니라 믹스인을 위한 일관된 메소드 세트: "적합"한 다른 객체에 통합
프로토타입에서 꽤 많은 객체가 이미 가장 눈에 띄는 경우에 혼합되어 있습니다. Array 및 Hash이지만 ObjectRange 및 다양한 DOM 또는 AJAX 관련 개체와 같이 덜 명확한 위치에서도 찾을 수 있습니다.
위 문장은 아마도 Enumerable이 Prototype의 초석이라는 의미일 것입니다. Enumerable은 단독으로 사용되지 않습니다. Prototype의 다른 개체는 Enumerable의 메서드를 혼합하므로 이러한 개체에는 Array, Hash, ObjectRange 및 일부 DOM, AJAX 관련 개체가 포함될 수 있습니다. .
저는 Enumerable이 C의 추상 클래스 개념과 동일하다는 것을 개인적으로 이해합니다. 다른 클래스는 이 클래스에서 상속할 수 있고 Enumerable에서 추상 메서드 "_each"를 구현하고 다른 메서드를 재정의할 수 있지만 Enumerable 자체는 인스턴스화할 수 없습니다. , 해당 하위 클래스만 인스턴스화할 수 있습니다.
Enumerable을 통해 자신만의 클래스를 작성하는 방법을 살펴보겠습니다.
코드 복사 코드는 다음과 같습니다.
var YourObject = Class.create ();
Object.extend(YourObject.prototype, Enumerable); Object.extend(YourObject.prototype, {
initialize: function() {
// 모든 생성자 인수 포함
/ / 구성 코드
},
_each: function(iterator) {
// 매 턴마다 반복자를 호출하는 반복 코드
},
// Enumerable 재정의를 포함한 다른 메서드
});
가장 중요한 것은 _each 메서드를 구현하는 것임을 알 수 있습니다. 초기화 메서드는 생성자와 동일합니다. 외부 매개변수가 필요하지 않으면 생략해도 됩니다. 아래에서는 난수 배열을 생성하는 클래스를 작성했습니다. 매우 간단하지만 불완전한 점이 많습니다.
코드를 복사하세요. 다음과 같습니다:
//RandomArray 클래스 생성
var RandomArray = Class.create();
//mixin Enumerable
Object.extend(RandomArray.prototype, Enumerable);
/ / _each 및 필수 메소드 구현
Object.extend(RandomArray.prototype, {
초기화: function(min,max,count) {
this.min=min;
this. max= max;
this._numbers=[];
this._createRandomArray()
},
_each: 함수(반복자) var index =this.count; 🎜> _createRandomArray:function(){
var index=0
while(index
function(number){
return this._numbers.indexOf(number)!=-1 ;
}
});
var obj = new RandomArray( 4,19,5)
//alert(obj.size()); .entries());
Enumerable의 소스 코드를 살펴보고 각 메서드를 자세히 알아보세요.
코드 복사
코드는 다음과 같습니다.
var $break = { };
var Enumerable = (function() {
//각 데이터 탐색
function Each(iterator, context) {
var index = 0;
try {
this._each(function(value) {
iterator.call(context, value, index );
}) catch(e) {
if (e != $break) throw e;
}
return this;
}
//데이터를 N개의 그룹으로 나누고 각 그룹에는 숫자가 있습니다. 마지막 그룹은 숫자보다 작을 수 있습니다.
function EachSlice(number, iterator, context) {
var index = -number, Slices = [], array = this.toArray()
if ( number < 1) 배열 반환;
while ((index = number) < array.length)
slices.push(array.slice(index, index number))
return Slices.collect( iterator, context );
}
//모든 데이터가 특정 조건을 만족하는지 테스트
function all(iterator, context) {
iterator = iterator || = true;
this.each(function(value, index) {
result = result && !!iterator.call(context, value, index);
if (!result) throw $break;
});
결과 반환
}
//특정 조건을 만족하는 데이터가 있는지 확인
function any(iterator, context) {
iterator = iterator || Prototype.K;
var result = false;
this.each(function(value, index) {
if (result = !!iterator.call(context, value, index) ))
throw $break;
});
return result;
}
//모든 데이터에 대해 모든 작업을 수행하고 결과 배열을 반환할 수 있습니다.
함수 수집(반복자, 컨텍스트) {
iterator = iterator || Prototype.K;
var results = [];
this.each(function(value, index) {
results.push(iterator.call(context, value) , index));
return results;
}
//특정 조건을 충족하는 첫 번째 데이터를 찾아 반환합니다. 이는 Alias 와 동일합니다. find 메소드
function detector(iterator, context) {
var result;
this.each(function(value, index) {
if (iterator.call(context, value, index) ) {
result = value;
throw $break;}
})
return result;
}
//특정 조건을 만족하는 모든 항목 찾기 데이터를 반환하고 결과를 반환합니다.
function findAll(iterator, context) {
var results = []
this.each(function(value, index) {
if (iterator.call(context , value, index))
results.push(value);
});
return results;
}
//필터 조건에 따라 모든 데이터를 필터링하고 필터 조건부 데이터 충족 및 결과 반환
//filter는 문자열 또는 정규 표현식입니다.
function grep(filter, iterator, context) {
iterator = iterator
var results = [];
if (Object.isString(filter))
filter = new RegExp(RegExp.escape(filter))
this.each(function(value, index ) {
if (filter.match(value))
results.push(iterator.call(context, value, index))
})
결과 반환; >
//특정 데이터가 포함되어 있는지 확인
function include(object) {
if (Object.isFunction(this.indexOf))
if (this.indexOf(object) != - 1 ) return true;
varfound = false;
this.each(function(value) {
if (value == object) {
found = true;
throw $ break;
}
});
returnfound;
}
//마지막 그룹의 요소 수가 숫자보다 작은 경우, fillWith 매개변수를 사용하세요. while(slice.length < number) Slice.push(fillWith);
return Slice;
})
}
//계속해서 누적을 달성합니다. 또는 누적 곱셈 및 기타 연산
function inject(memo, iterator, context) {
this.each(function(value, index) {
memo = iterator.call(context, memo, value, index) ;
});
remove
}
//모든 데이터에 대해 메소드 실행
function inform(method) {
var args = $A(arguments ) .slice(1);
return this.map(function(value) {
return value[method].apply(value, args);
})
}
//데이터에서 최대값 찾기
function max(iterator, context) {
iterator = iterator || Prototype.K
this.each(function(value; , index ) {
value = iterator.call(context, value, index);
if (result == null || value >= result)
result = value
});
결과 반환
}
//데이터에서 최소값 찾기
function min(iterator, context) {
iterator = Prototype.K; >var result ;
this.each(function(value, index) {
value = iterator.call(context, value, index);
if (result == null || value < result)
result = value;
});
return result;
}
//모든 데이터를 2개로 나누고, 첫 번째 그룹은 특정 조건을 만족하는 데이터입니다. 두 번째 그룹 조건을 충족하지 않는 데이터의 경우
function partition(iterator, context) {
iterator = iterator || Prototype.K
var trues = [], falses = []
this.each(function(value, index) {
(iterator.call(context, value, index) ?
trues : falses).push(value);
}) return [ trues, falses];
//모든 데이터의 속성 값을 가져오고 결과를 반환합니다
function pluck(property) {
var results = []
this .each(function(value) {
results.push(value[property]);
})
return results
}
//결과 찾기 특정 조건부 데이터를 만족하지 않는
function recognition(iterator, context) {
var results = []
this.each(function(value, index) {
if (!iterator. call(context, value , index))
results.push(value);
})
return results
}
//모든 데이터를 특정 항목에 따라 정렬 조건
function sortBy(iterator, context) {
return this.map(function(value, index) {
return {
value: value,
criteria: iterator.call(context, 값, 인덱스)
};
}).sort(function(left, right) {
var a = left.criteria, b = right.criteria;
return a < b ? - 1 : a > ; b ? 1 : 0;
}).pluck('value')
//데이터의 배열 표현 반환
function
return this.map();
}
//기본적으로 특정 작업을 수행하기 위해 두 세트의 데이터를 함께 사용합니다.
function zip() {
var iterator = Prototype.K , args = $A(인수);
if (Object.isFunction(args.last()))
iterator = args.pop()
var collections = [this].concat (args ).map($A);
return this.map(function(value, index) {
return iterator(collections.pluck(index));
}); 🎜>
function size() {
return this.toArray().length;
}
//Enumerable 객체를 나타내는 문자열 표현을 반환합니다.
function Inspection() {
return '#
}
return {
each: Each,
eachSlice: EachSlice ,
all: 모두,
every: 모두,
any: any,
some: any,
collect: 수집,
map: 수집,
Detect: 감지,
findAll: findAll,
선택: findAll,
필터: findAll,
grep: grep,
include: include,
member: include,
inGroupsOf: inGroupsOf,
inject: 주입,
invoke: 호출,
max: max,
min: min,
partition: partition,
pluck: pluck,
reject: 거부,
sortBy: sortBy,
toArray: toArray,
항목: toArray,
zip: zip,
크기: size,
검사: 검사,
찾기: 감지
} ;
})();
Enumerable에서 제공하는 메서드를 배워보겠습니다.
all
collect
탐지
eachSlice
항목
find
findAll
grep
inGroupsOf
include
inject
invoke
map
max
member
min
partition
pluck
reject
select
size
sortBy
toArray
zip
all 메소드:
여부를 결정합니다. 모든 요소는 직접적으로 또는 제공된 반복기에 의한 계산을 통해 true와 부울 동일합니다.
기본적으로 Each 메소드를 호출하여 각 데이터가 반복기 조건을 충족하는지 확인하고, 그 중 하나가 조건을 충족하지 않는 경우 반복자 조건에서 $break 예외가 발생하면 이 예외는 각 메서드에서 포착됩니다. 여기서 특정 객체를 해당 부울 값으로 변환할 수 있는 '!!'의 사용법에 주의하세요.
!!' String 'true
0 false
예를 살펴보겠습니다.
🎜> 코드 복사
코드는 다음과 같습니다.// -> true(빈 배열에는 false와 동일할 수 있는 요소가 없음) ) $R(1, 5).all()
// -> true([1..5]의 모든 값은 true와 동일)
[0, 1, 2].all()
// -> false(단 하나의 루프 주기만 사용: 0은 false와 동일함)
[9, 10, 15].all(함수 (n) { return n > = 10; })
// -> false(반복자는 9에서 false를 반환합니다)
$H({ 이름: 'John', 나이: 29 , 죄송합니다: false }).all (function(pair) { return pair.value; })
// -> false(죄송합니다/false 쌍은 false 값을 생성합니다)
any 메소드:
는 all 메소드와 유사하므로 자세한 내용은 설명하지 않겠습니다.
코드를 복사하세요
코드는 다음과 같습니다
[].any()
// -> false(빈 배열에는 true와 동일할 수 있는 요소가 없음)
$R(0, 2).any( )
// -> true(두 번째 루프 주기에서 1은 true와 동일)
[2, 4, 6, 8, 10].any(function(n) { return 0 == n % 3; : false, opt3: '', opt4: 'pfew!' }).any(function(pair) { return pair.value; })
// -> true (opt4/'pfew!' 덕분에) 값이 true인 쌍)
collect/map(수집 메서드 별칭) 메서드:
코드를 복사하세요.
['Hitch', "Hiker's", 'Guide', 'To', 'The', 'Galaxy'].collect(function(s) { return s.charAt(0).toUpperCase() }) .join('')
// -> 'HHGTTG'
$R(1,5).collect(function(n) { return n * n })
// -> [1, 4, 9, 16, 25]
도움말 문서의 마지막 몇 줄에 유의하세요. 🎜>
두 번째, 속성 가져오기 시나리오: 모든 요소에서 동일한 속성을 가져와 사용하려고 합니다.
탐지 방법:
다음을 충족하는 첫 번째 데이터를 찾습니다. 실제로 이 메소드는 find의 별칭이므로 discover와 find 호출은 동일합니다.
코드 복사
// 약간 압축된 최적의 정확한 소수 감지 방법입니다. function isPrime(n) {
if (2 > n) return false; if (0 == n % 2) return (2 == n);for (var index = 3; n / index > index; index = 2)
if (0 == n % index) return false
return true;
// isPrime
$R(10,15).find(isPrime) // -> 11
[ 'hello' , 'world', 'this', 'is', 'nice'].find(function(s) { return s.length <= 3; })
// ->
각 메소드:
사용법 <span style="font-family:新宋体">$continue</span>
는 속도를 위해 Prototype 1.5 이후 릴리스에서는 더 이상 사용되지 않습니다. .
예제 보기:<span style="font-family:新宋体">$continue</span>
코드 복사 코드는 다음과 같습니다.
['하나', '둘', '셋'].each(function(s) { 경고(들); });
[ 'hello', 'world'].each(function(s) , index) { Alert(index ': ' }); // 경고 -> '0: hello' 다음 '1: world'
// 주입을 사용하는 누산기// 여기...
var result = []
$R(1,10).each(function(n) {
if (0 == n % 2) throw $continue;
if (n > 6) throw $ break
result.push(n)
}); 1, 3, 5]
eachSlice 메소드:
코드 복사
코드는 다음과 같습니다.
var 학생 = [ { 이름: '써니', 나이: 20 }, { 이름: '오드리', 나이: 21 }, { 이름: '매트', 나이: 20 }, { 이름: ' Élodie', 나이: 26 }, { 이름: 'Will', 나이: 21 }, { 이름: 'David', 나이: 23 }, { 이름: 'Julien', 나이: 22 }, { 이름: 'Thomas' , 나이: 21 }, { 이름: '세르필', 나이: 22 } ]
students.eachSlice(4, function(toon) { return toon.pluck('name'); })
// -> [ ['써니', '오드리', '맷', '에로디'],
// ['윌', '데이비드', '줄리앙', '토마스'],
// ['Serpil'] ]
//아래 첫 번째 메소드는 Array 객체
students.eachSlice(2).first()
// -> name : 'Sunny', age: 20 }, { name: 'Audrey', age: 21 }]
entries 메소드는 toArray 메소드이고, map 메소드는 toArray 메소드, map 메소드는 Collect 메소드와 동일합니다:
코드 복사 코드는 다음과 같습니다:
$R(1, 5).toArray() // - > [1, 2, 3, 4, 5]
find/findAll(select 메소드의 별칭) 메소드:
코드 복사 코드는 다음과 같습니다.
//find method
[ 'hello', 'world', 'this', 'is' , 'nice'].find(function(s) { return s.length <= 3; })
// -> 'is'
//findAll 메소드
$R(1, 10).findAll(function(n) { return 0 == n % 2; })
// -> [2, 4, 6, 8, 10] [ 'hello', 'world', 'this ', 'is', 'nice'].findAll (함수(함수) { return s.length >= 5; })
// -> ['hello', 'world']
grep 메소드:
이 메소드에서 주목해야 할 점은 함수 내에서 매개변수 필터를 정규식으로 통일한 후 정규식의 match 메소드를 호출하여 판단하기
코드 복사 코드는 다음과 같습니다:
// 어딘가에 반복되는 문자가 있는 모든 문자열을 가져옵니다
[' hello', 'world', 'this', 'is', 'cool'].grep (/(.)1/)
// -> ['hello', 'cool']
/ / 0 또는 5로 끝나는 모든 숫자 가져오기
$R(1,30).grep (/[05]$/)
// ->
// 마이너스 1
$R(1,30).grep (/[05]$/, function(n) { return n - 1; })
// -> 4, 9, 14, 19, 24, 29]
//
['hello', 'world', 'this', 'is', 'cool'] 어딘가에서 반복되는 문자가 있는 모든 문자열을 가져옵니다. grep(/(.)1/)
// -> ['hello' , 'cool']
// 0 또는 5로 끝나는 모든 숫자를 가져옵니다
$R(1,30). grep(/[05]$/)
// -> [5, 10 , 15, 20, 25, 30]
// 마이너스 1
$R(1,30). grep(/[05]$/, function(n) { return n - 1; })
// -> [4, 9, 14, 19, 24, 29]
inGroupsOf 메소드:
코드 복사 코드는 다음과 같습니다.
var Students = [ { 이름: 'Sunny', 나이: 20 }, { 이름: 'Audrey', 나이: 21 }, { 이름: 'Matt', 나이: 20 }, { 이름: 'Élodie', 나이: 26 }, { 이름: 'Will', 나이: 21 }, { 이름: '데이비드', 나이: 23 }, { 이름: '줄리앙', 나이: 22 }, { 이름: '토마스', 나이: 21 }, { 이름: '세르필', 나이: 22 } ];
//pluck 메소드는 객체의 특정 속성을 얻는 것입니다. 여기서는 name 속성을 얻습니다.
students.pluck('name').inGroupsOf(4)
// -> [ ['Sunny', 'Audrey', 'Matt', 'Élodie'],
// ['Will', 'David', 'Julien', 'Thomas'],
// ['Serpil ', null, null, null] ]
include/member(include method alias) 메소드, 여기서는 먼저 객체에 indexOf 메소드가 있는지 확인하고, 있으면 호출합니다. 이 방법을 직접 사용하세요:
코드 복사 코드는 다음과 같습니다:
$R(1,15).include(10)
// -> true
['hello', 'world'].include('HELLO')
/ / -> false
[1, 2, '3', '4' , '5'].include(3)
// -> true(== 실제 유형 무시)
삽입 방법:
코드 복사 코드는 다음과 같습니다.
$R(1,10).inject(0, function(acc, n) { return acc n; })
// -> 55(1~10의 합)
$R(2,5).inject(1, function(acc, n) { return acc * n; })
// -> 120 (팩토리얼 5)
['hello', 'world' , 'this', 'is', 'nice'].inject([], function(array, value, index) {
if (0 == index % 2) array.push(value);
반환 배열
})
// -> ['hello', 'this', 'nice']
호출 메소드:
코드 복사 코드는 다음과 같습니다.
['hello', 'world', 'cool!'].invoke('toUpperCase')
// ['HELLO', 'WORLD', 'COOL!']
['hello', 'world', 'cool!'].invoke('substring', 0, 3)
// [ 'hel', 'wor', 'coo']
최대/최소 방법:
코드 복사 코드는 다음과 같습니다:
$R(1,10).max() // -> 10
['hello', 'world', 'gizmo'].max( )
// -> '세계'
function Person(name, age) { this.name = name; this.age = age }
var john = new Person('John', 20; );
var mark = new Person('Mark', 35);
var 데이지 = new Person('Daisy', 22)
[john, mark, 데이지].max(function(person) ) { return person.age })
// -> 35
파티션 방법:
코드 복사 코드는 다음과 같습니다.
['hello', null, 42, false, true, , 17].partition()
// -> ', 42, true, 17], [null, false, 정의되지 않음]]
$R(1, 10).partition(function(n) { return 0 == n % 2; })
// -> [[2, 4, 6, 8, 10], [1, 3, 5, 7, 9]]
['hello', null, 42, false, true, , 17].partition( )
// -> [['hello', 42, true, 17], [null, false, 정의되지 않음]]
$R(1, 10).partition(function(n) { return 0 == n % 2;
pluck 방법:
코드 복사
코드는 다음과 같습니다.
['hello', 'world', 'this' , 'is', 'nice'].pluck( 'length') // -> [5, 5, 4, 3, 4]
거부 방법:
코드 복사
코드는 다음과 같습니다.
$R(1, 10).reject(function(n) { return 0 == n % 2; }) // -> [1, 3, 5, 7, 9]
[ 'hello', 'world', 'this', 'is', ' nice'].reject(function(s) { return s.length >= 5; })// -> ['this', 'is', 'nice']
$R(1 , 10).reject(function(n) { return 0 == n % 2; })
// -> [1, 3, 5, 7, 9]
[ 'hello', 'world ', 'this', 'is', 'nice'].reject(function(s) { return s.length >= 5; })
// -> ['this', 'is', 'nice']
size 방식이 생략되었습니다.
이 메소드는 먼저 map 메소드를 통해 객체 배열을 반환한 다음 배열의 sort 메소드를 호출하고 마지막으로 객체의 value 속성을 꺼냅니다.
코드 복사
코드는 다음과 같습니다:
['hello', 'world', 'this', 'is', 'nice'].sortBy( function(s) { return s.length ; }) // -> 'is', 'this', 'nice', 'hello', 'world']
['hello', 'world ', 'this', 'is' , 'cool'].sortBy(function(s) {var md = s.match(/[aeiouy]/g);
return null == md ? 0 : md.length;
} )
// -> [ 'world', 'this', 'is', 'hello', 'cool'] (모음 개수순으로 정렬)
zip 방식 :
코드 복사
코드는 다음과 같습니다.
var firstNames = ['Justin', 'Mislav', 'Tobie', 'Christophe']
var lastNames = ['Palmer', 'Marohnić', 'Langel', 'Porteneuve'] ;
firstNames.zip(lastNames)
// -> [['Justin', 'Palmer'], ['Mislav', 'Marohnić'], ['Tobie', 'Langel'], [ 'Christophe', 'Porteneuve']]
//이 예에서 매개변수 a가 두 배열의 해당 항목을 나타내는 배열임을 알 수 있습니다.
firstNames.zip(lastNames, function(a) { return a.join(' ') })
// -> ['Justin Palmer', 'Mislav Marohnić', 'Tobie Langel', 'Christophe Porteneuve']
//이 예를 통해 다음을 수행할 수 있습니다.
에서 여러 배열을 전달할 수 있는지 확인하세요. var city = ['Memphis', 'Zagreb', 'Montreal', 'Paris']
firstNames.zip(lastNames, city, function(p) { return p [0] ' ' p[1] ', ' p[2] })
// -> ['Justin Palmer, Memphis', 'Mislav Marohnić, Zagreb', 'Tobie Langel, Montreal', ' Christophe Porteneuve, Paris']
firstNames.zip($R(1, 100), function(a) { return a.reverse().join('. '); })
// -> ['1. 저스틴', '2. 미슬라브', '4. 크리스토프']