027_自己实现一个ArrayList

这篇文章详细介绍了如何自定义一个MyArrayList类,包括构造方法、数组操作、扩容、边界检查和元素的添加、删除与获取。重点展示了如何利用Java数组实现类似ArrayList的功能并处理容量调整。
import java.util.Arrays;

/**
 * 自定义ArrayList
 */
public class MyArrayList {
	private Object[] elementData = {};
	private int size;
	
	/**
	 * 构造方法
	 */
	public MyArrayList() { }
	
	/**
	 * 数组大小
	 * @return
	 */
	public int size() {
		return size;
	}
	
	/**
	 * 数组是否为空
	 * @return
	 */
	public boolean isEmpty() {
		return size == 0;
	}
	
	/**
	 * 扩容
	 * @param minCapacity
	 */
	private void grow(int minCapacity) {
		if(minCapacity - elementData.length > 0) {
			int oldCapacity = elementData.length;
			int newCapacity = oldCapacity + (oldCapacity >> 1);
			if(newCapacity - minCapacity < 0) {
				newCapacity = minCapacity;
			}
			elementData = Arrays.copyOf(elementData, newCapacity);
		}
	}
	
	/**
	 * 检测下标是否越界
	 * @param index
	 */
	private void checkRange(int index) {
		if(index >= size || index < 0) {
			throw new IndexOutOfBoundsException();
		}
	}
	
	/**
	 * 添加元素到末尾
	 * @param o
	 * @return
	 */
	public boolean add(Object o) {
		grow(size + 1);
		elementData[size++] = o;
		return true;
	}
	
	/**
	 * 添加元素到指定位置
	 * @param index
	 * @param o
	 */
	public void add(int index, Object o) {
		if(!(index <= size && index >= 0)) {
			throw new IndexOutOfBoundsException();
		}
		
		grow(size + 1);
		System.arraycopy(elementData, index, elementData, index + 1, size - index);
		elementData[index] = o;
		size++;
	}
	
	/**
	 * 根据下标获取元素
	 * @param index
	 * @return
	 */
	public Object get(int index) {
		checkRange(index);
		
		return elementData[index];
	}
	
	/**
	 * 删除元素
	 * @param index
	 */
	private void fastRemove(int index) {
		int numMoved = size - index - 1;
		if(numMoved > 0) {
			System.arraycopy(elementData, index + 1, elementData, index, numMoved);
		}
		elementData[--size] = null;
	}
	
	/**
	 * 根据下标删除元素
	 * @param index
	 * @return
	 */
	public Object remove(int index) {
		checkRange(index);
		
		Object oldValue = get(index);
		fastRemove(index);
		
		return oldValue;
	}
	
	/**
	 * 根据元素删除数组中的元素
	 * @param o
	 * @return
	 */
	public boolean remove(Object o) {
		if(o == null) {
			for(int i = 0; i < size; i++) {
				if(elementData[i] == null) {
					fastRemove(i);
					return true;
				}
			}
		}else {
			for(int i = 0; i < size; i++) {
				if(o.equals(elementData[i])) {
					fastRemove(i);
					return true;
				}
			}
		}
		return false;
	}
}

 

