Cosine Similarity

Weight: 1.0

What It Does

Compares two code files by treating them as bags of tokens (words) and measuring the angle between their frequency vectors. Identical documents have cosine = 1; completely different documents have cosine = 0.

The Math

Given two documents represented as term-frequency vectors A and B:

similarity(A, B) = (A · B) / (‖A‖ × ‖B‖)

where:
  A · B    = Σ(aᵢ × bᵢ)       (dot product)
  ‖A‖     = √(Σ(aᵢ²))         (L2 norm)

Example

Given two code snippets:

File A: "int x = 5; int y = 10; return x + y;"
File B: "int a = 5; int b = 10; return a + b;"

After tokenization:

  • A: {int: 2, x: 2, 5: 1, y: 2, 10: 1, return: 1}
  • B: {int: 2, a: 2, 5: 1, b: 2, 10: 1, return: 1}

Shared tokens: int, 5, 10, return → significant overlap.

After identifier normalization (a preprocessing step), both become:

  • {int: 2, v0: 2, 5: 1, v1: 2, 10: 1, return: 1}

Now cosine similarity = 1.0 (identical).

Why It Works for Plagiarism Detection

  • Captures the overall “vocabulary” of a program
  • Insensitive to token ordering (reordering lines doesn’t help)
  • Combined with preprocessing (case fold, identifier normalize), it catches renamed-variable plagiarism

Limitations

  • Doesn’t capture structure — two programs with the same tokens in completely different order score identically
  • Short programs may score high by coincidence (few unique tokens)
  • That’s why Analogi uses multiple analyzers, not just cosine

Threshold

Only triggers when similarity > 0.6 (60%). Below this, most code is coincidentally similar due to language keywords.

Further Reading

  • Singhal, A. (2001). “Modern Information Retrieval: A Brief Overview.” IEEE Data Engineering Bulletin.
  • Manning, C.D., Raghavan, P., & Schütze, H. (2008). Introduction to Information Retrieval, Chapter 6.