Topsis-Anvvi-102317133 1.0.0
TOPSIS multi-criteria decision making — CLI tool with sensitivity dashboard
Requires Python: >=3.7

# Topsis-Anvvi-102317133

A Python package implementing the **TOPSIS** (Technique for Order of Preference by Similarity to Ideal Solution) multi-criteria decision analysis method. Supports CSV and Excel input, automatic ordinal encoding, null handling, and an optional interactive **sensitivity analysis dashboard**.

---

## Table of Contents

- [Installation](#installation)
- [Method Overview](#method-overview)
- [Command-Line Usage](#command-line-usage)
- [Input File Format](#input-file-format)
- [Ordinal Encoding](#ordinal-encoding)
- [Null Handling](#null-handling)
- [Output Format](#output-format)
- [Sensitivity Analysis Dashboard](#sensitivity-analysis-dashboard)
- [Programmatic API](#programmatic-api)
- [Requirements](#requirements)
- [License](#license)

---

## Installation
```bash
pip install Topsis-Anvvi-102317133
```

---

## Method Overview

TOPSIS ranks a set of alternatives by measuring how close each one is to an **ideal best** solution and how far it is from an **ideal worst** solution. The algorithm proceeds as follows:

1. **Normalise** the decision matrix using Euclidean (column-wise) normalisation
2. **Apply weights** to produce a weighted normalised matrix
3. Determine the **ideal best** and **ideal worst** vectors, respecting each criterion's impact direction (`+` beneficial, `-` cost)
4. Compute **Euclidean distances** from each alternative to both ideal vectors
5. Calculate the **TOPSIS score** — a value in [0, 1] where higher is better:
```
Score(i) = dist_worst(i) / (dist_best(i) + dist_worst(i))
```

6. **Rank** alternatives by score in descending order

---

## Command-Line Usage
```bash
topsis <InputFile> <Weights> <Impacts> <ResultFile> [--sensitivity]
```

### Arguments

| Argument | Type | Description |
|---|---|---|
| `InputFile` | `str` | Path to input `.csv` or `.xlsx` file |
| `Weights` | `str` | Comma-separated positive numbers e.g. `"1,1,2,1"` |
| `Impacts` | `str` | Comma-separated `+` or `-` signs e.g. `"+,+,-,+"` |
| `ResultFile` | `str` | Path for output `.csv` or `.xlsx` file |
| `--sensitivity` | flag | Optional — generates an interactive HTML dashboard |

### Examples
```bash
# Basic usage
topsis data.csv "1,1,2,1" "+,+,-,+" result.csv

# With sensitivity dashboard
topsis data.csv "1,1,2,1" "+,+,-,+" result.csv --sensitivity

# Excel input and output
topsis data.xlsx "1,1,2,1" "+,+,-,+" result.xlsx --sensitivity
```

---

## Input File Format

The input file must follow this structure:

- **Column 1** — Alternative names (any string label)
- **Columns 2 onward** — Criteria values (numeric, or ordinal text — see below)
- The number of criteria columns must equal the number of weights and impacts provided

### Sample Input (`data.csv`)

| Model | Cost ($) | Storage (GB) | Camera (MP) | Battery | Rating  |
|-------|----------|--------------|-------------|---------|---------|
| M1    | 250      | 16           | 12          | 5000    | good    |
| M2    | 200      | 32           | 13          | 3000    | poor    |
| M3    | 300      | 32           | 12          | 3500    | good    |
| M4    | 275      | 32           | 17          | 2500    | average |
| M5    | 225      | 16           | 13          | 4800    | excellent|
```bash
topsis data.csv "1,1,1,1,1" "-,+,+,+,+" result.csv
```

Cost has impact `-` (lower is better). All others have impact `+` (higher is better). The text column `Rating` is automatically encoded.

---

## Ordinal Encoding

Non-numeric text columns are automatically detected and encoded to integers if they match a known ordinal scale:

| Level | Scale Values | Encoded As |
|-------|-------------|------------|
| 2 | `no`, `yes` | 0, 1 |
| 2 | `false`, `true` | 0, 1 |
| 3 | `low`, `medium`, `high` | 1, 2, 3 |
| 3 | `bad`, `moderate`, `good` | 1, 2, 3 |
| 3 | `poor`, `average`, `good` | 1, 2, 3 |
| 3 | `weak`, `moderate`, `strong` | 1, 2, 3 |
| 3 | `small`, `medium`, `large` | 1, 2, 3 |
| 4 | `poor`, `average`, `good`, `excellent` | 1, 2, 3, 4 |
| 4 | `low`, `medium`, `high`, `very high` | 1, 2, 3, 4 |
| 5 | `very bad`, `bad`, `moderate`, `good`, `very good` | 1, 2, 3, 4, 5 |
| 5 | `very low`, `low`, `medium`, `high`, `very high` | 1, 2, 3, 4, 5 |
| 5 | `very poor`, `poor`, `average`, `good`, `excellent` | 1, 2, 3, 4, 5 |

> Matching is **case-insensitive** and trims whitespace. If a column contains text that doesn't match any known scale, the program exits with a descriptive error.

---

## Null Handling

Missing values are handled automatically before computation:

- **Rows where all criteria are null** — dropped entirely, with a warning printed
- **Numeric columns with nulls** — filled with the **column mean**
- **Text columns with nulls** — filled with the **column mode**

All substitutions are reported to stdout.

---

## Output Format

The result file contains all original columns plus two appended columns:

| Model | Cost ($) | ... | Topsis Score | Rank |
|-------|----------|-----|--------------|------|
| M5    | 225      | ... | 0.7623       | 1    |
| M1    | 250      | ... | 0.6891       | 2    |
| M3    | 300      | ... | 0.5340       | 3    |
| M4    | 275      | ... | 0.4102       | 4    |
| M2    | 200      | ... | 0.2987       | 5    |

- **Topsis Score** — float in [0, 1]; higher = better
- **Rank** — integer; 1 = best; ties share the same rank (dense ranking)

---

## Sensitivity Analysis Dashboard

When `--sensitivity` is passed, a self-contained HTML file is generated alongside the result (e.g. `result_sensitivity.html`). Open it in any browser — no server required.

### Features

- **Live weight sliders** — adjust each criterion's weight in real time; rankings update instantly
- **Score bars** — visual comparison of TOPSIS scores across all alternatives
- **Rank delta badges** — shows how many positions each alternative moved from the original ranking
- **Sweep analysis chart** — plots how every alternative's rank changes as one criterion's weight is swept from 0 → 5, while all others are held fixed
- **Natural-language insight** — auto-generated summary of the most significant rank change observed

### Interpreting the sweep chart

A **flat horizontal line** means an alternative's rank is robust to changes in that criterion. **Crossing lines** indicate rank reversals — points where two alternatives swap positions as the weight shifts.

---

## Programmatic API

TOPSIS can also be called directly from Python:
```python
from Topsis_Anvvi_102317133.Topsiss import topsis

result_df = topsis(
    input_file  = "data.csv",
    weights_str = "1,1,2,1",
    impacts_str = "+,+,-,+",
    result_file = "result.csv",
    sensitivity = True      # False to skip dashboard
)

print(result_df[["Topsis Score", "Rank"]])
```

The function returns the result `DataFrame` directly, in addition to writing it to disk.

---

## Requirements

| Package   | Minimum Version |
|-----------|----------------|
| Python    | 3.7+           |
| pandas    | 1.3.0          |
| numpy     | 1.21.0         |
| openpyxl  | 3.0.0          |

---

## License

MIT License — free to use, modify, and distribute.