<?xml version="1.0" encoding="UTF-8"?> <bpmn2:definitions xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:bpmn2="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:dc="http://www.omg.org/spec/DD/20100524/DC" xmlns:di="http://www.omg.org/spec/DD/20100524/DI" xmlns:camunda="http://camunda.org/schema/1.0/bpmn" id="diagram_approval_process--Process_1756947671990" targetNamespace="http://bpmn.io/schema/bpmn" xsi:schemaLocation="http://www.omg.org/spec/BPMN/20100524/MODEL BPMN20.xsd"> <bpmn2:process id="approval_process--Process_1756947671990" name="业务流程_1756947671990" isExecutable="true"> <bpmn2:startEvent id="Event_1x7vje5"> <bpmn2:outgoing>Flow_0suu6jo</bpmn2:outgoing> </bpmn2:startEvent> <bpmn2:userTask id="Activity_0olalgm" camunda:candidateUsers="1948194536744407041,2,1"> <bpmn2:extensionElements> <camunda:property name="dataType" value="USERS" /> </bpmn2:extensionElements> <bpmn2:incoming>Flow_0suu6jo</bpmn2:incoming> <bpmn2:outgoing>Flow_1w7da49</bpmn2:outgoing> <bpmn2:multiInstanceLoopCharacteristics camunda:collection="${multiInstanceHandler.getUserIds(execution)}" camunda:elementVariable="assignee" camunda:assignee="${assignee}"> <bpmn2:completionCondition xsi:type="bpmn2:tFormalExpression">${nrOfCompletedInstances >= nrOfInstances}</bpmn2:completionCondition> </bpmn2:multiInstanceLoopCharacteristics> </bpmn2:userTask> <bpmn2:sequenceFlow id="Flow_0suu6jo" sourceRef="Event_1x7vje5" targetRef="Activity_0olalgm" /> <bpmn2:userTask id="Activity_1lhfp6e" camunda:candidateUsers="1948194536744407041,2,1"> <bpmn2:extensionElements> <camunda:property name="dataType" value="USERS" /> </bpmn2:extensionElements> <bpmn2:incoming>Flow_1w7da49</bpmn2:incoming> <bpmn2:outgoing>Flow_1vn8upu</bpmn2:outgoing> <bpmn2:multiInstanceLoopCharacteristics camunda:collection="${multiInstanceHandler.getUserIds(execution)}" camunda:elementVariable="assignee" camunda:assignee="${assignee}"> <bpmn2:completionCondition xsi:type="bpmn2:tFormalExpression">${nrOfCompletedInstances > 0}</bpmn2:completionCondition> </bpmn2:multiInstanceLoopCharacteristics> </bpmn2:userTask> <bpmn2:sequenceFlow id="Flow_1w7da49" sourceRef="Activity_0olalgm" targetRef="Activity_1lhfp6e" /> <bpmn2:endEvent id="Event_027uz12"> <bpmn2:incoming>Flow_1vn8upu</bpmn2:incoming> </bpmn2:endEvent> <bpmn2:sequenceFlow id="Flow_1vn8upu" sourceRef="Activity_1lhfp6e" targetRef="Event_027uz12" /> </bpmn2:process> <bpmndi:BPMNDiagram id="BPMNDiagram_1"> <bpmndi:BPMNPlane id="BPMNPlane_1" bpmnElement="approval_process--Process_1756947671990"> <bpmndi:BPMNEdge id="Flow_0suu6jo_di" bpmnElement="Flow_0suu6jo"> <di:waypoint x="468" y="260" /> <di:waypoint x="520" y="260" /> </bpmndi:BPMNEdge> <bpmndi:BPMNEdge id="Flow_1w7da49_di" bpmnElement="Flow_1w7da49"> <di:waypoint x="620" y="260" /> <di:waypoint x="680" y="260" /> </bpmndi:BPMNEdge> <bpmndi:BPMNEdge id="Flow_1vn8upu_di" bpmnElement="Flow_1vn8upu"> <di:waypoint x="780" y="260" /> <di:waypoint x="842" y="260" /> </bpmndi:BPMNEdge> <bpmndi:BPMNShape id="Event_1x7vje5_di" bpmnElement="Event_1x7vje5"> <dc:Bounds x="432" y="242" width="36" height="36" /> </bpmndi:BPMNShape> <bpmndi:BPMNShape id="Activity_0olalgm_di" bpmnElement="Activity_0olalgm"> <dc:Bounds x="520" y="220" width="100" height="80" /> </bpmndi:BPMNShape> <bpmndi:BPMNShape id="Activity_1lhfp6e_di" bpmnElement="Activity_1lhfp6e"> <dc:Bounds x="680" y="220" width="100" height="80" /> </bpmndi:BPMNShape> <bpmndi:BPMNShape id="Event_027uz12_di" bpmnElement="Event_027uz12"> <dc:Bounds x="842" y="242" width="36" height="36" /> </bpmndi:BPMNShape> </bpmndi:BPMNPlane> </bpmndi:BPMNDiagram> </bpmn2:definitions> 我发起流程,流程直接到了结束节点直接已完成了,上面是页面生成的xml,下面是我的多实例处理用户信息的方法@Slf4j @AllArgsConstructor @Component("multiInstanceHandler") public class MultiInstanceHandler { @Resource private RepositoryService repositoryService; @Resource private RuntimeService runtimeService; private static final String CAMUNDA_NAMESPACE = "http://camunda.org/schema/1.0/bpmn"; //2025-0902旧 public List<String> getUserIds(DelegateExecution execution) { List<String> candidateUserIds = new ArrayList<>(); String processDefinitionId = execution.getProcessDefinitionId(); // 步骤1:从BPMN模型中获取多实例UserTask(固定原始ID) BpmnModelInstance modelInstance = repositoryService.getBpmnModelInstance(processDefinitionId); if (modelInstance == null) { return candidateUserIds; } // 步骤2:遍历模型,找到配置了多实例的UserTask(原始活动ID) UserTask multiInstanceTask = null; Collection<UserTask> userTasks = modelInstance.getModelElementsByType(UserTask.class); for (UserTask userTask : userTasks) { // 判断是否为多实例任务(通过loopCharacteristics) if (userTask.getLoopCharacteristics() instanceof MultiInstanceLoopCharacteristics) { multiInstanceTask = userTask; break; // 假设只有一个多实例任务,多个时需调整逻辑 } } if (multiInstanceTask == null) { log.warn("未找到多实例UserTask"); return candidateUserIds; } // 步骤3:使用模型中的多实例任务处理候选用户(替代原currentActivityId逻辑) String originalActivityId = multiInstanceTask.getId(); // 原始ID(如Activity_0apk00f) ExtensionElements extensionElements = multiInstanceTask.getExtensionElements(); if (extensionElements == null) { return candidateUserIds; } // 解析camunda:property(dataType) String dataType = ""; for (ModelElementInstance element : extensionElements.getElements()) { DomElement domElement = element.getDomElement(); if (ProcessConstants.NAMASPASE.equals(domElement.getNamespaceURI()) && "property".equals(domElement.getLocalName())) { dataType = domElement.getAttribute("value"); } } // 处理候选用户/组逻辑(与原逻辑一致) if ("USERS".equals(dataType)) { // 从流程变量中获取前端传入的用户列表(camunda:collection配置的值) Object collection = execution.getVariable("assignee_collection"); if (collection instanceof List) { candidateUserIds = (List<String>) collection; } log.info("用户会签 - 直接使用前端配置的用户列表: {}", candidateUserIds); return candidateUserIds; } else if (CollUtil.isNotEmpty(multiInstanceTask.getCamundaCandidateGroupsList())) { List<Long> groups = multiInstanceTask.getCamundaCandidateGroupsList().stream() .map(item -> Long.parseLong(item.substring(4))) // 假设组ID格式为"ROLE1"→提取"1" .collect(Collectors.toList()); List<Long> userIds = new ArrayList<>(); if ("ROLES".equals(dataType)) { // 通过角色ID查询用户 LambdaQueryWrapper<SysUserRole> lqw = Wrappers.lambdaQuery(SysUserRole.class) .select(SysUserRole::getUserId) .in(SysUserRole::getRoleId, groups); userIds = SimpleQuery.list(lqw, SysUserRole::getUserId); } else if ("DEPTS".equals(dataType)) { // 通过部门ID查询用户 LambdaQueryWrapper<SysUser> lqw = Wrappers.lambdaQuery(SysUser.class) .select(SysUser::getUserId) .in(SysUser::getDeptId, groups); userIds = SimpleQuery.list(lqw, SysUser::getUserId); } for (Long userId : userIds) { candidateUserIds.add(userId.toString()); } } log.info("多实例候选用户结果:size={}, 内容={}", candidateUserIds.size(), candidateUserIds); return candidateUserIds; } }
最新发布
09-05
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值