PHP에서 변수나 배열 요소의 값을 확인할 때 isset(), empty(), is_null() 중 어떤 함수를 써야 할지 헷갈린 적 있을까. 대부분의 개발자는 이 세 함수가 비슷한 역할을 한다고 생각하고 아무거나 써도 된다고 생각한다. 하지만 실제로는 각 함수가 검사하는 대상과 반환값이 미묘하게 다르고, 잘못 쓰면 버그로 직결된다. 이번에는 각 함수의 정확한 동작 방식, 실제 사용 사례, 그리고 언제 어떤 함수를 써야 하는지 완벽하게 정리해서 소개하겠다.

 

NULL 검사 함수 동작 원리

isset(), empty(), is_null()은 모두 변수의 상태를 검사하지만, 검사 범위와 반환값이 다르다. 먼저 각 함수가 언제 true를 반환하는지 정확히 알아야 한다.

isset()은 변수가 정의되어 있고 NULL이 아닌지 확인한다. 변수가 존재하면서 NULL이 아닌 모든 값에 대해 true를 반환한다. 0, 빈 문자열, false 같은 falsy 값도 true를 반환한다. 다만 변수가 정의되지 않았거나 명시적으로 NULL로 설정되면 false를 반환한다.

empty()는 변수가 비어있는지 검사한다. false, 0, "0", 빈 문자열, NULL, 정의되지 않은 변수를 모두 true로 간주한다. 즉, PHP가 falsy로 취급하는 모든 값을 true로 반환한다.

is_null()은 변수가 정확히 NULL인지만 확인한다. NULL이면 true, 그 외 모든 값(0, false, 빈 문자열 포함)은 false를 반환한다. 다만 정의되지 않은 변수에 사용하면 경고(Warning)를 발생시킨다.

 

세 함수 동작 비교표
값 isset() empty() is_null()
$var = NULL; false true true
$var = 0; true true false
$var = "0"; true true false
$var = ""; true true false
$var = false; true true false
$var = []; true true false
$var = "hello"; true false false
정의되지 않은 변수 false true Warning 발생

 

실전 예제로 이해하기
예제 1: 사용자 입력값 검증

웹 폼에서 사용자가 입력한 값을 받을 때 isset()을 쓰는 게 맞다. empty()를 쓰면 0이나 "0" 같은 유효한 값이 거부될 수 있다.

<?php
// ✗ 잘못된 것: empty()로 검증하면 0과 "0"이 거부됨
if (empty($_POST['age'])) {
    echo "나이를 입력하세요";
    exit;
}
$age = $_POST['age'];
// "0" 나이로 입력한 사용자도 막음

// ✓ 올바른 것: isset()으로 변수 존재 여부 먼저 확인
if (!isset($_POST['age'])) {
    echo "나이를 입력하세요";
    exit;
}
$age = $_POST['age'];
// 나이 값이 0이어도 통과

// ✓ 더 좋은 것: isset() + 추가 유효성 검증
if (!isset($_POST['age']) || trim($_POST['age']) === '') {
    echo "나이를 입력하세요";
    exit;
}
$age = (int)$_POST['age'];
if ($age < 0 || $age > 150) {
    echo "유효한 나이를 입력하세요";
    exit;
}
?>
예제 2: 배열 요소 존재 여부 확인

배열 요소를 접근하기 전에 먼저 요소가 존재하는지 확인해야 한다. isset()이 array_key_exists()보다 더 간결하다.

<?php
$user = [
    'name' => 'John',
    'email' => null,
    'phone' => '010-1234-5678'
];

// ✗ 잘못된 것: 존재하지만 NULL인 요소도 false 반환
if (!isset($user['email'])) {
    echo "이메일이 없습니다";  // 실행됨 (email이 NULL이므로)
}

// ✓ 올바른 것: 요소의 존재 여부만 확인하려면 array_key_exists() 사용
if (!array_key_exists('email', $user)) {
    echo "이메일이 없습니다";  // 실행 안 됨 (email 키가 존재)
}

// ✓ 올바른 것: 값이 NULL인지 확인하려면 is_null() 사용
if (is_null($user['email'])) {
    echo "이메일이 NULL입니다";  // 실행됨
}
?>
예제 3: API 응답 처리

외부 API에서 받은 응답을 처리할 때 empty()를 쓰면 0 값이나 false 값이 있는데도 "데이터가 없다"고 판단할 수 있다.

<?php
$response = [
    'status' => 200,
    'data' => [
        'user_count' => 0,  // 사용자가 0명
        'is_active' => false  // 비활성화 상태
    ]
];

