PHPackages                             samsonasik/array-lookup - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [File &amp; Storage](/categories/file-storage)
4. /
5. samsonasik/array-lookup

ActiveLibrary[File &amp; Storage](/categories/file-storage)

samsonasik/array-lookup
=======================

A fast lookup library that help you verify and search array and Traversable data

2.6.0(2mo ago)2868.2k↑17.5%32MITPHPPHP ^8.2CI passing

Since Jan 6Pushed 1mo ago2 watchersCompare

[ Source](https://github.com/samsonasik/ArrayLookup)[ Packagist](https://packagist.org/packages/samsonasik/array-lookup)[ Docs](https://github.com/samsonasik/ArrayLookup)[ GitHub Sponsors](https://github.com/samsonasik)[ RSS](/packages/samsonasik-array-lookup/feed)WikiDiscussions main Synced 2d ago

READMEChangelog (10)Dependencies (18)Versions (46)Used By (2)

ArrayLookup
===========

[](#arraylookup)

[![Latest Version](https://camo.githubusercontent.com/f820485fee4e11498c12b17e8ae9e9cf5b428605c08204cc2b7bcfc1269d539a/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f72656c656173652f73616d736f6e6173696b2f41727261794c6f6f6b75702e7376673f7374796c653d666c61742d737175617265)](https://github.com/samsonasik/ArrayLookup/releases)[![ci build](https://github.com/samsonasik/ArrayLookup/workflows/ci%20build/badge.svg)](https://github.com/samsonasik/ArrayLookup/workflows/ci%20build/badge.svg)[![Code Coverage](https://camo.githubusercontent.com/81b89aad3dd3ff8a0fab267cf62480496207c46b806dde817864b3e98deefcd7/68747470733a2f2f636f6465636f762e696f2f67682f73616d736f6e6173696b2f41727261794c6f6f6b75702f6272616e63682f6d61696e2f67726170682f62616467652e737667)](https://codecov.io/gh/samsonasik/ArrayLookup)[![PHPStan](https://camo.githubusercontent.com/fdcdf50c27377a0f41a7196eeaae8539c4684bfc8a1f9843fdac60fdbc53deab/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7374796c652d6c6576656c2532306d61782d627269676874677265656e2e7376673f7374796c653d666c61742d737175617265266c6162656c3d7068707374616e)](https://github.com/phpstan/phpstan)[![Downloads](https://camo.githubusercontent.com/60b0be9c8ea5e51fca9602a6b8f5a0cc39da3525bc9f06516b0d6b6a485ba6f2/68747470733a2f2f706f7365722e707567782e6f72672f73616d736f6e6173696b2f61727261792d6c6f6f6b75702f646f776e6c6f616473)](https://packagist.org/packages/samsonasik/array-lookup)

Introduction
------------

[](#introduction)

ArrayLookup is a fast lookup library that helps you verify and search `array` and `Traversable` data.

Features
--------

[](#features)

- Verify at least times: [`once()`](#1-atleastonce), [`twice()`](#2-atleasttwice), [`times()`](#3-atleasttimes)
- Verify at most times: [`once()`](#1-atmostonce), [`twice()`](#2-atmosttwice), [`times()`](#3-atmosttimes)
- Verify exact times: [`once()`](#1-onlyonce), [`twice()`](#2-onlytwice), [`times()`](#3-onlytimes)
- Verify in interval range: [`isInclusiveOf()`](#1-intervalisinclusiveof), [`isExclusiveOf()`](#2-intervalisexclusiveof)
- Verify all or none match: [`match()`](#1-allmatch), [`none()`](#2-allnone)
- Search data: [`first()`](#1-finderfirst), [`last()`](#2-finderlast), [`nth()`](#3-findernth), [`rows()`](#4-finderrows), [`partition()`](#5-finderpartition)
- Collect data with [`filter and transform`](#g-collector)

Installation
------------

[](#installation)

**Require this library uses [composer](https://getcomposer.org/).**

```
composer require samsonasik/array-lookup
```

Usage
-----

[](#usage)

**A. AtLeast**
--------------

[](#a-atleast)

#### 1. `AtLeast::once()`

[](#1-atleastonce)

It verify that data has filtered found item at least once.

```
use ArrayLookup\AtLeast;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 1;

var_dump(AtLeast::once($data, $filter)) // true

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 4;

var_dump(AtLeast::once($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [1, 2, 3];
$filter = static fn($datum, $key): bool => $datum === 1 && $key >= 0;

var_dump(AtLeast::once($data, $filter)) // true

$data = [1, 2, 3];
$filter = static fn($datum, $key): bool => $datum === 4 && $key >= 0;

var_dump(AtLeast::once($data, $filter)) // false
```

#### 2. `AtLeast::twice()`

[](#2-atleasttwice)

It verify that data has filtered found items at least twice.

```
use ArrayLookup\AtLeast;

$data = [1, "1", 3];
$filter = static fn($datum): bool => $datum == 1;

var_dump(AtLeast::twice($data, $filter)) // true

$data = [1, "1", 3];
$filter = static fn($datum): bool => $datum === 1;

var_dump(AtLeast::twice($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [1, "1", 3];
$filter = static fn($datum, $key): bool => $datum == 1 && $key >= 0;

var_dump(AtLeast::twice($data, $filter)) // true

$data = [1, "1", 3];
$filter = static fn($datum, $key): bool => $datum === 1 && $key >= 0;

var_dump(AtLeast::twice($data, $filter)) // false
```

#### 3. `AtLeast::times()`

[](#3-atleasttimes)

It verify that data has filtered found items at least times passed in 3rd arg.

```
use ArrayLookup\AtLeast;

$data = [false, null, 0];
$filter = static fn($datum): bool => ! $datum;
$times = 3;

var_dump(AtLeast::times($data, $filter, $times)) // true

$data = [1, null, 0];
$filter = static fn($datum): bool => ! $datum;
$times = 3;

var_dump(AtLeast::times($data, $filter, $times)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [false, null, 0];
$filter = static fn($datum, $key): bool => ! $datum && $key >= 0;
$times = 3;

var_dump(AtLeast::times($data, $filter, $times)) // true

$data = [1, null, 0];
$filter = static fn($datum, $key): bool => ! $datum && $key >= 0;
$times = 3;

var_dump(AtLeast::times($data, $filter, $times)) // false
```

**B. AtMost**
-------------

[](#b-atmost)

#### 1. `AtMost::once()`

[](#1-atmostonce)

It verify that data has filtered found item at most once.

```
use ArrayLookup\AtMost;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 1;

var_dump(AtMost::once($data, $filter)) // true

$data = [1, "1", 3];
$filter = static fn($datum): bool => $datum == 1;

var_dump(AtMost::once($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = ['abc', 'def', 'some test'];
$filter = static fn(string $datum, int $key): bool => $datum === 'def' && $key === 1;

var_dump(AtMost::once($data, $filter)) // true

$data = ['abc', 'def', 'some test'];
$filter = static fn(string $datum, int $key): bool => $key > 0;

var_dump(AtMost::once($data, $filter)) // false
```

#### 2. `AtMost::twice()`

[](#2-atmosttwice)

It verify that data has filtered found items at most twice.

```
use ArrayLookup\AtMost;

$data = [1, "1", 2];
$filter = static fn($datum): bool => $datum == 1;

var_dump(AtMost::twice($data, $filter)) // true

$data = [1, "1", 2, 1];
$filter = static fn($datum): bool => $datum == 1;

var_dump(AtMost::twice($data, $filter)) // false
```

#### 3. `AtMost::times()`

[](#3-atmosttimes)

It verify that data has filtered found items at most times passed in 3rd arg.

```
use ArrayLookup\AtMost;

$data = [false, null, 0];
$filter = static fn($datum): bool => ! $datum;
$times = 3;

var_dump(AtMost::times($data, $filter, $times)) // true

$data = [false, null, 0, 0];
$filter = static fn($datum): bool => ! $datum;
$times = 3;

var_dump(AtMost::times($data, $filter, $times)) // false
```

**C. Only**
-----------

[](#c-only)

#### 1. `Only::once()`

[](#1-onlyonce)

It verify that data has filtered found item exactly found only once.

```
use ArrayLookup\Only;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 1;

var_dump(Only::once($data, $filter)) // true

$data = [1, "1", 3]
$filter = static fn($datum): bool => $datum == 1;

var_dump(Only::once($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [1, 2, 3];
$filter = static fn($datum, $key): bool => $datum === 1 && $key >= 0;

var_dump(Only::once($data, $filter)) // true

$data = [1, "1", 3]
$filter = static fn($datum, $key): bool => $datum == 1  && $key >= 0;

var_dump(Only::once($data, $filter)) // false
```

#### 2. `Only::twice()`

[](#2-onlytwice)

It verify that data has filtered found items exactly found only twice.

```
use ArrayLookup\Only;

$data = [1, "1", 3];
$filter = static fn($datum): bool => $datum == 1;

var_dump(Only::twice($data, $filter)) // true

$data = [true, 1, new stdClass()];
$filter = static fn($datum): bool => (bool) $datum;

var_dump(Only::twice($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [1, "1", 3];
$filter = static fn($datum, $key): bool => $datum == 1 && $key >= 0;

var_dump(Only::twice($data, $filter)) // true

$data = [true, 1, new stdClass()];
$filter = static fn($datum, $key): bool => (bool) $datum && $key >= 0;

var_dump(Only::twice($data, $filter)) // false
```

#### 3. `Only::times()`

[](#3-onlytimes)

It verify that data has filtered found items exactly found only same with times passed in 3rd arg.

```
use ArrayLookup\Only;

$data = [false, null, 1];
$filter = static fn($datum): bool => ! $datum;
$times = 2;

var_dump(Only::times($data, $filter, $times)) // true

$data = [false, null, 0];
$filter = static fn($datum): bool => ! $datum;
$times = 2;

var_dump(Only::times($data, $filter, $times)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = [false, null, 1];
$filter = static fn($datum, $key): bool => ! $datum && $key >= 0;
$times = 2;

var_dump(Only::times($data, $filter, $times)) // true

$data = [false, null, 0];
$filter = static fn($datum, $key): bool => ! $datum && $key >= 0;
$times = 2;

var_dump(Only::times($data, $filter, $times)) // false
```

**D. Interval**
---------------

[](#d-interval)

#### 1. `Interval::isInclusiveOf()`

[](#1-intervalisinclusiveof)

It verify that data has filtered found items within min and max (inclusive).

```
use ArrayLookup\Interval;

$orders = [
    ['status' => 'paid'],
    ['status' => 'paid'],
    ['status' => 'pending'],
    ['status' => 'paid'],
];

$filter = static fn(array $order): bool => $order['status'] === 'paid';

// inclusive means min and max boundaries are allowed
var_dump(Interval::isInclusiveOf($orders, $filter, 3, 5)) // true
var_dump(Interval::isInclusiveOf($orders, $filter, 2, 5)) // true
```

#### 2. `Interval::isExclusiveOf()`

[](#2-intervalisexclusiveof)

It verify that data has filtered found items between min and max (exclusive).

```
use ArrayLookup\Interval;

$orders = [
    ['status' => 'paid'],
    ['status' => 'paid'],
    ['status' => 'pending'],
    ['status' => 'paid'],
];

$filter = static fn(array $order): bool => $order['status'] === 'paid';

// exclusive means strictly between min and max
var_dump(Interval::isExclusiveOf($orders, $filter, 3, 5)) // false
var_dump(Interval::isExclusiveOf($orders, $filter, 2, 5)) // true
```

**E. All**
----------

[](#e-all)

#### 1. `All::match()`

[](#1-allmatch)

It verify that all items match the filter and data is non-empty.

```
use ArrayLookup\All;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum > 0;

var_dump(All::match($data, $filter)) // true

$data = [1, 0, 3];
$filter = static fn($datum): bool => $datum > 0;

var_dump(All::match($data, $filter)) // false

$data = [];
$filter = static fn($datum): bool => $datum !== null;

var_dump(All::match($data, $filter)) // false

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = ['abc', 'def'];
$filter = static fn($datum, $key): bool => $datum !== '' && $key >= 0;

var_dump(All::match($data, $filter)) // true
```

#### 2. `All::none()`

[](#2-allnone)

It verify that no items match the filter (empty data returns true).

```
use ArrayLookup\All;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 4;

var_dump(All::none($data, $filter)) // true

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 2;

var_dump(All::none($data, $filter)) // false

$data = [];
$filter = static fn($datum): bool => $datum !== null;

var_dump(All::none($data, $filter)) // true

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$data = ['abc', 'def'];
$filter = static fn($datum, $key): bool => $key === 0 && $datum === 'abc';

var_dump(All::none($data, $filter)) // false
```

**F. Finder**
-------------

[](#f-finder)

#### 1. `Finder::first()`

[](#1-finderfirst)

It search first data filtered found.

```
use ArrayLookup\Finder;

$data = [1, 2, 3];
$filter = static fn($datum): bool => $datum === 1;

var_dump(Finder::first($data, $filter)) // 1

$filter = static fn($datum): bool => $datum == 1000;
var_dump(Finder::first($data, $filter)) // null

// RETURN the Array key, pass true to 3rd arg

$filter = static fn($datum): bool => $datum === 1;

var_dump(Finder::first($data, $filter, true)) // 0

$filter = static fn($datum): bool => $datum == 1000;
var_dump(Finder::first($data, $filter, true)) // null

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

$filter = static fn($datum, $key): bool => $datum === 1 && $key >= 0;

var_dump(Finder::first($data, $filter)) // 1

$filter = static fn($datum, $key): bool => $datum == 1000 && $key >= 0;
var_dump(Finder::first($data, $filter)) // null
```

#### 2. `Finder::last()`

[](#2-finderlast)

It search last data filtered found.

```
use ArrayLookup\Finder;

$data = [6, 7, 8, 9];
var_dump(Finder::last(
    $data,
    static fn ($datum): bool => $datum > 5
)); // 9

var_dump(Finder::last(
    $data,
    static fn ($datum): bool => $datum < 5
)); // null

// RETURN the Array key, pass true to 3rd arg

// ... with PRESERVE original key
var_dump(Finder::last(
    $data,
    static fn ($datum): bool => $datum > 5,
    true
)); // 3

// ... with RESORT key, first key is last record
var_dump(Finder::last(
    $data,
    static fn ($datum): bool => $datum > 5,
    true,
    false
)); // 0

var_dump(Finder::last(
    $data,
    static fn ($datum): bool => $datum < 5,
    true
)); // null

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter

var_dump(Finder::last(
    $data,
    static fn ($datum, $key): bool => $datum > 5 && $key >= 0
)); // 9

var_dump(Finder::last(
    $data,
    static fn ($datum, $key): bool => $datum < 5 && $key >= 0
)); // null
```

#### 3. `Finder::nth()`

[](#3-findernth)

It returns the 1st, 2nd, 3rd, and so on matching item, or multiple matching items at specific positions. The position is 1-based among matched results, not the original array index. Pass a single position to get one matching item, or an array of positions to get multiple matching items. If no match is found, it returns `null` for a single position or an empty array for multiple positions. Pass `true` to the 4th argument to return the key(s) instead of the value(s).

```
use ArrayLookup\Finder;

$data = [10, 20, 30, 40, 50];
$filter = static fn($datum): bool => $datum > 15;

// Get the 2nd matching value
var_dump(Finder::nth($data, $filter, 2)); // 30

// Get the 2nd matching key
var_dump(Finder::nth($data, $filter, 2, true)); // 2

// Get the 1st and 3rd matching values
var_dump(Finder::nth($data, $filter, [1, 3])); // [20, 40]

// Get the 1st and 3rd matching keys
var_dump(Finder::nth($data, $filter, [1, 3], true)); // [1, 3]

// No match (single)
var_dump(Finder::nth($data, $filter, 5)); // null

// No match (multiple)
var_dump(Finder::nth($data, $filter, [5, 6])); // []
```

#### 4. `Finder::rows()`

[](#4-finderrows)

It get rows data filtered found.

```
use ArrayLookup\Finder;

$data = [6, 7, 8, 9];
var_dump(Finder::rows(
    $data,
    static fn($datum): bool => $datum > 6
)); // [7, 8, 9]

var_dump(Finder::rows(
    $data,
    static fn ($datum): bool => $datum < 5
)); // []

// ... with PRESERVE original key
var_dump(Finder::rows(
    $data,
    static fn ($datum): bool => $datum > 6,
    true
)); // [1 => 7, 2 => 8, 3 => 9]

var_dump(Finder::rows(
    $data,
    static fn ($datum): bool => $datum < 5,
    true
)); // []

// WITH key array included, pass $key variable as 2nd arg on  filter to be used in filter
var_dump(Finder::rows(
    $data,
    static fn($datum, $key): bool => $datum > 6 && $key > 1
)); // [8, 9]

// WITH gather only limited found data
$data = [1, 2];
$filter = static fn($datum): bool => $datum >= 0;
$limit = 1;

var_dump(
    Finder::rows($data, $filter, limit: $limit)
); // [1]
```

#### 5. `Finder::partition()`

[](#5-finderpartition)

It splits data into two arrays: matching and non-matching items based on a filter.

```
use ArrayLookup\Finder;

// Basic partition - split numbers into greater than 5 and not
$data = [1, 6, 3, 8, 4, 9];
$filter = static fn($datum): bool => $datum > 5;

[$matching, $notMatching] = Finder::partition($data, $filter);

var_dump($matching);    // [6, 8, 9]
var_dump($notMatching); // [1, 3, 4]

// Partition with preserved keys
[$matching, $notMatching] = Finder::partition($data, $filter, preserveKey: true);

var_dump($matching);    // [1 => 6, 3 => 8, 5 => 9]
var_dump($notMatching); // [0 => 1, 2 => 3, 4 => 4]

// Using the array key inside the filter
$data = [10, 20, 30, 40];
$keyFilter = static fn($datum, $key): bool => $key % 2 === 0;

[$even, $odd] = Finder::partition($data, $keyFilter, preserveKey: true);

var_dump($even); // [0 => 10, 2 => 30]
var_dump($odd);  // [1 => 20, 3 => 40]
```

**G. Collector**
----------------

[](#g-collector)

It collect filtered data, with new transformed each data found:

**Before**

```
$newArray = [];

foreach ($data as $datum) {
    if (is_string($datum)) {
        $newArray[] = trim($datum);
    }
}
```

**After**

```
use ArrayLookup\Collector;

$when = fn ($datum): bool => is_string($datum);
$limit = 2;
$transform = fn ($datum): string => trim($datum);

$newArray = Collector::setUp($data)
       ->when($when) // optional, can just transform without filtering
       ->withLimit(2) // optional to only collect some data provided by limit config
       ->withTransform($transform)
       ->getResults();
```

###  Health Score

59

—

FairBetter than 98% of packages

Maintenance90

Actively maintained with recent releases

Popularity41

Moderate usage in the ecosystem

Community16

Small or concentrated contributor base

Maturity71

Established project with proven stability

 Bus Factor1

Top contributor holds 99.3% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~31 days

Recently: every ~16 days

Total

40

Last Release

75d ago

Major Versions

0.9.0 → 1.0.02023-01-09

1.x-dev → 2.0.02024-12-28

PHP version history (2 changes)0.0.1PHP ^8.1

2.0.0PHP ^8.2

### Community

Maintainers

![](https://www.gravatar.com/avatar/19076b7688ca1c8ee79ab3ac6fa6acdd7b96012973aba3b1a06cbb3154d7f3e5?d=identicon)[samsonasik](/maintainers/samsonasik)

---

Top Contributors

[![samsonasik](https://avatars.githubusercontent.com/u/459648?v=4)](https://github.com/samsonasik "samsonasik (283 commits)")[![nynka](https://avatars.githubusercontent.com/u/7600194?v=4)](https://github.com/nynka "nynka (2 commits)")

---

Tags

arrayatleastfastfilterfindfinderiterablelookuponlyphpsearchtraversablesearcharrayfilterfinderfastsplcollectorlookupiterabletraversable

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan, Rector

Type Coverage Yes

### Embed Badge

![Health badge](/badges/samsonasik-array-lookup/health.svg)

```
[![Health](https://phpackages.com/badges/samsonasik-array-lookup/health.svg)](https://phpackages.com/packages/samsonasik-array-lookup)
```

###  Alternatives

[sylius/resource-bundle

Resource component for Sylius.

23610.8M234](/packages/sylius-resource-bundle)[jeroen-g/explorer

Next-gen Elasticsearch driver for Laravel Scout.

399672.8k](/packages/jeroen-g-explorer)[yosymfony/resource-watcher

A simple resource watcher using Symfony Finder

698.8M22](/packages/yosymfony-resource-watcher)[ergebnis/classy

Provides collectors for classy constructs (classes, enums, interfaces, and traits).

393.0M25](/packages/ergebnis-classy)[arthurhoaro/favicon

PHP Library used to discover favicon from given URL

32776.7k](/packages/arthurhoaro-favicon)[ahmed-bhs/doctrine-doctor

Runtime analysis tool for Doctrine ORM integrated into Symfony Web Profiler. Unlike static linters, it analyzes actual query execution at runtime to detect performance bottlenecks, security vulnerabilities, and best practice violations during development with real execution context and data.

9410.8k](/packages/ahmed-bhs-doctrine-doctor)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
