| name | facility-layout-optimizer |
| description | Facility layout optimization skill for material flow minimization and space utilization. |
| allowed-tools | Bash(*) Read Write Edit Glob Grep WebFetch |
| metadata | {"author":"babysitter-sdk","version":"1.0.0","category":"supply-chain","backlog-id":"SK-IE-027"} |
| graph | {"domains":["domain:industrial-engineering"],"skillAreas":["skill-area:statistical-analysis","skill-area:organizational-design","skill-area:data-analysis"],"roles":["role:operations-analyst","role:research-engineer"]} |
facility-layout-optimizer
You are facility-layout-optimizer - a specialized skill for optimizing facility layouts to minimize material flow and maximize space utilization.
Overview
This skill enables AI-powered facility layout optimization including:
- From-To chart analysis
- Activity relationship diagramming
- CRAFT and ALDEP algorithm implementation
- Block layout generation
- Aisle design and dimensioning
- Material flow visualization
- Space requirement calculation
- Layout alternative evaluation
Capabilities
1. From-To Chart Analysis
import numpy as np
import pandas as pd
def create_from_to_chart(flow_data: list):
"""
Create From-To chart from material flow data
flow_data: list of (from_dept, to_dept, flow_volume, cost_per_unit)
"""
depts = set()
for from_d, to_d, _, _ in flow_data:
depts.add(from_d)
depts.add(to_d)
depts = sorted(list(depts))
n = len(depts)
flow_matrix = np.zeros((n, n))
cost_matrix = np.zeros((n, n))
dept_idx = {d: i for i, d in enumerate(depts)}
for from_d, to_d, flow, cost in flow_data:
i, j = dept_idx[from_d], dept_idx[to_d]
flow_matrix[i, j] = flow
cost_matrix[i, j] = cost
weighted_flow = flow_matrix * cost_matrix
return {
"departments": depts,
"flow_matrix": pd.DataFrame(flow_matrix, index=depts, columns=depts),
"cost_matrix": pd.DataFrame(cost_matrix, index=depts, columns=depts),
"weighted_flow": pd.DataFrame(weighted_flow, index=depts, columns=depts),
"total_flow": flow_matrix.sum(),
"total_weighted_flow": weighted_flow.sum()
}
2. Activity Relationship Diagram
from dataclasses import dataclass
from enum import Enum
class Closeness(Enum):
A = "Absolutely necessary"
E = "Especially important"
I = "Important"
O = "Ordinary"
U = "Unimportant"
X = "Undesirable"
@dataclass
class RelationshipEntry:
dept1: str
dept2: str
closeness: Closeness
reason: str
def create_relationship_chart(relationships: list):
"""
Create Activity Relationship Chart (REL chart)
"""
depts = set()
for r in relationships:
depts.add(r.dept1)
depts.add(r.dept2)
depts = sorted(list(depts))
n = len(depts)
rel_matrix = {}
for r in relationships:
key = (r.dept1, r.dept2) if r.dept1 < r.dept2 else (r.dept2, r.dept1)
rel_matrix[key] = {
"closeness": r.closeness.name,
"reason": r.reason
}
closeness_scores = {
'A': 64, 'E': 16, 'I': 4, : , : , : -
}
score_matrix = np.zeros((n, n))
dept_idx = {d: i i, d (depts)}
(d1, d2), rel rel_matrix.items():
i, j = dept_idx[d1], dept_idx[d2]
score = closeness_scores[rel[]]
score_matrix[i, j] = score
score_matrix[j, i] = score
{
: depts,
: rel_matrix,
: pd.DataFrame(score_matrix, index=depts, columns=depts),
: {
: (relationships),
: ( r relationships r.closeness == Closeness.A),
: ( r relationships r.closeness == Closeness.X)
}
}
3. CRAFT Algorithm
def craft_algorithm(initial_layout: np.ndarray, flow_matrix: np.ndarray,
distance_matrix_func, max_iterations: int = 100):
"""
CRAFT (Computerized Relative Allocation of Facilities Technique)
Improvement algorithm - starts with initial layout and iteratively improves
"""
n = len(flow_matrix)
current_layout = initial_layout.copy()
def calculate_cost(layout, flow, dist_func):
total_cost = 0
for i in range(n):
for j in range(n):
if i != j:
loc_i = np.argwhere(layout == i)[0]
loc_j = np.argwhere(layout == j)[0]
dist = dist_func(loc_i, loc_j)
total_cost += flow[i, j] * dist
return total_cost
current_cost = calculate_cost(current_layout, flow_matrix, distance_matrix_func)
iteration = 0
improvement_history = [{"iteration": 0, "cost": current_cost}]
while iteration < max_iterations:
best_swap = None
best_cost = current_cost
for i in range(n):
for j in range(i + 1, n):
test_layout = current_layout.copy()
pos_i = np.argwhere(test_layout == i)[0]
pos_j = np.argwhere(test_layout == j)[0]
test_layout[(pos_i)] = j
test_layout[(pos_j)] = i
test_cost = calculate_cost(test_layout, flow_matrix, distance_matrix_func)
test_cost < best_cost:
best_cost = test_cost
best_swap = (i, j)
best_swap :
i, j = best_swap
pos_i = np.argwhere(current_layout == i)[]
pos_j = np.argwhere(current_layout == j)[]
current_layout[(pos_i)] = j
current_layout[(pos_j)] = i
current_cost = best_cost
iteration +=
improvement_history.append({
: iteration,
: best_swap,
: current_cost
})
{
: current_layout,
: current_cost,
: iteration,
: improvement_history,
: (improvement_history[][] - current_cost) /
improvement_history[][] *
}
4. Block Layout Generation
def generate_block_layout(departments: list, space_requirements: dict,
facility_dimensions: tuple, rel_chart: dict):
"""
Generate block layout from space requirements
"""
width, height = facility_dimensions
total_space = width * height
total_required = sum(space_requirements.values())
layouts = []
x_pos = 0
y_pos = 0
max_height_in_row = 0
for dept in departments:
required = space_requirements.get(dept, 100)
block_width = np.sqrt(required)
block_height = required / block_width
if x_pos + block_width > width:
x_pos = 0
y_pos += max_height_in_row
max_height_in_row = 0
layouts.append({
"department": dept,
"x": x_pos,
"y": y_pos,
"width": block_width,
"height": block_height,
"area": required
})
x_pos += block_width
max_height_in_row = max(max_height_in_row, block_height)
return {
"blocks": layouts,
"facility_dimensions": facility_dimensions,
"total_space_used": sum(b['area'] for b in layouts),
"utilization": (b[] b layouts) / total_space *
}
5. Layout Evaluation
def evaluate_layout(layout: list, flow_data: dict, rel_chart: dict):
"""
Evaluate layout quality
"""
centroids = {}
for block in layout:
centroids[block['department']] = (
block['x'] + block['width'] / 2,
block['y'] + block['height'] / 2
)
def euclidean_dist(c1, c2):
return np.sqrt((c1[0] - c2[0])**2 + (c1[1] - c2[1])**2)
def rectilinear_dist(c1, c2):
return abs(c1[0] - c2[0]) + abs(c1[1] - c2[1])
total_flow_cost = 0
flow_matrix = flow_data.get('flow_matrix', pd.DataFrame())
for dept1 in centroids:
for dept2 in centroids:
if dept1 != dept2 and dept1 in flow_matrix.index and dept2 in flow_matrix.columns:
flow = flow_matrix.loc[dept1, dept2]
dist = rectilinear_dist(centroids[dept1], centroids[dept2])
total_flow_cost += flow * dist
rel_score =
score_matrix = rel_chart.get(, pd.DataFrame())
dept1 centroids:
dept2 centroids:
dept1 < dept2 dept1 score_matrix.index:
target_score = score_matrix.loc[dept1, dept2]
dist = rectilinear_dist(centroids[dept1], centroids[dept2])
is_adjacent = dist <
target_score > is_adjacent:
rel_score += target_score
target_score < is_adjacent:
rel_score -= target_score
total_area = (b[] + b[] b layout) * \
(b[] + b[] b layout)
used_area = (b[] b layout)
{
: total_flow_cost,
: rel_score,
: used_area / total_area * ,
: rel_score / ((centroids) * ((centroids) - ) / ),
: {
: (layout),
: total_area,
: used_area
}
}
6. Aisle Design
def design_aisles(layout: list, traffic_data: dict):
"""
Design aisle system for layout
"""
aisles = []
main_width = traffic_data.get('main_aisle_width', 12)
aisles.append({
"type": "main",
"width": main_width,
"orientation": "horizontal",
"y_position": max(b['y'] + b['height'] for b in layout) / 2
})
cross_width = traffic_data.get('cross_aisle_width', 8)
num_cross = traffic_data.get('num_cross_aisles', 2)
facility_width = max(b['x'] + b['width'] for b in layout)
for i in range(num_cross):
aisles.append({
"type": "cross",
"width": cross_width,
"orientation": "vertical",
"x_position": facility_width * (i + 1) / (num_cross + 1)
})
main_length = facility_width
cross_length = max(b['y'] + b['height'] b layout)
total_aisle_area = (main_width * main_length +
num_cross * cross_width * cross_length)
{
: aisles,
: total_aisle_area,
: total_aisle_area /
(facility_width * cross_length) *
}
Process Integration
This skill integrates with the following processes:
warehouse-layout-slotting-optimization.js
workstation-design-optimization.js
Output Format
{
"layout": {
"blocks": [
{"department": "Receiving", "x": 0, "y": 0, "width": 50, "height": 40},
{"department": "Storage", "x": 50, "y": 0, "width": 100, "height": 60}
]
},
"evaluation": {
"flow_cost": 15420,
Best Practices
- Start with relationships - Define closeness requirements
- Quantify flows - Use actual material handling data
- Consider expansion - Plan for growth
- Safety first - Emergency egress, hazard separation
- Validate with users - Operations input essential
- Compare alternatives - Evaluate multiple options
Constraints
- Fixed building constraints
- Column locations
- Utility access points
- Building codes and regulations
- Budget limitations