Spaces:
Runtime error
Runtime error
| import spacy | |
| from rapidfuzz import process | |
| from nltk import ngrams | |
| from nltk.tokenize import word_tokenize | |
| from huggingface_hub import snapshot_download | |
| class SkillListMatcher: | |
| """ | |
| Provides methods to extract and match skills from text. | |
| """ | |
| def __init__(self, spacy_model= "en_core_web_sm"): | |
| """ | |
| Initializes the matcher and loads the spaCy model. | |
| :param spacy_model: Name of the spaCy model to load. | |
| """ | |
| if not spacy.util.is_package(spacy_model): | |
| spacy.cli.download(spacy_model) | |
| self.nlp = spacy.load(spacy_model) | |
| def __lemmatization(self, skills): | |
| """ | |
| Lemmatizes a list of skills. | |
| :param skills: List of skill strings. | |
| :return: List of lemmatized skills. | |
| """ | |
| new_skills = [] | |
| for i in range(len(skills)): | |
| skill = skills[i] | |
| doc = self.nlp(skill) | |
| tokens = [token.lemma_ for token in doc] | |
| new_skills.append(" ".join(tokens).lower().strip()) | |
| return new_skills | |
| def extract(self, text, skills, threshold=95): | |
| """ | |
| Extracts relevant skills from the given text. | |
| :param text: The input text. | |
| :param skills: List of reference skill strings. | |
| :param threshold: Threshold for matching skills. | |
| :return: List of matched skills found in the text. | |
| """ | |
| text = text.lower() | |
| tokens = word_tokenize(text) | |
| candidates = set() | |
| for n in range(1, 5): | |
| for gram in ngrams(tokens, n): | |
| phrase = ' '.join(gram) | |
| candidates.add(phrase) | |
| new_skills = self.__lemmatization(skills) | |
| found_skills = set() | |
| for phrase in candidates: | |
| match, score, _ = process.extractOne(phrase, new_skills) | |
| if score >= threshold: | |
| found_skills.add(match) | |
| return list(found_skills) | |
| def match(self, main_skills, extract_skills): | |
| """ | |
| Matches extracted skills with main skills. | |
| :param main_skills: List of target skill strings. | |
| :param extract_skills: List of extracted skill strings. | |
| :return: Tuple of match ratio and formatted match string. | |
| """ | |
| main_skills = self.__lemmatization(main_skills) | |
| extract_skills = self.__lemmatization(extract_skills) | |
| count = 0 | |
| for skill in extract_skills: | |
| if skill in main_skills: | |
| count += 1 | |
| return count / len(main_skills), f"{count}/{len(main_skills)}" | |
| class SkillDynamicMatcher: | |
| """ | |
| Extracts and matches skills using a trained spaCy NER model. | |
| """ | |
| def __init__(self, model_path="amjad-awad/skill-extractor"): | |
| """ | |
| Initializes the NER model from the specified path. | |
| :param model_path: Path to the trained NER model. | |
| """ | |
| model_path = snapshot_download(model_path, repo_type="model") | |
| self.ner_model = spacy.load(model_path) | |
| def extract(self, text): | |
| """ | |
| Extracts skill entities from the input text. | |
| :param text: The input text. | |
| :return: List of extracted skill entities. | |
| """ | |
| skills = [] | |
| doc = self.ner_model(text) | |
| for ent in doc.ents: | |
| if "SKILLS" in ent.label_: | |
| skills.append(ent.text.lower()) | |
| return list(set(skills)) | |
| def match(self, main_skills, extract_skills): | |
| """ | |
| Matches extracted skills with main skills. | |
| :param main_skills: List of target skill strings. | |
| :param extract_skills: List of extracted skill strings. | |
| :return: Tuple of match ratio and formatted match string. | |
| """ | |
| count = 0 | |
| for skill in extract_skills: | |
| if skill in main_skills: | |
| count += 1 | |
| return count / len(main_skills), f"{count}/{len(main_skills)}" |