// ✗ 잘못된 것: empty()로 검증하면 0과 false를 "없는 데이터"로 취급
if (empty($response['data']['user_count'])) {
    echo "사용자가 없습니다";  // 실행됨 (0은 empty()에서 true)
}
// 하지만 user_count는 실제로 존재하는 데이터

// ✓ 올바른 것: isset()으로 키 존재 여부 확인
if (!isset($response['data']['user_count'])) {
    echo "user_count 필드가 없습니다";  // 실행 안 됨
}

// ✓ 올바른 것: 정확한 값 비교
if ($response['data']['user_count'] === 0) {
    echo "사용자가 0명입니다";  // 실행됨
}

if ($response['data']['is_active'] === false) {
    echo "계정이 비활성화되었습니다";  // 실행됨
}
?>

 

주의사항과 흔한 실수

✗ 실수 1: empty()를 모든 곳에 사용하기
empty()는 의도한 것보다 많은 값을 거부한다. 특히 0이나 false 같은 유효한 값이 필요한 경우 반드시 피해야 한다. 예를 들어 상품 수량이 0개, 할인율이 0%, 회원 활성화 상태가 false 같은 정상적인 데이터까지 제외된다.

✗ 실수 2: is_null()을 정의되지 않은 변수에 사용하기
is_null()을 정의되지 않은 변수에 사용하면 PHP Warning이 발생한다. isset()으로 먼저 변수가 정의되었는지 확인한 후 is_null()을 사용하거나, 처음부터 isset()만 사용하는 게 낫다.

<?php
// ✗ 잘못된 것: Warning 발생
if (is_null($undefined_var)) {  // PHP Warning: Undefined variable
    echo "NULL입니다";
}

// ✓ 올바른 것: 먼저 정의 여부 확인
if (isset($undefined_var) && is_null($undefined_var)) {
    echo "NULL입니다";
}

// ✓ 더 간단한 것: isset()만 사용
if (!isset($undefined_var)) {
    echo "정의되지 않았거나 NULL입니다";
}
?>

✗ 실수 3: 타입 비교 없이 값 비교하기
NULL 검사 후에도 반드시 타입을 함께 확인해야 할 때가 있다. 예를 들어 문자열 "0"과 정수 0은 값이 같아 보이지만 다르다. isset()이 true를 반환한 후에도 값의 타입과 범위를 검증해야 한다.

<?php
$_GET['id'] = "0";  // 사용자 입력

// ✗ 잘못된 것: isset() 후 바로 사용
if (isset($_GET['id'])) {
    $id = $_GET['id'];  // 문자열 "0"
    if ($id == 0) {  // 느슨한 비교(==): "0" == 0 = true
        echo "아이디가 0입니다";  // 실행됨
    }
}

// ✓ 올바른 것: 타입 캐스팅과 엄격한 비교
if (isset($_GET['id'])) {
    $id = (int)$_GET['id'];  // 정수로 변환
    if ($id === 0) {  // 엄격한 비교(===): 0 === 0 = true
        echo "아이디가 0입니다";
    }
}
?>

 

함수 선택 가이드

isset()을 사용할 때: 변수가 정의되어 있고 NULL이 아닌지 확인하고 싶을 때. GET/POST/SESSION 배열 요소 접근 전에 먼저 isset()으로 확인하는 게 PHP 개발의 기본이다. 0, false, 빈 문자열 같은 값도 유효한 데이터로 취급해야 할 때도 isset()이 맞다.

empty()를 사용할 때: 사용자 입력이 정말 "비어있는" 상태인지 빠르게 판단할 때만 사용하자. 예를 들어 선택적 필드(optional field)에서 사용자가 아무것도 입력하지 않았는지 확인할 때다. 하지만 그 뒤에도 반드시 더 정확한 검증이 필요하다.

is_null()을 사용할 때: 변수가 정확히 NULL 값인지만 확인하고 싶을 때다. 다만 항상 isset()으로 먼저 정의 여부를 확인한 후 사용하거나, NULL이 될 수 있다고 알려진 함수의 반환값을 확인할 때 사용한다.

 

실무 체크리스트

isset(), empty(), is_null()은 NULL 검사 함수 중 가장 기초적이면서도 자주 틀리는 부분이다. 작은 선택이 모여서 예상 밖의 버그를 만든다는 점을 잊지 말자. 이 글의 비교표와 예제를 참고해 지금 바로 자신의 코드를 점검해보면, 사용자 입력 처리 부분에서 NULL 검사 오류를 줄일 수 있을 것이다.