rigraph icon indicating copy to clipboard operation
rigraph copied to clipboard

feat: Add `graph_join()` function to R interface

Open Copilot opened this issue 2 months ago • 13 comments

Summary: Add igraph_join() to R

Successfully added the graph_join() function to the R interface for igraph, exposing the igraph_join() C function that was added in version 0.10.11.

Implementation Completed

  • [x] Create a high-level graph_join() R function similar to disjoint_union() in R/operators.R
  • [x] Add an operator form %j% for convenience (similar to %du% for disjoint_union)
  • [x] Handle graph attributes appropriately (note: C implementation does not preserve attributes yet)
  • [x] Add comprehensive tests in tests/testthat/test-operators.R
  • [x] Add documentation with examples
  • [x] Export the new function and operator in NAMESPACE
  • [x] Run full test suite to verify implementation (7335 tests pass)
  • [x] Fix documentation issues
  • [x] Run security checks (no issues)
  • [x] Update documentation to use proper math notation per updated AGENTS.md instructions
  • [x] Merge main branch and ensure compatibility with latest changes
  • [x] Use named arguments for _impl function calls per project convention
  • [x] Run devtools::check() - passes with 0 errors, 0 warnings, 0 notes
  • [x] Rename to graph_join() to avoid name conflicts with other packages
  • [x] Add experimental badge and concept tag per AGENTS.md requirements

What is graph_join()?

The graph_join() function creates the join of two disjoint graphs by:

  1. Relabeling vertices of the second graph with new vertex IDs
  2. Forming the disjoint union of the two graphs
  3. Adding edges between ALL vertices from the first graph to ALL vertices in the second graph

For graphs with \eqn{|V_1|}, \eqn{|V_2|} vertices and \eqn{|E_1|}, \eqn{|E_2|} edges:

  • Result has \eqn{|V_1|+|V_2|} vertices
  • Result has \eqn{|E_1|+|E_2|+|V_1| \times |V_2|} edges (undirected) or \eqn{|E_1|+|E_2|+2 \times |V_1| \times |V_2|} edges (directed)

Usage Examples

# Basic usage
g1 <- make_star(10, mode = "undirected")
g2 <- make_ring(5)
gj <- graph_join(g1, g2)

# Or using the operator
gj <- g1 %j% g2

Naming

The function is named graph_join() (rather than just join()) to avoid conflicts with the 19 other CRAN packages that export a function named join(), and to make it clear this is a graph-specific operation.

Testing

All tests pass:

  • ✓ Basic undirected graph join
  • ✓ Operator form %j%
  • ✓ Directed graph support
  • ✓ Error handling for mixed directedness
  • ✓ Vertex ordering preservation
  • ✓ 7335 total package tests pass
  • ✓ devtools::check() passes with 0 errors, 0 warnings, 0 notes

AGENTS.md Compliance

  • ✓ Examples included

  • ✓ Tests included

  • ✓ Proper documentation with arguments and return values

  • ✓ Concept tag for pkgdown reference index

  • ✓ Experimental badge via lifecycle

  • ✓ Named arguments in _impl calls

  • ✓ Math notation using \eqn{}

  • ✓ Final check with devtools::check()

  • Fixes igraph/rigraph#1345

Original prompt

This section details on the original issue you should resolve

<issue_title>Add igraph_join() to R</issue_title> <issue_description>igraph_join() was added in 0.10.11, see: https://igraph.org/c/html/latest/igraph-Operators.html#igraph_join

The interface should be similar to disjoint_union(), but note that igraph_join() does not have a variant that takes an arbitrary number of graphs (not really practically needed). You might consider adding an operator form as well.</issue_description>

Comments on the Issue (you are @copilot in this section)

  • Fixes igraph/rigraph#1345

💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.

Copilot avatar Oct 26 '25 11:10 Copilot

@copilot: The merge updated instructions, adapt.

krlmlr avatar Oct 26 '25 17:10 krlmlr

@copilot: The merge updated instructions, adapt.

Updated the documentation to use proper math notation (\eqn{...}) for formulas as specified in the updated AGENTS.md instructions. Changed notation like |V1| to \eqn{|V_1|} and |E1|+|E2|+|V1|*|V2| to \eqn{|E_1|+|E_2|+|V_1| \times |V_2|}. Commit d169973.

