11import { useMemo } from 'react' ;
2- import { StepType , JAVA_LINE_MAPPING } from '../types' ;
3- import { getJavaPermutationCode , getCurrentExecutionLine } from '../engine/javaTokenizer' ;
2+ import { StepType } from '../types' ;
3+ import { ProgrammingLanguage , LANGUAGE_CONFIGS , getLanguageConfig } from '../types/languages' ;
4+ import {
5+ getCodeLines ,
6+ getHighlightedLines ,
7+ getCurrentExecutionLine ,
8+ getLineVariableMapping
9+ } from '../engine/multiLangTokenizer' ;
410import './CodeEditor.css' ;
511
612interface CodeEditorProps {
@@ -9,46 +15,36 @@ interface CodeEditorProps {
915 available ?: number [ ] ;
1016 inputNumbers ?: number [ ] ;
1117 resultCount ?: number ;
18+ language : ProgrammingLanguage ;
19+ onLanguageChange : ( lang : ProgrammingLanguage ) => void ;
1220}
1321
14- // 定义哪些行需要显示哪些变量的值
15- const LINE_VARIABLE_MAPPING : Record < number , string [ ] > = {
16- 3 : [ 'res' ] , // List<List<Integer>> res = new ArrayList<>();
17- 4 : [ 'len' ] , // int len = nums.length;
18- 5 : [ 'used' ] , // boolean[] used = new boolean[len];
19- 6 : [ 'path' ] , // Deque<Integer> path = new ArrayDeque<>();
20- 11 : [ 'depth' ] , // void dfs(..., int depth, ...)
21- 14 : [ 'depth' , 'len' ] , // if (depth == len)
22- 18 : [ 'i' , 'len' ] , // for (int i = 0; i < len; i++)
23- 19 : [ 'used[i]' ] , // if (used[i]) continue;
24- 20 : [ 'nums[i]' ] , // path.addLast(nums[i]);
25- 21 : [ 'used[i]' ] , // used[i] = true;
26- } ;
27-
2822export function CodeEditor ( {
2923 currentStepType,
3024 currentPath = [ ] ,
3125 available = [ ] ,
3226 inputNumbers = [ ] ,
3327 resultCount = 0 ,
28+ language,
29+ onLanguageChange,
3430} : CodeEditorProps ) {
35- const codeLines = useMemo ( ( ) => getJavaPermutationCode ( ) , [ ] ) ;
31+ const codeLines = useMemo ( ( ) => getCodeLines ( language ) , [ language ] ) ;
32+ const langConfig = useMemo ( ( ) => getLanguageConfig ( language ) , [ language ] ) ;
33+ const lineVariableMapping = useMemo ( ( ) => getLineVariableMapping ( language ) , [ language ] ) ;
3634
3735 const highlightedLines = useMemo ( ( ) => {
38- if ( ! currentStepType ) return [ ] ;
39- return JAVA_LINE_MAPPING [ currentStepType ] || [ ] ;
40- } , [ currentStepType ] ) ;
36+ return getHighlightedLines ( language , currentStepType ) ;
37+ } , [ language , currentStepType ] ) ;
4138
4239 const currentExecutionLine = useMemo ( ( ) => {
43- return getCurrentExecutionLine ( currentStepType ) ;
44- } , [ currentStepType ] ) ;
40+ return getCurrentExecutionLine ( language , currentStepType ) ;
41+ } , [ language , currentStepType ] ) ;
4542
4643 // 计算变量值
4744 const getVariableValue = useMemo ( ( ) => {
4845 const depth = currentPath . length ;
4946 const len = inputNumbers . length ;
5047 const used = inputNumbers . map ( n => ! available . includes ( n ) ) ;
51- // 当前正在处理的索引 (最后选择的数字在原数组中的位置)
5248 const currentI = currentPath . length > 0
5349 ? inputNumbers . indexOf ( currentPath [ currentPath . length - 1 ] )
5450 : 0 ;
@@ -58,6 +54,7 @@ export function CodeEditor({
5854 case 'res' :
5955 return `size=${ resultCount } ` ;
6056 case 'len' :
57+ case 'n' :
6158 return `${ len } ` ;
6259 case 'used' :
6360 return `[${ used . map ( u => u ? 'T' : 'F' ) . join ( ', ' ) } ]` ;
@@ -79,7 +76,7 @@ export function CodeEditor({
7976
8077 // 获取某行的变量值显示
8178 const getLineVariableDisplay = ( lineNumber : number ) : string | null => {
82- const variables = LINE_VARIABLE_MAPPING [ lineNumber ] ;
79+ const variables = lineVariableMapping [ lineNumber ] ;
8380 if ( ! variables || inputNumbers . length === 0 ) return null ;
8481
8582 const values = variables
@@ -95,8 +92,23 @@ export function CodeEditor({
9592 return (
9693 < div className = "code-editor" >
9794 < div className = "editor-header" >
98- < span className = "file-icon" > ☕</ span >
99- < span className = "file-name" > Solution.java</ span >
95+ < div className = "file-info" >
96+ < span className = "file-icon" > { langConfig . icon } </ span >
97+ < span className = "file-name" > { langConfig . fileName } </ span >
98+ </ div >
99+ < div className = "language-selector" >
100+ { LANGUAGE_CONFIGS . map ( ( config ) => (
101+ < button
102+ key = { config . id }
103+ className = { `lang-btn ${ language === config . id ? 'active' : '' } ` }
104+ onClick = { ( ) => onLanguageChange ( config . id ) }
105+ title = { config . name }
106+ >
107+ < span className = "lang-icon" > { config . icon } </ span >
108+ < span className = "lang-name" > { config . name } </ span >
109+ </ button >
110+ ) ) }
111+ </ div >
100112 </ div >
101113 < div className = "editor-content" >
102114 { codeLines . map ( ( line ) => {
@@ -120,7 +132,10 @@ export function CodeEditor({
120132 </ span >
121133 ) ) }
122134 { variableDisplay && (
123- < span className = "inline-variable-value" > // { variableDisplay } </ span >
135+ < span className = "inline-variable-value" >
136+ { language === 'python' ? ' # ' : ' // ' }
137+ { variableDisplay }
138+ </ span >
124139 ) }
125140 </ div >
126141 </ div >
@@ -134,14 +149,13 @@ export function CodeEditor({
134149/**
135150 * 用于测试的辅助函数:获取高亮行号
136151 */
137- export function getHighlightedLineNumbers ( stepType : StepType | null ) : number [ ] {
138- if ( ! stepType ) return [ ] ;
139- return JAVA_LINE_MAPPING [ stepType ] || [ ] ;
152+ export function getHighlightedLineNumbers ( stepType : StepType | null , lang : ProgrammingLanguage = 'java' ) : number [ ] {
153+ return getHighlightedLines ( lang , stepType ) ;
140154}
141155
142156/**
143157 * 用于测试的辅助函数:获取代码行数
144158 */
145- export function getCodeLineCount ( ) : number {
146- return getJavaPermutationCode ( ) . length ;
159+ export function getCodeLineCount ( lang : ProgrammingLanguage = 'java' ) : number {
160+ return getCodeLines ( lang ) . length ;
147161}
0 commit comments