Skip to content

Commit 103a0bf

Browse files
committed
fixup! Add EEP for native records
1 parent f609250 commit 103a0bf

File tree

1 file changed

+36
-42
lines changed

1 file changed

+36
-42
lines changed

eeps/eep-0079.md

Lines changed: 36 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -474,76 +474,70 @@ ETS nor `element/2` will work with native records.
474474
475475
### Native-record guard BIFs
476476
477-
#### `is_record/2`
477+
#### `is_record/3`
478478
479-
We define a pseudo-BIF `is_record/2`, which will be translated by
480-
the compiler to instructions to test whether `Term` is a native
481-
record.
479+
The existing `is_record/3` BIF is overloaded to also accept a native record:
482480
483481
```erlang
484-
is_record(Term :: dynamic(), #Module:Name) -> boolean().
485-
is_record(Term :: dynamic(), #Name) -> boolean().
482+
-spec is_record(Term :: dynamic(), Module :: module(), Name :: atom()) -> boolean();
483+
(Term :: dynamic(), Name :: atom(), Arity :: non_neg_integer()) -> boolean().
486484
```
487485
488-
The `Module` and `Name` arguments must be atoms.
489-
490-
If `Module` is not given, `Name` must refer to either an imported
491-
record or to a native record defined in the current module. The compiler
492-
will issue a diagnostic if no record having name `Name` is neither imported
493-
nor defined in the current module.
486+
If `Module` is a module name and `Name` is an atom, the predicate
487+
returns true if term `Term` is a native-record value with the
488+
corresponding native-record name and the native-record is visible (via
489+
export) at the call site.
494490
495-
Examples:
491+
Example:
496492
497-
```erlang
493+
```
498494
-module(misc).
499-
-record #user() {a,b,c}.
500-
501-
is_user(U) when is_record(U, #user) ->
502-
true;
503-
is_user(U) when is_record(U, #some_module:other_user) ->
504-
true;
505-
is_user(_U) ->
506-
false.
495+
is_user(U) -> is_record(U, some_module, user).
507496
```
508497
509-
<!-- -->
498+
#### `is_record/2`
499+
500+
The existing `is_record/2` function is extended to also work on native
501+
records:
510502
511503
```erlang
512-
-module(example).
513-
-import_record(misc, [user/0]).
514-
is_user(U) -> is_record(U, #user).
504+
is_record(Term :: dynamic(), Name :: atom()) -> boolean().
515505
```
516506
517-
> Why not include curly brackets after the record name, for example
518-
> `is_record(R, #user{})`?
507+
`Name` must be the name of one of the following:
519508
520-
That would look like a record construction, which it is not.
509+
* a tuple record
510+
* a local native record
511+
* a native record imported using `-import_record()'
521512

522-
An attempt to use the existing `is_record/2` in the following way will
523-
result in a compilation error:
513+
When `is_record/2` is used in a guard, `Name` must be a literal atom;
514+
otherwise, there will be a compilation error. There will be a
515+
compilation error if `Name` is neither the name of a local record nor
516+
an imported native record.
524517

525-
```erlang
526-
-module(misc).
527-
-record #user() {a,b,c}.
528-
is_user(U) -> is_record(U, user).
529-
```
518+
If `is_record/2` is used in a function body, `Name` is allowed to be a
519+
variable.
530520

531-
Rationale: It is preferable to only having one syntax for testing for a
532-
native. Therefore, the `#` is required. In practice, when migrating old
533-
code, it is better to use pattern matching to test for a record:
521+
Examples:
534522

535523
```erlang
536524
-module(misc).
537525
-record #user() {a,b,c}.
538526

539-
is_user(#user{}) ->
540-
true;
541-
is_user(#some_module:other_user{}) ->
527+
is_user(U) when is_record(U, user) ->
542528
true;
543529
is_user(_U) ->
544530
false.
545531
```
546532

533+
<!-- -->
534+
535+
```erlang
536+
-module(example).
537+
-import_record(misc, [user/0]).
538+
is_user(U) -> is_record(U, user).
539+
```
540+
547541
#### `is_record/1`
548542

549543
```erlang

0 commit comments

Comments
 (0)