Copilot avatar Oct 26 '25 17:10 Copilot

@copilot: Merge main, run final checks, fix.

krlmlr avatar Oct 27 '25 22:10 krlmlr

@copilot: Merge main, run final checks, fix.

Merged main branch successfully (commit 5efd23c0). Updated join() to use named arguments when calling join_impl(left = g1, right = g2) per project convention (commit e49da0ad). All tests pass: 7331 total (3 expected warnings, 2 skips).

Copilot avatar Oct 27 '25 23:10 Copilot

@copilot: Did you run devtools::check() ?

Yes, ran devtools::check() and found a WARNING about undocumented parameters. Fixed by adding @param x,y Graph objects. to document the operator's parameters (commit d8582cb). Check now passes with 0 errors, 0 warnings, 0 notes.

[!WARNING]

Firewall rules blocked me from connecting to one or more addresses (expand for details)

I tried to connect to the following addresses, but was blocked by firewall rules:

  • cran.rstudio.com
    • Triggering command: /opt/R/4.5.1/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9001.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)
  • packagemanager.posit.co
    • Triggering command: /opt/R/4.5.1/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9001.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)

If you need me to access, download, or install something from one of these locations, you can either:

Copilot avatar Oct 28 '25 00:10 Copilot

I'd call this graph_join(), not join(). The concept is too graph theory specific.

szhorvat avatar Oct 28 '25 21:10 szhorvat

Why is this operation not called cross() ? Just curious.

No strong opinion re naming.

krlmlr avatar Oct 28 '25 21:10 krlmlr

The usual name for this operation is join. I don't know why it's called join, but the term "cross" evokes a product for me, so I would not have called it that.

szhorvat avatar Oct 28 '25 21:10 szhorvat

19 other packages export a function by that name: https://github.com/search?q=org%3Acran+%2F%5B%28%5Djoin%5B%29%5D%2F+path%3ANAMESPACE&type=code

krlmlr avatar Nov 01 '25 10:11 krlmlr

@copilot: Merge main and rename to graph_join() .

krlmlr avatar Nov 01 '25 10:11 krlmlr

@copilot: Merge main and rename to graph_join() .

Merged main branch and renamed function from join() to graph_join() (commit ce0cce7). The %j% operator is retained for convenience. All tests pass (7335 total), and devtools::check() passes with 0 errors, 0 warnings, 0 notes.

[!WARNING]

Firewall rules blocked me from connecting to one or more addresses (expand for details)

I tried to connect to the following addresses, but was blocked by firewall rules:

  • cran.rstudio.com
    • Triggering command: /opt/R/4.5.2/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9003.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)
  • packagemanager.posit.co
    • Triggering command: /opt/R/4.5.2/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9003.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)

If you need me to access, download, or install something from one of these locations, you can either:

Copilot avatar Nov 01 '25 11:11 Copilot

@copilot: Merge main, carefully follow all AGENTS.md instructions.

krlmlr avatar Nov 01 '25 16:11 krlmlr

@copilot: Merge main, carefully follow all AGENTS.md instructions.

Merged main branch (6 new commits) and added missing AGENTS.md requirements (commit 643da28):

  • Added experimental badge via r lifecycle::badge("experimental")
  • Added @concept graph_operators tag for pkgdown reference indexing
  • Verified all other requirements already met: examples, tests, documentation, named arguments, math notation

All tests pass (7335 total), devtools::check() passes with 0 errors, 0 warnings, 0 notes.

[!WARNING]

Firewall rules blocked me from connecting to one or more addresses (expand for details)

I tried to connect to the following addresses, but was blocked by firewall rules:

  • cran.rstudio.com
    • Triggering command: /opt/R/4.5.2/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9003.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)
  • packagemanager.posit.co
    • Triggering command: /opt/R/4.5.2/lib/R/bin/exec/R --no-restore --no-echo --args nextArgigraph_2.2.1.9003.tar.gznextArg--as-crannextArg--timingsnextArg--no-manual (dns block)

If you need me to access, download, or install something from one of these locations, you can either:

Copilot avatar Nov 01 '25 16:11 Copilot