<?php

/**
 * Função que testa se o array é sequencial.
 * 
 * @param array Array a ser testado
 * @return bool True se $array for sequencial, False caso contrário
 */

function is_sequential ($array) {
    for($x = 0; $x < count($array); $x++){
        if(array_key_exists($x, $array) == false){
            return false;
        }
    }
    
    return true;
}

/**
 * Função que testa se o array é associativo.
 * 
 * @param array Array a ser testado
 * @return bool True se $array for associativo, False caso contrário
 */

function is_associative (array $array) {
    return !is_sequential($array);
}

/**
 * Lista de testes que a função deve ser submetida.
 * 
 * Cada item da lista deve ser um array com três índices.
 * O primeiro, "array", com o array a ser testado pela função.
 * O segundo, "is_sequential", um valor booleano esperado como retorno da função is_sequential.
 * O terceiro, "is_associative", um valor booleano esperado como retorno da função is_associative.
 */

$tests = array();

// Teste 1: Array com índices numéricos sequenciais

$tests[] = [
    "array" => ["a", "b", "c", "d", "e"], 
    "is_sequential" => true,
    "is_associative" => false
];

// Teste 2: Array associativo

$tests[] = [
    "array" => ["name" => "foo", "lastname" => "bar"], 
    "is_sequential" => false,
    "is_associative" => true
];

// Teste 3: Array com chave do tipo string contendo inteiro válido

$tests[] = [
    "array" => ["0" => "foo", "1" => "bar"], 
    "is_sequential" => true,
    "is_associative" => false
];

// Teste 4: Array com índices do tipo float

$tests[] = [
    "array" => [0.5 => "foo", -3.5 => "bar"], 
    "is_sequential" => true,
    "is_associative" => false
];

// Teste 5: Array com índices do tipo booleanos

$tests[] = [
    "array" => [true => "foo", false => "bar"], 
    "is_sequential" => true,
    "is_associative" => false
];

// Teste 6: Array com índice nulo

$tests[] = [
    "array" => [null => "foo"], 
    "is_sequential" => false,
    "is_associative" => true
];

// Teste 7: Array misto

$tests[] = [
    "array" => ["foo", "baz" => "bar"], 
    "is_sequential" => true,
    "is_associative" => true
];

// Teste 8: Array de índices numéricos desordenados

$tests[] = [
    "array" => [1 => "foo", 0 => "bar"], 
    "is_sequential" => true,
    "is_associative" => false
];

// Teste 9: Array de índices numéricos ordenados não sequenciais

$tests[] = [
    "array" => [0 => "foo", 1 => "bar", 6 => "baz"], 
    "is_sequential" => true,
    "is_associative" => false
];


/**
 * Executa os testes.
 */
 
foreach ($tests as $i => $test) {
    if ($test["is_sequential"] !== is_sequential($test["array"])) {
        echo sprintf("is_sequential: Algo errado não está certo! Teste %d falhou.\n", $i+1);
    }
    
    if ($test["is_associative"] !== is_associative($test["array"])) {
        echo sprintf("is_associative: Algo errado não está certo! Teste %d falhou.\n", $i+1);
    }
}
